天天看点

类别添加属性,即runtime运行时添加属性(动态属性)

在自定义扩展类时,可以通过运行时添加属性。

关键点在于,首先必须导入运行时头文件;

#import <objc/runtime.h>
           

其次,设置属性;

objc_setAssociatedObject(self, &keyLineBottom, lineBottom, OBJC_ASSOCIATION_RETAIN);
           

还有是获得设置的属性;

UIImageView *lineBottom = objc_getAssociatedObject(self, &keyLineBottom);
           

还有一点需要设置,即设置关联key值

static NSString *const keyLineBottom = @"lineBottomView"; 
           

注意:扩展类中添加的属性必须是对象类型,如要添加NSInteger类型,则需转换成NSNumber类型。

示例如下(UITableViewCell添加底端分割线属性):

.h文件

#import <UIKit/UIKit.h>

@interface UITableViewCell (CellLine)

///设置分割线
- (void)showLineView:(CGFloat)offX color:(UIColor *)lineColor type:(CellLineShowType)type;

///底端分割线
@property (nonatomic, strong) UIImageView *lineViewButtom;

@end
           

.m文件

#import "UITableViewCell+CellLine.h"
#import <objc/runtime.h>

static NSString *const keyLineTop = @"lineTopView";
static NSString *const keyLineBottom = @"lineBottomView";

static CGFloat const heightLine = 0.5; // 默认分割线高度

@implementation UITableViewCell (CellLine)

///设置分割线
- (void)showLineView:(CGFloat)offX color:(UIColor *)lineColor type:(CellLineShowType)type
{
    // 底端分割线
    UIImageView *lineBottom = objc_getAssociatedObject(self, &keyLineBottom);
    if (!lineBottom)
    {
        lineBottom = [[UIImageView alloc] initWithFrame:CGRectMake(0.0, (CGRectGetHeight(self.bounds) - heightLine), CGRectGetWidth(self.bounds), heightLine)];
        [self.contentView addSubview:lineBottom];
        
        objc_setAssociatedObject(self, &keyLineBottom, lineBottom, OBJC_ASSOCIATION_RETAIN);
    }

    CGRect rectButtom = lineBottom.frame;
    rectButtom.origin.x = offX;
    lineBottom.frame = rectButtom;
    
    lineBottom.backgroundColor = lineColor;
    lineBottom.image = [UIImage imageWithColor:lineColor andSize:CGSizeMake(1.0, 1.0)];
    
    // 顶端分割线
    UIImageView *lineTop = objc_getAssociatedObject(self, &keyLineTop);
    if (!lineTop)
    {
        lineTop = [[UIImageView alloc] initWithFrame:CGRectMake(0.0, 0.0, CGRectGetWidth(self.bounds), heightLine)];
        [self.contentView addSubview:lineTop];
        
        objc_setAssociatedObject(self, &keyLineTop, lineTop, OBJC_ASSOCIATION_RETAIN);
    }
    
    CGRect rectTop = lineTop.frame;
    rectTop.origin.x = offX;
    lineTop.frame = rectTop;
    
    lineTop.backgroundColor = lineColor;
    lineTop.image = [UIImage imageWithColor:lineColor andSize:CGSizeMake(1.0, 1.0)];
    
    switch (type)
    {
        case CellLineShowNone:
        {
            lineBottom.hidden = YES;
            lineTop.hidden = YES;
        }
            break;
        case CellLineShowAll:
        {
            lineBottom.hidden = NO;
            lineTop.hidden = NO;
        }
            break;
        case CellLineShowButtom:
        {
            lineBottom.hidden = NO;
            lineTop.hidden = YES;
        }
            break;
        case CellLineShowTop:
        {
            lineBottom.hidden = YES;
            lineTop.hidden = NO;
        }
            break;
            
        default:
            break;
    }
}

#pragma mark - setter/getter

- (void)setLineViewButtom:(UIImageView *)lineViewButtom
{
    objc_setAssociatedObject(self, &keyLineBottom, lineViewButtom, OBJC_ASSOCIATION_RETAIN);
}

- (UIImageView *)lineViewButtom
{
    UIImageView *line = objc_getAssociatedObject(self, &keyLineBottom);
    return line;
}

- (void)setLineViewTop:(UIImageView *)lineViewTop
{
    objc_setAssociatedObject(self, &keyLineTop, lineViewTop, OBJC_ASSOCIATION_RETAIN);
}

- (UIImageView *)lineViewTop
{
    UIImageView *line = objc_getAssociatedObject(self, &keyLineTop);
    return line;
}

@end
           

继续阅读