- 自定义等高的 cell
一、storyboard 自定义 cell
1.创建一个继承自 UITableViewCell 的子类,比如 YJWGoodsCell
2.在 storyboard 中:
-
设置 cell 的重用标识
-
设置 cell 的 class 为 YJWGoodsCell
往 cell 里面增加需要用到的子控件
3.在控制器中:
- 通过懒加载加载数据
-(NSArray *)goodsArray{
if (_goodsArray == nil) {
NSString *path = [[NSBundle mainBundle]pathForResource:@"deals" ofType:@".plist"];
NSArray *dicArray = [NSArray arrayWithContentsOfFile:path];
NSMutableArray *array = [[NSMutableArray alloc]init];
for (NSDictionary *dic in dicArray) {
YJWGoodsModel *goods = [YJWGoodsModel goodWithDict:dic];
[array addObject:goods];
}
_goodsArray = array;
}
return _goodsArray;
}
- 利用重用标识符找到 cell
- 给 cell 传递模型数据
-(UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath{
static NSString *reUseId = @"cell";
YJWGoodsCell *cell = [tableView dequeueReusableCellWithIdentifier:reUseId];
cell.goods = self.goodsArray[indexPath.row];
return cell;
}
4.在 YJWGoodsModel 中:
- 设置模型,并提供一个通过字典创建模型的方法
/** title */
@property(nonatomic,strong) NSString *title;
/** icon */
@property(nonatomic,strong) NSString *icon;
/** price */
@property(nonatomic,strong) NSString *price;
/** count */
@property(nonatomic,strong) NSString *buyCount;
+(instancetype)goodWithDict:(NSDictionary *)dict;
- 在模型中的具体实现
#import "YJWGoodsModel.h"
@implementation YJWGoodsModel
+(instancetype)goodWithDict:(NSDictionary *)dict
{
YJWGoodsModel *good = [[self alloc]init];
[good setValuesForKeysWithDictionary:dict];
return good;
}
@end
5.在 YJWGoodsCell 中:
- 将 storyboard 中的子控件连线到类扩展中
@property (weak, nonatomic) IBOutlet UIImageView *iconView;
@property (weak, nonatomic) IBOutlet UILabel *title;
@property (weak, nonatomic) IBOutlet UILabel *price;
@property (weak, nonatomic) IBOutlet UILabel *count;
- 需要提供一个模型属性,重写模型的 set 方法,在这个方法中设置模型数据到子控件上
@property(strong,nonatomic)YJWGoodsModel *goods;
-(void)setGoods:(YJWGoodsModel *)goods{
_goods = goods;
self.iconView.image = [UIImage imageNamed:goods.icon];
self.title.text = goods.title;
self.price.text = [NSString stringWithFormat:@"¥ %@",goods.price];
self.count.text = [NSString stringWithFormat:@"%@人已购买",goods.buyCount];
}
二、xib 自定义 cell
1.创建一个继承自 UITableViewCell 的子类,比如 YJWGoodsCell
2.创建一个 xib 文件(文件名建议跟 cell 的类名一样),比如 YJWGoodsCell.xib
- 拖拽一个 UITableViewCell 出来
- 修改 cell 的 class 为 YJWGoodsCell
-
设置 cell 的重用标识符
- 往 cell 中添加需要用到的子控件
3.在控制器中
- 利用 registerNib... 方法注册 xib 文件
UINib *nib = [UINib nibWithNibName:@"YJWGoodsCell" bundle:nil];
[self.myTableView registerNib:nib forCellReuseIdentifier:@"YJWcell"];
- 利用重用标识符找到 cell
- 给 cell 传递模型数据
-(UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath{
static NSString *reUseId = @"YJWcell";
YJWGoodsCell *cell = [tableView dequeueReusableCellWithIdentifier:reUseId];
cell.goods = self.goodsArray[indexPath.row];
return cell;
}
如果没有注册 xib 文件,就需要手动去加载 xib 文件:
-(UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath{
static NSString *reUseId = @"YJWcell";
YJWGoodsCell *cell = [tableView dequeueReusableCellWithIdentifier:reUseId];
if (cell == nil) {
cell = [[NSBundle mainBundle]loadNibNamed:@"YJWGoodsCell" owner:nil options:nil][0];
}
cell.goods = self.goodsArray[indexPath.row];
return cell;
}
4.在 YJWGoodsCell 中
- 将 xib 中的子控件连线到类扩展中
- 需要提供一个模型属性,重写模型的 set 方法,在这个方法中设置模型数据到子控件上
- 也可以将创建获得 cell 的代码封装起来
三、1️⃣代码自定义 cell
1.创建一个继承自 UITableViewCell 的子类,比如 YJWGoodsCell
- 在 initWithStyle:reuseIdentifier:方法中:
- 添加子控件
- 设置子控件的初始化属性(比如文字的颜色、字体)
- 在 layoutSubviews 方法中设置子控件的 frame
- 这个方法专门用来布局子控件,一般在这里设置子控件的 frame,当控件本身的尺寸发生改变的时候,系统会自动调用这个方法
- 需要提供一个模型属性,重写模型的 set 方法,在这个方法中设置模型数据到子控件
2.在控制器中
- 利用 registerClass... 方法注册 YJWGoodsCell 类
- 利用重用标识符找到 cell (如果没有注册类,就需要手动创建cell)
- 给 cell 传递模型数据
2️⃣代码自定义 cell
1.创建一个继承自 UITableViewCell 的子类,比如 YJWGoodsCell
- 在 initWithStyle:reuseIdentifier:方法中:
- 添加子控件
- 添加子控件约束(建议使用 masonry)
- 设置子控件的初始化属性(比如文字的颜色、字体)
- 需要提供一个模型属性,重写模型的 set 方法,在这个方法中设置模型数据到子控件
2.在控制器中
- 利用 registerClass... 方法注册 YJWGoodsCell 类
- 利用重用标识符找到 cell (如果没有注册类,就需要手动创建cell)
- 给 cell 传递模型数据
- 自定义非等高 cell
一、xib 自定义cell(重要)
- 在模型中增加一个 cellHeight 属性,用来存放对应 cell 的高度
- 在 cell 的模型属性 set 方法中调用 [self layoutIfNeeded] 方法强制布局,然后计算出 cellHeight 属性值
- 在控制器中实现 -tableView: estimatedHeightForRowAtIndexPath: 方法,返回一个估计高度,比如 200【调用此方法后,先执行 tableView:(UITableView *)tableView cellForRowAtIndexPath: 然后再执行 tableView:heightForRowAtIndexPath: 方法,否则执行顺序相反】
- 在控制器中实现 tableView:heightForRowAtIndexPath: 方法,返回 cell 的真实高度(模型中的 cellHeight 属性)
- 当 label 中的内容不止一行时,系统计算往往会有些布局上的瑕疵,此时在 cell 中实现如下方法,会有所改善:
-(void)awakeFromNib{
//设置 label 每一行文字的最大宽度
//为了保证计算出来的数值 跟 真正显示出来的效果一致
self.content.preferredMaxLayoutWidth = [UIScreen mainScreen].bounds.size.width - 20;
}
二、storyboard 定义 cell
和用 xib 自定义 cell 类似,内部各控件换个地方而已。
三、代码自定义 cell(frame)
四、代码自定义 cell(Autolayout)
与自定义等高 cell 极其相似。