1

I have a UITabBarController with some tab and in all of them i have:

-(void)viewDidappear:(BOOL)animated{
   ......
   [[NSNotificationCenter defaultCenter] addObserverForName:kNotificationName object:nil        queue: nil, usingBlock{...}
}

and

-(void)viewDidDisappear:(BOOL)animated{
   ......
   [[NSNotificationCenter defaultCenter] removeObserver:self];
}

In another class i post the notification with name kNotificationName:

[[NSNotificationCenter defaultCenter] postNotification:kNotificationName object:nil];

I've set some log on all of this methods, and the order they are called is correct but...if i switch from First to Second tab (and the notification is posted), the first and the second tab receive the notification (but the viewDidDisappear of the first tab is called!).

If from second tab i go to third tab, the first, second, and third tab receive the notification.

I've tried to use:

[[NSNotificationCenter defaultCenter] removeObserver:self name:postNotification:kNotificationName  object:nil];

but the behaviour is the same. All observer are notified.

EDIT1: As suggest to the other topic i've moved all in viewWillAppear: and viewWillDisappear:, but this haven't have any effect.

I've tried to remove the observer after have received the notification, like this:

-(void)viewWillAppear:(BOOL)animated
{
    [super viewWillAppear:animated];

    [[NSNotificationCenter defaultCenter]     addObserverForName:kDLSyncEngineSyncCompletedNotificationName object:nil queue:nil   usingBlock:^(NSNotification *note) {
    ....
    [[NSNotificationCenter defaultCenter] removeObserver:self name:kDLSyncEngineSyncCompletedNotificationName object:nil];
}];
}

But, using this (bad) approach too, the notification is received to the first tab too (i've added this code only on the first tab, to check if after press the second tab, the first tab is receiving again the notification).

EDIT2 - SOLVED - (but what is the difference?)

Instead of using *addObserverForName:object:queue:usingBlock*: I've used *addObserver:selector:name:object:* and in this way all works.

Apple documentation say this for the method with usingBlock:

The block is copied by the notification center and (the copy) held until the observer registration is removed.

Sure, I've called removeObserver....

Haroldo Gondim
  • 7,725
  • 9
  • 43
  • 62
Mistre83
  • 2,677
  • 6
  • 40
  • 77
  • possible duplicate of [NSNotification is being called multiple times from UITabBarController](http://stackoverflow.com/questions/21029468/nsnotification-is-being-called-multiple-times-from-uitabbarcontroller) – rishi Jun 23 '14 at 16:41
  • I've moved all in viewWillAppear: and viewWillDisappear. The chain call is correct (remove observer from the first tab is invoked BEFORE the viewWillAppear: of the second tab), but after notify, the first tab respond to the notify too. – Mistre83 Jun 23 '14 at 17:14
  • not clear what you are asking – rishi Jun 24 '14 at 04:28
  • 1
    If i use addObserver:selector:name:object: and removeObserver it works. If i use addObserverForName:object:queue:usingBlock: and removeObserver dont works. The observer that i have removed continue to handle notification. – Mistre83 Jun 24 '14 at 06:33
  • I usually assign an `id` object to the observer. Then I remove it and I nil out it. It works – Luca D'Alberti Jul 22 '15 at 13:20

1 Answers1

0

Inside the block in the addObserver method -

usingBlock:^(NSNotification *notification){
                       /*
                       do something
                       */
                       [[NSNotificationCenter defaultCenter] removeObserver:self];
                }];

As you might have already checked this in documentation -

Be sure to invoke removeObserver: or removeObserver:name:object: before notificationObserver or any object specified in addObserver:selector:name:object: is deallocated.
rishi
  • 11,779
  • 4
  • 40
  • 59