Search code examples
ioscocoakey-value-observing

removeObserver: forKeyPath is not working


I have a UIView subclass that registers itself and an observer with an object in an NSDictionary.

When this view is removed (when its containing view is removed) I call the removeObserver:forKey method in the view's dealloc method.

The app will later crash because my view object is not actually being removed from the observers. I have confirmed this through the dictionary's observationInfo.

I can see that my dealloc is indeed running when I would expect. This same method is working fine with other subclassed things, like UIButton and UILabel.

If it helps: The only difference between the other subclassed things and this view is the other things are instantiated from a NIB, where this view is built in code...

Any idea what might be preventing this from removing properly?


Solution

  • You are likely calling addObserver:forKey:context: multiple times. You must exactly balance calls to addObserver:... and removeObserver:...

    Where are you calling addObserver:...? Are you aware of how nib-loaded objects are instantiated? You probably want to put the addObserver:... in awakeFromNib or initWithCoder:. I often use a setup method for objects that might or might not be created from a nib file. For instance:

    - (void)setup {
      // Do setup work here
    }
    
    - (id)initWithFrame:(CGRect)frame {
      self = [super init];
      if (self) {
        [self setup];
      }
      return self;
    }
    
    - (id)initWithCoder:(NSCoder *)coder {
      self = [super initWithCoder:coder];
      if (self) {
        [self setup];
      }
      return self;
    }