Skip to content

Commit c3fffca

Browse files
authored
Merge pull request #1575 from sdroege/override-signal
glib: Remove `SignalClassHandlerToken` from default class handler
2 parents 8044406 + 6a64a88 commit c3fffca

File tree

2 files changed

+68
-15
lines changed

2 files changed

+68
-15
lines changed

glib/src/subclass/object.rs

+63-1
Original file line numberDiff line numberDiff line change
@@ -404,7 +404,7 @@ mod test {
404404
.param_types([String::static_type()])
405405
.return_type::<String>()
406406
.action()
407-
.class_handler(|_, args| {
407+
.class_handler(|args| {
408408
let obj = args[0]
409409
.get::<super::SimpleObject>()
410410
.expect("Failed to get Object from args[0]");
@@ -426,6 +426,16 @@ mod test {
426426
super::Signal::builder("create-child-object")
427427
.return_type::<super::ChildObject>()
428428
.build(),
429+
super::Signal::builder("return-string")
430+
.return_type::<String>()
431+
.action()
432+
.class_handler(|args| {
433+
let _obj = args[0]
434+
.get::<super::SimpleObject>()
435+
.expect("Failed to get Object from args[0]");
436+
Some("base".to_value())
437+
})
438+
.build(),
429439
]
430440
})
431441
}
@@ -487,6 +497,33 @@ mod test {
487497
}
488498
}
489499

500+
#[derive(Default)]
501+
pub struct SimpleSubObject;
502+
503+
#[glib::object_subclass]
504+
impl ObjectSubclass for SimpleSubObject {
505+
const NAME: &'static str = "SimpleSubObject";
506+
type Type = super::SimpleSubObject;
507+
type ParentType = super::SimpleObject;
508+
509+
fn class_init(class: &mut Self::Class) {
510+
class.override_signal_class_handler("return-string", |token, args| {
511+
let obj = args[0]
512+
.get::<super::SimpleSubObject>()
513+
.expect("Failed to get Object from args[0]");
514+
515+
let res = obj.imp().signal_chain_from_overridden(token, args);
516+
assert_eq!(res.unwrap().get::<&str>().unwrap(), "base");
517+
518+
Some("sub".to_value())
519+
});
520+
}
521+
}
522+
523+
impl ObjectImpl for SimpleSubObject {}
524+
525+
impl SimpleObjectImpl for SimpleSubObject {}
526+
490527
#[derive(Clone, Copy)]
491528
#[repr(C)]
492529
pub struct DummyInterface {
@@ -514,6 +551,14 @@ mod test {
514551
pub struct SimpleObject(ObjectSubclass<imp::SimpleObject>);
515552
}
516553

554+
pub trait SimpleObjectImpl: ObjectImpl {}
555+
556+
unsafe impl<Obj: SimpleObjectImpl> IsSubclassable<Obj> for SimpleObject {}
557+
558+
wrapper! {
559+
pub struct SimpleSubObject(ObjectSubclass<imp::SimpleSubObject>) @extends SimpleObject;
560+
}
561+
517562
wrapper! {
518563
pub struct Dummy(ObjectInterface<imp::Dummy>);
519564
}
@@ -543,6 +588,14 @@ mod test {
543588
assert!(weak.upgrade().is_none());
544589
}
545590

591+
#[test]
592+
fn test_sub_create() {
593+
let obj = Object::builder::<SimpleSubObject>().build();
594+
assert!(obj.type_().is_a(SimpleObject::static_type()));
595+
assert_eq!(obj.type_(), SimpleSubObject::static_type());
596+
assert!(obj.property::<bool>("constructed"));
597+
}
598+
546599
#[test]
547600
fn test_properties() {
548601
let type_ = SimpleObject::static_type();
@@ -829,6 +882,8 @@ mod test {
829882
"old-name"
830883
);
831884
assert!(name_changed_triggered.load(Ordering::Relaxed));
885+
886+
assert_eq!(obj.emit_by_name::<String>("return-string", &[]), "base");
832887
}
833888

834889
#[test]
@@ -845,6 +900,13 @@ mod test {
845900
assert_eq!(value, "return value");
846901
}
847902

903+
#[test]
904+
fn test_signal_override() {
905+
let obj = Object::builder::<SimpleSubObject>().build();
906+
907+
assert_eq!(obj.emit_by_name::<String>("return-string", &[]), "sub");
908+
}
909+
848910
#[test]
849911
fn test_callback_validity() {
850912
use std::sync::{

glib/src/subclass/signal.rs

+5-14
Original file line numberDiff line numberDiff line change
@@ -16,9 +16,7 @@ pub struct SignalBuilder {
1616
flags: SignalFlags,
1717
param_types: Vec<SignalType>,
1818
return_type: SignalType,
19-
class_handler: Option<
20-
Box<dyn Fn(&SignalClassHandlerToken, &[Value]) -> Option<Value> + Send + Sync + 'static>,
21-
>,
19+
class_handler: Option<Box<dyn Fn(&[Value]) -> Option<Value> + Send + Sync + 'static>>,
2220
accumulator: Option<
2321
Box<dyn Fn(&SignalInvocationHint, &mut Value, &Value) -> bool + Send + Sync + 'static>,
2422
>,
@@ -352,11 +350,7 @@ impl IntoGlib for SignalType {
352350
#[allow(clippy::type_complexity)]
353351
enum SignalRegistration {
354352
Unregistered {
355-
class_handler: Option<
356-
Box<
357-
dyn Fn(&SignalClassHandlerToken, &[Value]) -> Option<Value> + Send + Sync + 'static,
358-
>,
359-
>,
353+
class_handler: Option<Box<dyn Fn(&[Value]) -> Option<Value> + Send + Sync + 'static>>,
360354
accumulator: Option<
361355
Box<dyn Fn(&SignalInvocationHint, &mut Value, &Value) -> bool + Send + Sync + 'static>,
362356
>,
@@ -472,9 +466,7 @@ impl SignalBuilder {
472466

473467
// rustdoc-stripper-ignore-next
474468
/// Class handler for this signal.
475-
pub fn class_handler<
476-
F: Fn(&SignalClassHandlerToken, &[Value]) -> Option<Value> + Send + Sync + 'static,
477-
>(
469+
pub fn class_handler<F: Fn(&[Value]) -> Option<Value> + Send + Sync + 'static>(
478470
mut self,
479471
func: F,
480472
) -> Self {
@@ -610,9 +602,8 @@ impl Signal {
610602
let return_type = self.return_type;
611603

612604
let class_handler = class_handler.map(|class_handler| {
613-
Closure::new(move |values| unsafe {
614-
let instance = gobject_ffi::g_value_get_object(values[0].to_glib_none().0);
615-
let res = class_handler(&SignalClassHandlerToken(instance as *mut _, return_type.into(), values.as_ptr()), values);
605+
Closure::new(move |values| {
606+
let res = class_handler(values);
616607

617608
if return_type == Type::UNIT {
618609
if let Some(ref v) = res {

0 commit comments

Comments
 (0)