iO从TabBarController上的ViewController中删除Observers

时间:2014-06-23 16:00:13

标签: ios objective-c xcode

我有一个UITabBarController带有一些标签,所有标签中都有:

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

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

在另一个班级,我发布名为kNotificationName的通知:

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

我已经设置了所有这些方法的一些日志,并且它们被调用的顺序是正确的但是......如果我从第一个选项卡切换到第二个选项卡(并且通知已发布),则第一个和第二个选项卡接收通知(但第一个标签的viewDidDisappear被调用!)。

如果从第二个标签转到第三个标签,则第一个,第二个和第三个标签会收到通知。

我试过用:

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

但行为是一样的。所有观察员都会收到通知。

EDIT1: 作为对其他主题的建议,我已将所有内容移至viewWillAppear:viewWillDisappear:,但这没有任何效果。

我收到通知后试图删除观察者,如下所示:

-(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];
}];
}

但是,也使用这个(坏)方法,通知也会收到第一个选项卡(我只在第一个选项卡上添加了此代码,以检查是否在按下第二个选项卡后,第一个选项卡再次收到通知)。

EDIT2 - 已解决 - (但有什么区别?)

我没有使用*addObserverForName:object:queue:usingBlock*:而是使用了*addObserver:selector:name:object:*,而且这种方式都有效。

Apple文档说明了使用usingBlock的方法:

  

该块由通知中心复制并保存(副本)   直至观察员注册被移除。

当然,我打电话给removeObserver ....

1 个答案:

答案 0 :(得分:0)

在addObserver方法的块内 -

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

您可能已经在文档中检查了这一点 -

Be sure to invoke removeObserver: or removeObserver:name:object: before notificationObserver or any object specified in addObserver:selector:name:object: is deallocated.