Categories
Syntax#
-
@interface ClassName (categoryName) // ClassName is the class to be extended
-
// Method and property declarations
-
@end
Remarks#
To avoid method name clashes, it is recommended to use prefixes (like xyz_ in the example). If methods with the same name exist, it is undefined which one will be used in the runtime.
Simple Category
Interface and implementation of a simple category on NSArray, named Filter, with a single method that filters numbers.
It is good practice to add a prefix (PF) to the method to ensure we don’t overwrite any future NSArray methods.
@interface NSArray (PFFilter)
- (NSArray *)pf_filterSmaller:(double)number;
@end
@implementation NSArray (PFFilter)
- (NSArray *)pf_filterSmaller:(double)number
{
NSMutableArray *result = [NSMutableArray array];
for (id val in self)
{
if ([val isKindOfClass:[NSNumber class] && [val doubleValue] >= number)
{
[result addObject:val];
}
}
return [result copy];
}
@endDeclaring a class method
Header file UIColor+XYZPalette.h:
@interface UIColor (XYZPalette)
+(UIColor *)xyz_indigoColor;
@endand implementation UIColor+XYZPalette.m:
@implementation UIColor (XYZPalette)
+(UIColor *)xyz_indigoColor
{
return [UIColor colorWithRed:75/255.0f green:0/255.0f blue:130/255.0f alpha:1.0f];
}
@endAdding a property with a category
Properties can be added with categories using associated objects, a feature of the Objective-C runtime.
Note that the property declaration of retain, nonatomic matches the last argument to objc_setAssociatedObject. See Attach object to another existing object for explanations.
#import <objc/runtime.h>
@interface UIViewController (ScreenName)
@property (retain, nonatomic) NSString *screenName;
@end
@implementation UIViewController (ScreenName)
@dynamic screenName;
- (NSString *)screenName {
return objc_getAssociatedObject(self, @selector(screenName));
}
- (void)setScreenName:(NSString *)screenName {
objc_setAssociatedObject(self, @selector(screenName), screenName, OBJC_ASSOCIATION_RETAIN_NONATOMIC);
}
@endConforming to protocol
You can add protocols to standard classes to extends their functionality:
@protocol EncodableToString <NSObject>
- (NSString *)toString;
@end
@interface NSDictionary (XYZExtended) <EncodableToString>
@end
@implementation NSDictionary (XYZExtended)
- (NSString *)toString {
return self.description;
}
@endwhere XYZ your project’s prefix
Create a Category on XCode
Categories provide the ability to add some extra functionality to an object without subclassing or changing the actual object.
For example we want to set some custom fonts.
Let’s create a category that add functionality to UIFont class. Open your XCode project, click on File -> New -> File and choose Objective-C file, click Next enter your category name say “CustomFont” choose file type as Category and Class as UIFont then Click “Next” followed by “Create.”
Declare the Category Method :-
Click “UIFont+CustomFonts.h” to view the new category’s header file. Add the following code to the interface to declare the method.
@interface UIFont (CustomFonts)
+(UIFont *)productSansRegularFontWithSize:(CGFloat)size;
@endNow Implement the Category Method:-
Click “UIFont+CustomFonts.m” to view the category’s implementation file. Add the following code to create a method that will set ProductSansRegular Font.
+(UIFont *)productSansRegularFontWithSize:(CGFloat)size{
return [UIFont fontWithName:@"ProductSans-Regular" size:size];
}Import your category
#import "UIFont+CustomFonts.h"Now set the Label font
[self.label setFont:[UIFont productSansRegularFontWithSize:16.0]];
