Skip to content

Commit

Permalink
Add ns::NotificationGuard
Browse files Browse the repository at this point in the history
  • Loading branch information
yury committed Dec 30, 2023
1 parent 4130fc4 commit d53a7ee
Show file tree
Hide file tree
Showing 3 changed files with 79 additions and 6 deletions.
1 change: 1 addition & 0 deletions cidre/src/ns.rs
Original file line number Diff line number Diff line change
Expand Up @@ -163,6 +163,7 @@ pub use path_utilities::SearchPathDomainMask;
mod notification;
pub use notification::Notification;
pub use notification::NotificationCenter;
pub use notification::NotificationGuard;
pub use notification::NotificationName;

mod operation;
Expand Down
81 changes: 77 additions & 4 deletions cidre/src/ns/notification.rs
Original file line number Diff line number Diff line change
Expand Up @@ -60,7 +60,11 @@ impl Notification {
}
}

define_obj_type!(pub NotificationCenter(ns::Id), NS_NOTIFICATION_CENTER);
define_obj_type!(
#[doc(alias = "NSNotificationCenter")]
pub NotificationCenter(ns::Id), NS_NOTIFICATION_CENTER
);

impl NotificationCenter {
#[objc::cls_msg_send(defaultCenter)]
pub fn default() -> &'static mut Self;
Expand All @@ -84,7 +88,7 @@ impl NotificationCenter {

#[cfg(feature = "blocks")]
#[objc::msg_send(addObserverForName:object:queue:usingBlock:)]
pub fn add_observer_for_ar<'bar, B>(
pub fn add_observer_ar<'bar, B>(
&mut self,
name: &ns::NotificationName,
object: Option<&ns::Id>,
Expand All @@ -96,7 +100,7 @@ impl NotificationCenter {

#[cfg(feature = "blocks")]
#[objc::rar_retain]
pub fn add_observer_for<'bar, B>(
pub fn add_observer<'bar, B>(
&mut self,
name: &ns::NotificationName,
object: Option<&ns::Id>,
Expand All @@ -105,6 +109,51 @@ impl NotificationCenter {
) -> arc::R<ns::Id>
where
B: FnMut(&'bar ns::Notification);

#[cfg(feature = "blocks")]
pub fn add_observer_mut<'bar, B>(
&mut self,
name: &ns::NotificationName,
object: Option<&ns::Id>,
queue: Option<&ns::OpQueue>,
block: B,
) -> arc::R<ns::Id>
where
B: FnMut(&'bar ns::Notification) + 'static,
{
let mut block = blocks::mut1(block);
self.add_observer(name, object, queue, block.escape())
}

#[cfg(feature = "blocks")]
pub fn add_observer_guard<'bar, B>(
&mut self,
name: &ns::NotificationName,
object: Option<&ns::Id>,
queue: Option<&ns::OpQueue>,
block: B,
) -> NotificationGuard
where
B: FnMut(&'bar ns::Notification) + 'static,
{
let mut block = blocks::mut1(block);
let token = self.add_observer(name, object, queue, block.escape());
NotificationGuard {
token,
center: self.retained(),
}
}
}

pub struct NotificationGuard {
token: arc::R<ns::Id>,
center: arc::R<ns::NotificationCenter>,
}

impl Drop for NotificationGuard {
fn drop(&mut self) {
self.center.remove_observer(&self.token);
}
}

#[link(name = "ns", kind = "static")]
Expand Down Expand Up @@ -132,7 +181,7 @@ mod tests {
*guard += 1;
});
let name = ns::NotificationName::with_str("test");
let token = nc.add_observer_for(&name, None, None, block.escape());
let token = nc.add_observer(&name, None, None, block.escape());
nc.post_with_name_object(&name, None);
nc.post_with_name_object(&name, None);

Expand All @@ -148,4 +197,28 @@ mod tests {
assert_eq!(2, *guard);
}
}

#[test]
fn guard() {
let nc = ns::NotificationCenter::default();
let counter = Arc::new(Mutex::new(0));
let block_counter = counter.clone();
let name = ns::NotificationName::with_str("test");
{
let _g = nc.add_observer_guard(&name, None, None, move |_note| {
let mut guard = block_counter.lock().unwrap();
*guard += 1;
});
nc.post_with_name_object(&name, None);
{
let guard = counter.lock().unwrap();
assert_eq!(1, *guard);
}
}
nc.post_with_name_object(&name, None);
{
let guard = counter.lock().unwrap();
assert_eq!(1, *guard);
}
}
}
3 changes: 1 addition & 2 deletions cidre/src/ns/regular_expression.rs
Original file line number Diff line number Diff line change
Expand Up @@ -128,8 +128,7 @@ extern "C" {

#[cfg(test)]
mod tests {
use crate::objc::ar_pool;
pub use crate::{cf, ns};
use crate::{ns, objc::ar_pool};

#[test]
fn basics() {
Expand Down

0 comments on commit d53a7ee

Please sign in to comment.