标签云

微信群

扫码加入我们

WeChat QR Code

How do you add an observer in Swift to the default notification center?I'm trying to port this line of code that sends a notification when the battery level changes.[[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(batteryLevelChanged:) name:UIDeviceBatteryLevelDidChangeNotification object:nil];


What are you asking specifically? How the selector works?

2019年09月19日59分21秒

I didn't realize the "Selector" type is just a string in Swift.No mention of it in the docs.

2019年09月18日59分21秒

stackoverflow.com/questions/36910965/…

2019年09月18日59分21秒

Thanks!I didn't know how to pass the selector name in Swift.

2019年09月18日59分21秒

BerryBlue, did the above solution work for you? I believe that you need to change "batteryLevelChanged" to "batteryLevelChanged:" if your function accepts the NSNotification as a parameter.

2019年09月18日59分21秒

Olshansk Yes, you're correct.You do need that.Thanks!

2019年09月18日59分21秒

why is UIDeviceBatteryLevelDidChangeNotification not in quotes? It's a string type.

2019年09月18日59分21秒

Be sure to annotate either the class or the target method with objc.

2019年09月19日59分21秒

Be sure to annotate either the class or the target method with objc.

2019年09月19日59分21秒

goofansu Are you sure? I reckon that you have to add it when it's a pure Swift class.

2019年09月18日59分21秒

methodOFReceivedNotication must be either annotated with dynamic or be a member of a subclass of NSObject.

2019年09月18日59分21秒

If not, I get a runtime warning object 0x7fd68852d710 of class 'TestNotifications.MyObject' does not implement methodSignatureForSelector: -- trouble ahead, Unrecognized selector -[TestNotifications.MyObject methodOFReceivedNotication:]

2019年09月18日59分21秒

TaylorAllred, Thank you very much for review my answer. I am really appreciate your suggestion. I have changed it. Please review it.

2019年09月18日59分21秒

This is great! For completeness I would just like to see unregistering example too. It is quite different then the addObserver(_:selector:name:object:) way of unregistering. You have to keep the object returned by addObserverForName(_:object:queue:usingBlock:) and pass it to removeObserver:

2019年09月19日59分21秒

This needs updating to include de-registration of the objected returned by addObserverForName(_:object:queue:usingBlock:).

2019年09月19日59分21秒

This is a much better answer than connor's or Renish's (both above at time of this comment) because it gets around having to use the Obj-C #selector methods. The result is much more Swift-y and more correct, IMO. Thanks!

2019年09月19日59分21秒

Remember, if you use this in, say, a UIViewController and refer to self in that closure, you need to use [weak self] or you'll have a reference cycle and the memory leak.

2019年09月18日59分21秒

"from iOS 9 and OS X 10.11. It is no longer necessary for an NSNotificationCenter observer to un-register itself when being deallocated."This is true only for the Selector based observers. Block based observers still need to be removed.

2019年09月18日59分21秒

great thanks man !

2019年09月18日59分21秒

Glad to hear it helped you :)

2019年09月18日59分21秒

You don't need to annotate with objc if your observer class inherits from NSObject.

2019年09月18日59分21秒

And you shouldn't need to explicitly cast a String to Selector either. :)

2019年09月18日59分21秒

alfvata: My observer class does not inherit from NSObject. It inherits from AnyObject, Swift-style. Explicitly casting the string to Selector is allowing me to avoid doing any of the other Objective-C-related workarounds.

2019年09月19日59分21秒

I'm not sure I understand how that works. I removed the objc annotation from the method in my non-NSObject observer class, added the as Selector casting to the String selector name, and when the notification fires the app crashes. My Swift version is exactly the same as yours.

1970年01月01日00分03秒

alfavata, I don't know what to tell you. I'm now on Xcode Beta 4, and it's still working. My project is totally Swift; there are no Objective-C components. Maybe that makes a difference. Maybe there's something different in the project settings. There are any number of possibilities! I'll say: as long as the objc annotation works for you, and this way doesn't, then keep annotating!

2019年09月18日59分21秒

Downvotes should be explained :x

2019年09月18日59分21秒

I believe you don't need this since iOS 9. It's done automatically.

2019年09月18日59分21秒

Just to clarify for anyone reading this answer: "the Selector is of type objc func..." means the function associated with #selector must be annotated with objc. For example: objc func keyboardShow() { ... } That threw me for a minute in Swift 4!

2019年09月19日59分21秒