自定义cell的高度

学习李明杰的课,原封代码

  • 1.获取数据
- (NSArray *)dataArray {
    if (_dataArray == nil) {
        _dataArray = [NSArray array];
        NSString *path = [[NSBundle mainBundle] pathForResource:@"statuses.plist" ofType:nil];
        NSArray *array = [NSArray arrayWithContentsOfFile:path];
        NSMutableArray *statusArray = [NSMutableArray array];
        for (NSDictionary *dict in array) {
            StatusModel *model = [StatusModel statusWithDict:dict];
            
            StatusFrame *statusFrame = [[StatusFrame alloc] init];
            statusFrame.statusModel = model;
            
            [statusArray addObject:statusFrame];
        }
        _dataArray = statusArray;
    }
    return _dataArray;
}
  • 这两个数据模型如下

StatusModel.h

@property (nonatomic , copy) NSString *icon;
@property (nonatomic , copy) NSString *name;
@property (nonatomic , copy) NSString *text;
@property (nonatomic , copy) NSString *picture;
@property (nonatomic , assign , getter=isVip) BOOL vip;
+ (instancetype)statusWithDict:(NSDictionary *)dict;

.m实现

- (instancetype)initWithDict:(NSDictionary *)dict {
    if (self = [super init]) {
        [self setValuesForKeysWithDictionary:dict];
    }
    return self;
}

+ (instancetype)statusWithDict:(NSDictionary *)dict {
    return [[self alloc] initWithDict:dict];
}

StatusFrame

.h

/** 头像 */
@property (nonatomic , assign , readonly) CGRect iconF;
/** 昵称 */
@property (nonatomic , assign , readonly) CGRect nameF;
/** vip */
@property (nonatomic , assign , readonly) CGRect vipF;
/** 正文 */
@property (nonatomic , assign , readonly) CGRect textF;
/** 配图 */
@property (nonatomic , assign , readonly) CGRect pictureF;
/** cell的高度 */
@property (nonatomic , assign , readonly) CGFloat cellHeight;
@property (nonatomic , strong) StatusModel *statusModel;

.m实现

//  存放cell内部所有子控件的frame

#define NameFont [UIFont systemFontOfSize:14]
#define TextFont [UIFont systemFontOfSize:15]
#define KWidth [UIScreen mainScreen].bounds.size.width

#import "StatusFrame.h"
#import "StatusModel.h"

@implementation StatusFrame

- (void)setStatusModel:(StatusModel *)statusModel {
    _statusModel = statusModel;
    
    // 控件之间的间距
    CGFloat padding = 10;
    // 头像
    CGFloat iconX = padding;
    CGFloat iconY = padding;
    CGFloat iconW = 30;
    CGFloat iconH = 30;
    _iconF = CGRectMake(iconX, iconY, iconW, iconH);
    // 昵称
    // 文字的字体
    CGSize maxNameSize = CGSizeMake(MAXFLOAT, MAXFLOAT);
    CGSize nameSize = [self sizeWithText:self.statusModel.name font:NameFont maxSize:maxNameSize];
    CGFloat nameX = CGRectGetMaxX(_iconF) + padding;
    CGFloat nameY = iconY + (iconH - nameSize.height) / 2;
    _nameF = CGRectMake(nameX, nameY, nameSize.width, nameSize.height);
    // vip
    CGFloat vipX = CGRectGetMaxX(_nameF) + padding;
    CGFloat vipY = nameY;
    CGFloat vipW = 14;
    CGFloat vipH = 14;
    _vipF = CGRectMake(vipX, vipY, vipW, vipH);
    // 正文
    CGFloat textX = iconX;
    CGFloat textY = CGRectGetMaxY(_vipF) + padding;
    CGSize textSize = [self sizeWithText:self.statusModel.text font:TextFont maxSize:CGSizeMake(KWidth - 2 * padding, MAXFLOAT)];
    _textF = CGRectMake(textX, textY, textSize.width, textSize.height);
    // 配图
    if (self.statusModel.picture) {
        CGFloat pictureX = iconX;
        CGFloat pictureY = CGRectGetMaxY(_textF) + padding;
        CGFloat pictureW = 100;
        CGFloat pictureH = 100;
        _pictureF = CGRectMake(pictureX, pictureY, pictureW, pictureH);
        _cellHeight = CGRectGetMaxY(_pictureF) + padding;
    } else {
        _cellHeight = CGRectGetMaxY(_textF) + padding;
    }
}

- (CGSize)sizeWithText:(NSString *)text font:(UIFont *)font maxSize:(CGSize)maxSize {
    NSDictionary *attrs = @{NSFontAttributeName:font};
    return [text boundingRectWithSize:maxSize options:NSStringDrawingUsesLineFragmentOrigin attributes:attrs context:nil].size;
}

@end

两个model类实现之后,实现tableView的代理方法

- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section {
    return self.dataArray.count;
}
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {
    TableViewCell *cell = [TableViewCell cellWithTableView:tableView];
    cell.statusFrame = self.dataArray[indexPath.row];
    return cell;
}
- (CGFloat)tableView:(UITableView *)tableView heightForRowAtIndexPath:(NSIndexPath *)indexPath {
    StatusFrame *statusFrame = self.dataArray[indexPath.row];
    return statusFrame.cellHeight;
}

自定义cell

+ (instancetype)cellWithTableView:(UITableView *)tableView {
    static NSString *ID = @"status";
    TableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:ID];
    if (!cell) {
        cell = [[TableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:ID];
    }
    return cell;
}

- (instancetype)initWithStyle:(UITableViewCellStyle)style reuseIdentifier:(NSString *)reuseIdentifier {
    self = [super initWithStyle:style reuseIdentifier:reuseIdentifier];
    if (self) {
        // 头像
        UIImageView *iconView = [[UIImageView alloc] init];
        [self.contentView addSubview:iconView];
        self.iconView = iconView;
        
        // 昵称
        UILabel *nameView = [UILabel new];
        nameView.font = NameFont;
        [self.contentView addSubview:nameView];
        self.nameView = nameView;
        
        // vip
        UIImageView *vipView = [UIImageView new];
        vipView.image = [UIImage imageNamed:@"vip"];
        [self.contentView addSubview:vipView];
        self.vipView = vipView;
        
        // 正文
        UILabel *textView = [UILabel new];
        textView.font = TextFont;
        textView.numberOfLines = 0;
        [self.contentView addSubview:textView];
        self.textView = textView;
        
        // 配图
        UIImageView *pictureView = [UIImageView new];
        [self.contentView addSubview:pictureView];
        self.pictureView = pictureView;
    }
    return self;
}

设置frame

-(void)layoutSubviews {
    [super layoutSubviews];
    self.iconView.frame = self.statusFrame.iconF;
    // 昵称
    self.nameView.frame = self.statusFrame.nameF;
    // vip
    self.vipView.frame = self.statusFrame.vipF;
    // 正文
    self.textView.frame = self.statusFrame.textF;
    // 配图
    if (self.statusFrame.statusModel.picture) {
        self.pictureView.frame = self.statusFrame.pictureF;
    }
}

设置数据

- (void)setStatusFrame:(StatusFrame *)statusFrame {
    _statusFrame = statusFrame;
    
    // 头像
    self.iconView.image = [UIImage imageNamed:self.statusFrame.statusModel.icon];
    // 昵称
    self.nameView.text = self.statusFrame.statusModel.name;
    // vip
    if (self.statusFrame.statusModel.vip) {
        self.vipView.hidden = NO;
        self.nameView.textColor = [UIColor redColor];
    } else {
        self.nameView.textColor = [UIColor blackColor];
        self.vipView.hidden = YES;
    }
    // 正文
    self.textView.text = self.statusFrame.statusModel.text;
    // 配图
    if (self.statusFrame.statusModel.picture) {
        self.pictureView.hidden = NO;
        self.pictureView.image = [UIImage imageNamed:self.statusFrame.statusModel.picture];
    } else {
        self.pictureView.hidden = YES;
    }
}

其他的宏

#define NameFont [UIFont systemFontOfSize:14]
#define TextFont [UIFont systemFontOfSize:15]
#define KWidth [UIScreen mainScreen].bounds.size.width

最后实现的界面如下

微博学习demo

推荐阅读更多精彩内容