How to send object in NSNotification? - iphone

I want to send object to selector in NSNotification.I mean, I have 3 buttons and on click of each button I am registering notification and when that event occurred I am calling one selector and in that selector I want to find out which button user has clicked because I have common action for all 3 buttons.
-(void)allThreeButtonAction:(sender)id
{
[[NSNotificationCenter defaultCenter] addObserver:self selector:#selector(performSomeOperationWhenEventOccur) name:#"EventCompletedNotification" object:nil];
}
//Some event occurred, so I am sending notification
[[NSNotificationCenter defaultCenter] postNotificationName:#"EventCompletedNotification" object:nil];
//Notified method
-(void)performSomeOperationWhenEventOccur
{
//Here I want to know which button is pressed.
}
I hope I am clear.

You may want to look at postNotificationName:object:userInfo: from NSNotificationCenter documentation
You simply send a UserInfo containing whatever you need to identify the button (easiest is the pointer to the button) that you retrieve in your selector.
Your selector signature should receive the notification:
- (void)performSomeOperationWhenEventOccur:(NSNotification*) notification:(NSNotification*) notification
{
// Use [notification userInfo] to determine which button was pressed...
}
Don't forget to modify the selector name when your register it:
[[NSNotificationCenter defaultCenter] addObserver:self selector:#selector(performSomeOperationWhenEventOccur:) name:#"EventCompletedNotification" object:nil];

You can't pass an object when adding a notification observer, so you'll have to store the button that was pressed somewhere:
-(void)allThreeButtonAction:(id)sender
{
[[NSNotificationCenter defaultCenter] addObserver:self selector:#selector(performSomeOperationWhenEventOccur) name:#"EventCompletedNotification" object:nil];
self.buttonPressed = sender;
}
Then you can just read it in your notification handler:
-(void)performSomeOperationWhenEventOccur
{
if ( self.buttonPressed = self.button1 )
...
}

Below Snippet will help you.
Button1
[[NSNotificationCenter defaultCenter] addObserver:self selector:#selector(performSomeOperationWhenEventOccur:) name:#"button1" object:button1];
Button2
[[NSNotificationCenter defaultCenter] addObserver:self selector:#selector(performSomeOperationWhenEventOccur:) name:#"button2" object:button2];
Change method to following
- (void) performSomeOperationWhenEventOccur:(NSNotification *) notification
{
if ([[notification name] isEqualToString:#"button1"])
{
NSButton *button1=[notification button1];
NSLog (#"Successfully received the test notification! from button1");
}
else
{
NSButton *button2=[notification button2];
NSLog (#"Successfully received the test notification! from button2");
}
}

Related

NSNotification not receiving in View Controller from appDelegate

hello i assign nsnotifiaction in app delegate.m's method and this method call eprox every 30sec, and i wants its notifcation in viewcontroller adn execute method,
here is my code of appdelegate .m
- (void)layoutAnimated:(BOOL)animated{
BOOL yy= self.bannerView.bannerLoaded;
if (yy==1){
self.iAdString=[NSMutableString stringWithString:#"1"];
[[NSNotificationCenter defaultCenter] postNotificationName:#"BannerViewActionWillBegin" object:self];
}
else{
self.iAdString=[NSMutableString stringWithString:#"0"];
[[NSNotificationCenter defaultCenter] postNotificationName:#"BannerViewActionDidFinish" object:self];
}
}
and in viewcontroller.m
//i defined in viewdidload method
- (void)viewDidLoad{
[super viewDidLoad];
[[NSNotificationCenter defaultCenter] addObserver:self selector:#selector(willBeginBannerViewActionNotification:) name:#"BannerViewActionWillBegin "object:nil];
[[NSNotificationCenter defaultCenter] addObserver:self selector:#selector(didFinishBannerViewActionNotification:) name:#"BannerViewActionDidFinish" object:nil];
}
its method are..
- (void)willBeginBannerViewActionNotification:(NSNotification *)notification{
[self.view addSubview:self.app.bannerView];
NSLog(#"come");
}
- (void)didFinishBannerViewActionNotification:(NSNotification *)notification {
NSLog(#"come");
[self.app.bannerView removeFromSuperview];
}
- (void)dealloc{
[[NSNotificationCenter defaultCenter] removeObserver:self];
}
I have not getting response of excessing method while method read in appdelegate file.
Please help me.
You have a typo error.
[[NSNotificationCenter defaultCenter] addObserver:self selector:#selector(willBeginBannerViewActionNotification:) name:#"BannerViewActionWillBegin "object:nil];
//Your error here-------------------------------------------------------------------------------------------------------------------------------------^
You have put a space there.
SideNote: For all notification names, you should/can create a separate file and put all your notification names as constants strings.
const NSString *kBannerViewActionWillBegin=#"BannerViewActionWillBegin";
this will be easier to change the value and no such typo will happen.
From your code what I get is except for the notification name's all other stuff is fine, did you check whether the notification gets fired. Try keeping break points at the notification firing line.

NSNotificationCenter not acting on the message

In one of my classes I post a notification:
[[NSNotificationCenter defaultCenter] postNotificationName:#"ALERTNOTI" object:self userInfo:nil];
In my app delegaate I listen:
[[NSNotificationCenter defaultCenter] addObserver:self selector:#selector(myMethod) name:#"ALERTNOTI" object:nil];
I use NSLog to track when I send and when the method myMethod gets called.
The method is not getting called despite me sending out the notification.
Is there something that I need to know about NSNotification? Is it tempermental?
do this changes
[[NSNotificationCenter defaultCenter] postNotificationName:#"ALERTNOTI" object:nil];
if you want to pass some object through the notification. then do this
ex: you want to pass an NSDictionary *dict
[[NSNotificationCenter defaultCenter] postNotificationName:#"ALERTNOTI" object:nil userInfo:dict];
the method you want to call via notification should be like this.
-(void)method:(NSNotification *) notif
{
// your code here.
//if you want to access your dict
NSDictionary *myDict=[notif userInfo];
}
Try this:
[[NSNotificationCenter defaultCenter] postNotificationName:#"ALERTNOTI" object:nil];

"unrecognized selector sent to instance" when keyboard appears

When I click a text field into my app screen and the keyboard is showing up xcode debugger shows this error:
[mainViewController keyboardWasShown]: unrecognized selector sent to instance 0x5867ac0
In the viewDidLoad method of the mainViewController I'm calling the registerForKeyboardNotifications method like that:
[self registerForKeyboardNotifications];
Here's its implementation (in mainViewController.m):
- (void)registerForKeyboardNotifications
{
[[NSNotificationCenter defaultCenter] addObserver:self selector:#selector(keyboardWasShown:) name:UIKeyboardDidShowNotification object:nil];
[[NSNotificationCenter defaultCenter] addObserver:self selector:#selector(keyboardWillBeHidden:) name:UIKeyboardWillHideNotification object:nil];
}
// Called when the UIKeyboardDidShowNotification is sent.
- (void)keyboardWasShown:(NSNotification*)aNotification
{
}
// Called when the UIKeyboardWillHideNotification is sent
- (void)keyboardWillBeHidden:(NSNotification*)aNotification
{
}
Any idea what could be wrong?
Make sure the notification selector has the colon at the end; this is important, keyboardWasShown and keyboardWasShown: are different selectors.

Can I watch an NSNotification from another class?

I'm trying to get my head around NSNotificationCenter. If I have something like this in my App Delegate:
[[NSNotificationCenter defaultCenter] addObserver:self
selector:#selector(something:)
name:#"something"
object:nil];
-----
-(void)something:(NSNotification *) notification
{
// do something
}
Can I somehow watch this in another view controller? In my case, I'd like to watch it in a view controller with a table, and then reload the table when a notification is received. Is this possible?
Yes you can do it like this:
In class A : post the notification
[[NSNotificationCenter defaultCenter] postNotficationName:#"DataUpdated "object:self];
In class B : register first for the notification, and write a method to handle it.
You give the corresponding selector to the method.
//view did load
[[NSNotificationCenter defaultCenter] addObserver:self selector:#selector(handleUpdatedData:) name:#"DataUpdated" object:nil];
-(void)handleUpdatedData:(NSNotification *)notification {
NSLog(#"recieved");
}
Yes you can that is the whole purpose of NSNotification, you just have to add the View Controller you want as an observer exactly the same way you did on your App Delegate, and it will receive the notification.
You can find more information here: Notification Programming
Of course it's possible, that's the whole point of notifications. Using addObserver:selector:name:object: is how you register to receive notifications (you should do this in your table view controller), and you can use postNotificationName:object:userInfo: to post a notification from any class.
Read Notofication Programming Topics for more info.
You can register to observe notifications in as many classes as you like. You simply need to "rinse and repeat". Include the code to register as an observer in your view controller (perhaps in viewWillAppear:) and then reload the tableView from your method:
- (void)viewWillAppear:(BOOL)animated {
[[NSNotificationCenter defaultCenter] addObserver:self selector:#selector(something:) name:#"something" object:nil];
}
-(void)something:(NSNotification *) notification
{
[self.tableView reloadData];
}
It's also a good idea to de-register the view controller once you no longer need the notifications:
- (void)viewWillDisappear:(BOOL)animated {
[[NSNotificationCenter defaultCenter] removeObserver:self];
}
You should just add that as an Observer and give a different selector method if you want that viewController to behave differently when that notification is posted.
[[NSNotificationCenter defaultCenter] addObserver:self
selector:#selector(somethingOtherThing:)
name:#"something"
object:nil];
-(void)somethingOtherThing:(NSNotification *) notification
{
// do something
}

Does NSNotification work everywhere?

I'm sending a notification using:
[[NSNotificationCenter defaultCenter] postNotificationName:#"historyLoaded" object:jsonReturn];
And receiving the notification using:
[[NSNotificationCenter defaultCenter] addObserver:self selector:#selector(manageHistory:) name:#"historyLoaded" object:nil];
Then the method in the selector is:
- (void) manageHistory: (NSNotification *) historyData{
NSLog(#"this bit of code was run");
}
For some reaason the notification doesn't get through. Can notifications be send and received from anywhere in the app?
The object parameter in postNotification should be filled with an object which is "sending" the notification, or nil if the sender is not necessarily specified.
If you want to pass some information along, you should use postNotificationName:object:userInfo and put the information in userInfo dictionary instead.
[[NSNotificationCenter defaultCenter] addObserver:self
selector:#selector(manageHistory) name:#"historyLoaded" object:nil];
[[NSNotificationCenter defaultCenter] postNotificationName:#"historyLoaded"
object:nil userInfo:jsonReturn];
- (void) manageHistory: (NSNotification *) historyData{
NSDictionary* _dict = historyData.userInfo;
NSLog(#"Your information embedded to dictiuonary obj %#",_dict);
}
NOTE : Make sure your historyData should be a dictionary object in postNotificationName