NSNotificationCenter,块和SEL类型的ivar:无法使其工作

时间:2011-08-12 11:28:31

标签: objective-c nsnotificationcenter objective-c-blocks

我正在尝试以下方法:

每当OAuth令牌发生变化时,我都想更新一些视图控制器。我想要更新的视图控制器都是从视图控制器继承的。每当设置新的访问令牌或清除访问令牌时,此视图控制器都将侦听通知。无论何时设置或清除访问令牌,我都希望将选择器设置为一旦显示视图控制器就应该执行的方法(即在-viewWillAppear:上)。

addObserverForName:object:queue:usingBlock:内的块似乎没有被调用。我甚至无法记录它。因此,选择器永远不会改变。根据我在ivar上使用__block属性的内容,我应该允许从一个块内更改ivar。

@interface SDViewController ()
- (void)reloadData;
- (void)clearData;
@end


@implementation SDViewController 
{
   __block SEL selectorOnViewWillAppear;
}

- (id)initWithDataSource:(id <SDViewControllerDataSource>)dataSource
{
   self = [super init];
   if (self) 
   {
      selectorOnViewWillAppear = @selector(reloadData);
   }
   return self;
}

- (void)viewDidLoad 
{
   NSLog(@"view did load");

   [super viewDidLoad];

   [[NSNotificationCenter defaultCenter] addObserverForName:kAccessTokenChangedNotification object:self queue:[NSOperationQueue currentQueue] usingBlock:^(NSNotification *note) {
      NSLog(@"selector: test1");
      selectorOnViewWillAppear = @selector(reloadData);
   }];
   [[NSNotificationCenter defaultCenter] addObserverForName:kAccessTokenClearedNotification object:self queue:[NSOperationQueue currentQueue] usingBlock:^(NSNotification *note) {
      NSLog(@"selector: test2");
      selectorOnViewWillAppear = @selector(clearData);
   }];
}

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

   if (selectorOnViewWillAppear) 
      [self performSelector:selectorOnViewWillAppear];
}

- (void)reloadData
{
   NSLog(@"reloadData");
   selectorOnViewWillAppear = nil;
}

- (void)clearData 
{
   NSLog(@"clearData");
   selectorOnViewWillAppear = nil;
}

@end

1 个答案:

答案 0 :(得分:0)

通过更改观察者代码来修复它:

[[NSNotificationCenter defaultCenter] 
   addObserverForName:kAccessTokenClearedNotification 
   object:self 
   queue:[NSOperationQueue currentQueue] 
   usingBlock:^(NSNotification *note) {
      NSLog(@"selector: test2");
      selectorOnViewWillAppear = @selector(clearData);
   }];

对此:

[[NSNotificationCenter defaultCenter] 
   addObserverForName:kAccessTokenClearedNotification 
   object:nil 
   queue:[NSOperationQueue currentQueue] 
   usingBlock:^(NSNotification *note) {
      NSLog(@"selector: test2");
      selectorOnViewWillAppear = @selector(clearData);
   }];

与此问题相关的Apple文档is found here。中的对象 -addObserverForName:object:queue:usingBlock:方法应该是生成通知的对象。将对象设置为nil可以解决问题。