Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

KVO for manually implemented properties

According to Ensuring KVC Compliance,

For properties that are an attribute or a to-one relationship, this requires that your class:

  • Implement a method named -<key>, -is<Key>, or have an instance variable <key> or _<key>.

What is the best way to add observers to "FAKE" properties like the following?

@property (nonatomic, readonly) BOOL shortlisted; 

#pragma mark - Fake properties

- (BOOL)shortlisted
{
    return [self.provider isJobShortlisted:self];
}   
like image 263
Injectios Avatar asked Apr 06 '12 11:04

Injectios


1 Answers

Dependent Keys

If you simply have one key which is dependent on another key of the same object, you can override +keyPathsForValuesAffectingValueForKey:. (See also this article for a common pitfall.)

The KVO documentation has information about keys dependent on other objects, but unfortunately it looks like this only has built-in support on OS X (not iOS).

Manual Notifcations

If you're implementing a completely custom property, the section on Manual Change Notification in the KVO docs has all the information you need. The key points are (with quotes from the docs):

  • A class that implements manual notification must override the NSObject implementation of automaticallyNotifiesObserversForKey:. ... For properties that perform manual notification, the subclass implementation of automaticallyNotifiesObserversForKey: should return NO.

  • To implement manual observer notification, you invoke willChangeValueForKey: before changing the value, and didChangeValueForKey: after changing the value.

    (If you change multiple properties, you can nest these calls.)

  • In the case of an ordered to-many relationship, you must specify not only the key that changed, but also the type of change and the indexes of the objects involved.

    For this you use the methods willChange:valuesAtIndexes:forKey: and didChange:valuesAtIndexes:forKey:.

like image 83
jtbandes Avatar answered Nov 11 '22 07:11

jtbandes