Disconnect signals on dispose

This commit is contained in:
Ian Douglas Scott 2021-09-24 10:30:09 -07:00
parent 58e3850766
commit 397c671da0
2 changed files with 31 additions and 17 deletions

View file

@ -14,6 +14,7 @@ use crate::notifications::{Notification, NotificationId, Notifications};
pub struct NotificationListInner { pub struct NotificationListInner {
listbox: DerefCell<gtk4::ListBox>, listbox: DerefCell<gtk4::ListBox>,
notifications: DerefCell<Notifications>, notifications: DerefCell<Notifications>,
ids: RefCell<Vec<glib::SignalHandlerId>>,
rows: RefCell<HashMap<NotificationId, gtk4::ListBoxRow>>, rows: RefCell<HashMap<NotificationId, gtk4::ListBoxRow>>,
} }
@ -43,8 +44,12 @@ impl ObjectImpl for NotificationListInner {
self.listbox.set(listbox); self.listbox.set(listbox);
} }
fn dispose(&self, _obj: &NotificationList) { fn dispose(&self, obj: &NotificationList) {
self.listbox.unparent(); self.listbox.unparent();
for i in obj.inner().ids.take().into_iter() {
obj.inner().notifications.disconnect(i);
}
} }
} }
@ -59,14 +64,15 @@ impl NotificationList {
pub fn new(notifications: &Notifications) -> Self { pub fn new(notifications: &Notifications) -> Self {
let obj = glib::Object::new::<Self>(&[]).unwrap(); let obj = glib::Object::new::<Self>(&[]).unwrap();
// XXX disconnect?
obj.inner().notifications.set(notifications.clone()); obj.inner().notifications.set(notifications.clone());
notifications.connect_notification_recieved(clone!(@weak obj => move |notification| { *obj.inner().ids.borrow_mut() = vec![
obj.handle_notification(&notification); notifications.connect_notification_recieved(clone!(@weak obj => move |notification| {
})); obj.handle_notification(&notification);
notifications.connect_notification_closed(clone!(@weak obj => move |id| { })),
obj.remove_notification(id); notifications.connect_notification_closed(clone!(@weak obj => move |id| {
})); obj.remove_notification(id);
})),
];
obj obj
} }

View file

@ -14,6 +14,7 @@ use crate::notifications::{Notification, NotificationId, Notifications};
pub struct NotificationPopoverInner { pub struct NotificationPopoverInner {
notification_widget: DerefCell<NotificationWidget>, notification_widget: DerefCell<NotificationWidget>,
notifications: DerefCell<Notifications>, notifications: DerefCell<Notifications>,
ids: RefCell<Vec<glib::SignalHandlerId>>,
source: RefCell<Option<glib::SourceId>>, source: RefCell<Option<glib::SourceId>>,
} }
@ -54,6 +55,12 @@ impl ObjectImpl for NotificationPopoverInner {
}); });
}; };
} }
fn dispose(&self, obj: &NotificationPopover) {
for i in obj.inner().ids.take().into_iter() {
obj.inner().notifications.disconnect(i);
}
}
} }
impl WidgetImpl for NotificationPopoverInner {} impl WidgetImpl for NotificationPopoverInner {}
@ -74,16 +81,17 @@ impl NotificationPopover {
obj.set_child(Some(&notification_widget)); obj.set_child(Some(&notification_widget));
obj.inner().notification_widget.set(notification_widget); obj.inner().notification_widget.set(notification_widget);
// XXX disconnect?
obj.inner().notifications.set(notifications.clone()); obj.inner().notifications.set(notifications.clone());
notifications.connect_notification_recieved(clone!(@weak obj => move |notification| { *obj.inner().ids.borrow_mut() = vec![
obj.handle_notification(&notification); notifications.connect_notification_recieved(clone!(@weak obj => move |notification| {
})); obj.handle_notification(&notification);
notifications.connect_notification_closed(clone!(@weak obj => move |id| { })),
if obj.id() == Some(id) { notifications.connect_notification_closed(clone!(@weak obj => move |id| {
obj.popdown(); if obj.id() == Some(id) {
} obj.popdown();
})); }
})),
];
obj obj
} }