自定义非等高cell
2016-04-18 本文已影响160人
letaibai
非等高cell创建方式1:xib
1.创建自定义类,继承自UITableViewCell,勾选同时创建xib,创建完毕后设置cell的重用标识.
2.新建一个模型类,继承自NSObject给cell提供数据源
3.将storyboard中的控制器及viewController文件删掉,在storyboard中拖入一个UITableViewController,自定义一个WeiboStatusController类,将storyboard中控制器的class改为WeiboStatusController.
此时工程中包含了如下文件:
4.修改模型文件,将plist文件包含的属性定义为成员属性,写入,并提供构造方法,方便外界创建模型数据.
模型.h文件
#import <UIKit/UIKit.h>
@interface DLStatus : NSObject
//定义plist文件中的keys
@property(nonatomic,strong) NSString *icon;
@property(nonatomic,strong) NSString *name;
@property(nonatomic,strong) NSString *text;
@property(nonatomic,strong) NSString *picture;
@property(nonatomic,assign,getter=isVip) BOOL vip;
//定义cell的行高
@property(nonatomic,assign) CGFloat cellHeight;
//构造方法,方便外界创建模型数据
+ (instancetype)statusWithDict:(NSDictionary *)dict;
@end
模型.m文件如下:
#import "DLStatus.h"
@implementation DLStatus
+ (instancetype)statusWithDict:(NSDictionary *)dict{
DLStatus *status = [[self alloc] init];
//KVC(Key Value Coding)
[status setValuesForKeysWithDictionary:dict];
return status;
}
@end
5.把xib的控件与自定义cell连线,拿到对应的属性.在.h中定义一个模型属性,为cell传递模型数据.同时提供构造方法,方便外界创建该类型的cell.
自定义类的.h文件内容如下:
#import <UIKit/UIKit.h>
@class DLStatus;
@interface DLStatusCell : UITableViewCell
@property(nonatomic,strong) DLStatus *status;
+ (instancetype)cellWithTableView:(UITableView *)tableView;
@end
自定义类的.m文件内容如下:
#import "DLStatusCell.h"
#import "DLStatus.h"
@interface DLStatusCell ()
@property (weak, nonatomic) IBOutlet UIImageView *name;
@property (weak, nonatomic) IBOutlet UILabel *nameLabel;
@property (weak, nonatomic) IBOutlet UIImageView *vip;
@property (weak, nonatomic) IBOutlet UILabel *contentLabel;
@property (weak, nonatomic) IBOutlet UIImageView *picture;
@end
@implementation DLStatusCell
//构造方法的实现
+ (instancetype)cellWithTableView:(UITableView *)tableView{
static NSString *ID = @"status";//将cell的创建封装到类内部
DLStatusCell *cell = [tableView dequeueReusableCellWithIdentifier:ID];
if (cell == nil) {//缓存池找不到cell时,从xib创建
cell = [[[NSBundle mainBundle] loadNibNamed:NSStringFromClass([DLStatusCell class]) owner:nil options:nil] lastObject];
}
return cell;
}
- (void)awakeFromNib{
//设置contentLabel的最大宽度,防止layoutIfNeeded方法计算的尺寸偏差.
self.contentLabel.preferredMaxLayoutWidth = [UIScreen mainScreen].bounds.size.width - 20;
}
//重写模型属性的set方法
- (void)setStatus:(DLStatus *)status{
_status = status;
//设置模型属性内部子控件的值
self.nameLabel.text = status.name;
//判断vip的状态
if (_status.isVip) {
self.vip.hidden = NO;
self.nameLabel.textColor = [UIColor orangeColor];
}else{
self.vip.hidden = YES;
self.nameLabel.textColor = [UIColor blackColor];
}
self.name.image = [UIImage imageNamed:status.icon];
self.contentLabel.text = status.text;
//判断picture的状态
if (_status.picture) {
self.picture.hidden = NO;
self.picture.image = [UIImage imageNamed:status.picture];
}else{
self.picture.hidden = YES;
}
//强制布局控件
[self layoutIfNeeded];
//返回cell的高度
if (self.picture.hidden) {
status.cellHeight = CGRectGetMaxY(self.contentLabel.frame) + 10;
}else{
status.cellHeight = CGRectGetMaxY(self.picture.frame) + 10;
}
}
@end
6.在WeiboStatusController文件中定义一个数组接收模型数据,同时实现cell的数据源方法.
WeiboStatusController.m文件内容如下:
#import "WeiboStatusController.h"
#import "DLStatus.h"
#import "DLStatusCell.h"
@interface WeiboStatusController ()
//定义属性,接收模型
@property (nonatomic,strong) NSArray *status;
@end
@implementation WeiboStatusController
//懒加载模型
- (NSArray *)status{
if (_status == nil) {
NSString *path = [[NSBundle mainBundle] pathForResource:@"statuses.plist" ofType:nil];
NSArray *dictArr = [NSArray arrayWithContentsOfFile:path];
NSMutableArray *statusArr = [NSMutableArray array];
for (NSDictionary *dict in dictArr) {
DLStatus *status = [DLStatus statusWithDict:dict];
[statusArr addObject:status];
}
_status = statusArr;
}
return _status;
}
- (void)viewDidLoad {
[super viewDidLoad];
}
#pragma mark - Table view data source
//返回cell的个数
- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section {
return self.status.count;
}
//返回cell的内容
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {
//通过自定义cell创建cell
DLStatusCell *cell = [DLStatusCell cellWithTableView:tableView];
//取出对应的模型数据
cell.status = self.status[indexPath.row];
return cell;
}
//设置cell的估计高度,调换heightForRowAtIndexPath:与cellForRowAtIndexPath:的调用顺序,同时优化系统
- (CGFloat)tableView:(UITableView *)tableView estimatedHeightForRowAtIndexPath:(NSIndexPath *)indexPath{
return 200;
}
//返回cell的真是高度
- (CGFloat)tableView:(UITableView *)tableView heightForRowAtIndexPath:(NSIndexPath *)indexPath{
//取出模型中对应的高度数据
DLStatus *status = self.status[indexPath.row];
return status.cellHeight;
}
@end
非等高cell创建方式2:storyboard
此方法创建cell只需要将xib文件中的子控件换到storyboard中,拖线,修改重用标识,将cell的构造方法改为如下内容即可:
+ (instancetype)cellWithTableView:(UITableView *)tableView{
return [tableView dequeueReusableCellWithIdentifier:ID];
}