iOS UITableViewableViewCell自适应高度

  前两天做了一个项目,中间有遇到一个问题,就是聊天的时候cell高度的问题。这是一个很多前辈都遇到过,并且很完美的解决过的问题。这里主要是记录自己的学习心得。项目中首先想到的是用三方库,可是有问题,遂放弃,自己写一个,但是没有封装。项目地址

  UITableView 的属性特征什么的,这里就暂时不做介绍了。

  由于聊天内容比较简单,不需要对聊天做出很多操作,只是简单的使用 UILable 进行展示即可。首先我们定义一个模型 JXChatModel

//
//  JXChatModel.h
//  JXAutoCell
//
//  Created by 王加祥 on 16/9/28.
//  Copyright © 2016年 王加祥. All rights reserved.
//

#import <UIKit/UIKit.h>

@interface JXChatModel : NSObject
// 字典模型转换
+ (instancetype)modelWithDict:(NSDictionary *)dict;
/** 昵称 */
@property (nonatomic,copy) NSString * nickName;
/** 等级 */
@property (nonatomic,copy) NSString * graide;
/** 内容 */
@property (nonatomic,copy) NSString * content;
/** 高度,用来存放计算后的cell高度 */
@property (nonatomic,assign) CGFloat cellHeight;
@end
//
//  JXChatModel.m
//  JXAutoCell
//
//  Created by 王加祥 on 16/9/28.
//  Copyright © 2016年 王加祥. All rights reserved.
//

#import "JXChatModel.h"

@implementation JXChatModel
+ (instancetype)modelWithDict:(NSDictionary *)dict {
    JXChatModel * model = [[self alloc] init];
    [model setValuesForKeysWithDictionary:dict];
    return model;
}

- (void)setValue:(id)value forUndefinedKey:(NSString *)key {
    // 这里对没有定义的键值对不进行任何操作
}
@end
  • 自定义 UITableViewCell

  前面我们定义了一个数据模型,当我们请求过来的数据之后,我们首先将数据转换成模型,之后直接将模型赋值给我们自定义的表格,这样做有极大的好处

//
//  JXChatCell.h
//  JXAutoCell
//
//  Created by 王加祥 on 16/9/28.
//  Copyright © 2016年 王加祥. All rights reserved.
//

#import <UIKit/UIKit.h>

@class JXChatModel;

@interface JXChatCell : UITableViewCell
/** 模型 */
@property (nonatomic,strong) JXChatModel * model;
@end
//
//  JXChatCell.m
//  JXAutoCell
//
//  Created by 王加祥 on 16/9/28.
//  Copyright © 2016年 王加祥. All rights reserved.
//

#import "JXChatCell.h"
#import "JXChatModel.h"
#import "Masonry.h"

/** 等级图片宽度 */
#define kIconWidth 25
/** 等级图片高度 */
#define kIconHeight 25

#define kWidth [UIScreen mainScreen].bounds.size.width
@interface JXChatCell ()
/** 头像 */
@property (nonatomic,weak) UIImageView * iconImageView;
/** 昵称 */
@property (nonatomic,weak) UILabel * nickNameLabel;
/** 内容 */
@property (nonatomic,weak) UILabel * contentLabel;

@end

@implementation JXChatCell

- (void)setModel:(JXChatModel *)model {

    NSString * name = [NSString stringWithFormat:@"rank_%@",model.graide];
    self.iconImageView.image = [UIImage imageNamed:name];

    self.nickNameLabel.text = model.nickName;
    [self.nickNameLabel sizeToFit];
    CGRect frame = self.nickNameLabel.frame;
    frame.size.height = kIconHeight;
    self.nickNameLabel.frame = frame;

    // 设置内容宽度,这里首先在自适应之前需要将内容的宽度固定
    self.contentLabel.text = model.content;
    CGRect contentFrame = self.nickNameLabel.frame;
    contentFrame.size.width = kWidth - kIconWidth - self.nickNameLabel.frame.size.width - 80;
    self.contentLabel.frame = contentFrame;
    [self.contentLabel sizeToFit];

    model.cellHeight = CGRectGetMaxY(self.contentLabel.frame) + 10;

}

#pragma mark - 布局
- (void)layoutSubviews {
    [super layoutSubviews];

    // 等级图片
    self.iconImageView.frame = CGRectMake(5, 0, kIconWidth, kIconHeight);

    // 昵称
    self.nickNameLabel.frame = CGRectMake(kIconWidth + 10 , 0, self.nickNameLabel.frame.size.width, kIconHeight);

    // 内容大小
    self.contentLabel.frame = CGRectMake(CGRectGetMaxX(self.nickNameLabel.frame) + 5, 5, self.contentLabel.frame.size.width, self.contentLabel.frame.size.height);

}
#pragma mark - 懒加载
- (UIImageView *)iconImageView{
    if (_iconImageView == nil) {
        UIImageView * iconImageView = [[UIImageView alloc] init];
        [self.contentView addSubview:iconImageView];
        _iconImageView = iconImageView;
    }
    return _iconImageView;
}

- (UILabel *)nickNameLabel{
    if (_nickNameLabel == nil) {
        UILabel * nickNameLabel = [[UILabel alloc] init];
        nickNameLabel.textColor = [UIColor orangeColor];
        nickNameLabel.font = [UIFont systemFontOfSize:13.0];
        [self.contentView addSubview:nickNameLabel];
        _nickNameLabel = nickNameLabel;
    }
    return _nickNameLabel;
}

- (UILabel *)contentLabel{
    if (_contentLabel == nil) {
        UILabel * contentLabel = [[UILabel alloc] init];
        contentLabel.textColor = [UIColor blackColor];
        contentLabel.numberOfLines = 0;
        contentLabel.font = [UIFont systemFontOfSize:13.0];
        [self.contentView addSubview:contentLabel];
        _contentLabel = contentLabel;
    }
    return _contentLabel;
}
@end
  • 控制器部分代码

  在控制器中我们需要操作的就稍微少了点了,这里我们只需要将数据请求下来,然后将数据转换成模型,存到数组中。之后的 UITableView 数据源就根据这个数组来操作

//
//  ViewController.m
//  JXAutoCell
//
//  Created by 王加祥 on 16/9/28.
//  Copyright © 2016年 王加祥. All rights reserved.
//  自动计算行高

#import "ViewController.h"
#import "JXChatCell.h"
#import "JXChatModel.h"
@interface ViewController ()<UITableViewDelegate,UITableViewDataSource>
/** 数据源数组 */
@property (nonatomic,strong) NSMutableArray * chatArray;
/** UITableView */
@property (nonatomic,weak) UITableView * tableView;
@end

@implementation ViewController

- (void)viewDidLoad {
    [super viewDidLoad];

    // 数据
    NSArray * array = @[
                        @{
                           @"nickName":@"你成佛了",
                           @"graide":@"16",
                           @"content":@"连接方式李金发欧式24234242342冯绍峰烦死拉伸的减肥了敬爱是骄傲是激发按时发放费;啊; 拉伸放假接方式李反对党的圾费垃圾房间爱乱收费;啊; 拉伸放假啊;发;是放假啊;了解算法lkjslajflsajflasjlasjflajflj零距离圣诞节佛按实际大量积分垃圾地方啦垃圾了房间爱令肌肤拉伸件地方垃圾垃圾了极大浪费就暗恋的激发了设计费垃圾费拉激发偶尔加乱收费来释放接方式李反对党的圾费垃圾房间爱乱收费;啊; 拉伸放假啊;发;是放假啊;了解算法lkjslajflsajflasjlasjflajflj零距离圣诞节佛按实际大量积分垃圾地方啦垃圾了房间爱令肌肤拉伸件地方垃圾垃圾了极大浪费就暗恋的激发了设计费垃圾费拉激发偶尔加乱收费来释放接方式李反对党的圾费垃圾房间爱乱收费;啊; 拉伸放假啊;发;是放假啊;了解算法lkjslajflsajflasjlasjflajflj零距离圣诞节佛按实际大量积分垃圾地方啦垃圾了房间爱令肌肤拉伸件地方垃圾垃圾了极大浪费就暗恋的激发了设计费垃圾费拉激发偶尔加乱收费来释放接方式李反对党的圾费垃圾房间爱乱收费;啊; 拉伸放假啊;发;是放假啊;了解算法lkjslajflsajflasjlasjflajflj零距离圣诞节佛按实际大量积分垃圾地方啦垃圾了房间爱令肌肤拉伸件地方垃圾垃圾了极大浪费就暗恋的激发了设计费垃圾费拉激发偶尔加乱收费来释放啊;发;是放假啊;了解算法来释放"
                            },
                        @{
                            @"nickName":@"式李金发",
                            @"graide":@"13",
                            @"content":@"连接方式323242342432圾房间爱乱收费;啊; 拉伸放假啊;发;是放假啊;了解算法来释放"
                            },
                        @{
                            @"nickName":@"垃圾费垃圾房间",
                            @"graide":@"1",
                            @"content":@"连接方式李反对党的圾费垃圾房间爱乱收费;啊; 拉伸放假啊;发;是放假啊;了解算法来释放"
                            },
                        @{
                            @"nickName":@"了仨解放啦",
                            @"graide":@"6",
                            @"content":@"连接方式沙发沙发"
                            },
                        @{
                            @"nickName":@"式李金发",
                            @"graide":@"13",
                            @"content":@"连接方式323242342432圾房间爱乱收费;啊; 拉伸放假啊;发;是放假啊;了解算法来释放"
                            },
                        @{
                            @"nickName":@"垃圾费垃圾房间",
                            @"graide":@"1",
                            @"content":@"连接方式李反对党的圾费垃圾房间爱乱收费;啊; 拉伸放假啊;发;是放假啊;了解算法来释放"
                            },
                        @{
                            @"nickName":@"式李金发",
                            @"graide":@"13",
                            @"content":@"连接方式323242342432圾房间爱乱收费;啊; 拉伸放假啊;发;是放假啊;了解算法来释放"
                            },
                        @{
                            @"nickName":@"垃圾费垃圾房间",
                            @"graide":@"1",
                            @"content":@"连接方式李反对党的圾费垃圾房间爱乱收费;啊; 拉伸放假啊;发;是放假啊;了解算法来释放"
                            },
                        @{
                            @"nickName":@"式李金发",
                            @"graide":@"13",
                            @"content":@"连接方式323242342432圾房间爱乱收费;啊; 拉伸放假啊;发;是放假啊;了解算法来释放"
                            },
                        @{
                            @"nickName":@"垃圾费垃圾房间",
                            @"graide":@"1",
                            @"content":@"连接方式李反对党的圾费垃圾房间爱乱收费;啊; 拉伸放假啊;发;是放假啊;了解算法来释放"
                            },
                        @{
                            @"nickName":@"式李金发",
                            @"graide":@"13",
                            @"content":@"连接方式323242342432圾房间爱乱收费;啊; 拉伸放假啊;发;是放假啊;了解算法来释放"
                            },
                        @{
                            @"nickName":@"垃圾费垃圾房间",
                            @"graide":@"1",
                            @"content":@"连接方式李反对党的圾费垃圾房间爱乱收费;啊; 拉伸放假啊;发;是放假啊;了解算法来释放"
                            },
                        @{
                            @"nickName":@"式李金发",
                            @"graide":@"13",
                            @"content":@"连接方式323242342432圾房间爱乱收费;啊; 拉伸放假啊;发;是放假啊;了解算法来释放"
                            },
                        @{
                            @"nickName":@"垃圾费垃圾房间",
                            @"graide":@"1",
                            @"content":@"连接方式李反对党的圾费垃圾房间爱乱收费;啊; 拉伸放假啊;发;是放假啊;了解算法来释放"
                            },
                        @{
                            @"nickName":@"式李金发",
                            @"graide":@"13",
                            @"content":@"连接方式323242342432圾房间爱乱收费;啊; 拉伸放假啊;发;是放假啊;了解算法来释放"
                            },
                        @{
                            @"nickName":@"垃圾费垃圾房间",
                            @"graide":@"1",
                            @"content":@"连接方式李反对党的圾费垃圾房间爱乱收费;啊; 拉伸放假啊;发;是放假啊;了解算法来释放"
                            },
                        @{
                            @"nickName":@"式李金发",
                            @"graide":@"13",
                            @"content":@"连接方式323242342432圾房间爱乱收费;啊; 拉伸放假啊;发;是放假啊;了解算法来释放"
                            },
                        @{
                            @"nickName":@"垃圾费垃圾房间",
                            @"graide":@"1",
                            @"content":@"连接方式李反对党的圾费垃圾房间爱乱收费;啊; 拉伸放假啊;发;是放假啊;了解算法来释放"
                            },
                        @{
                            @"nickName":@"式李金发",
                            @"graide":@"13",
                            @"content":@"连接方式323242342432圾房间爱乱收费;啊; 拉伸放假啊;发;是放假啊;了解算法来释放"
                            },
                        @{
                            @"nickName":@"垃圾费垃圾房间",
                            @"graide":@"1",
                            @"content":@"连接方式李反对党的圾费垃圾房间爱乱收费;啊; 拉伸放假啊;发;是放假啊;了解算法来释放"
                            },
                        @{
                            @"nickName":@"式李金发",
                            @"graide":@"13",
                            @"content":@"连接方式323242342432圾房间爱乱收费;啊; 拉伸放假啊;发;是放假啊;了解算法来释放"
                            },
                        @{
                            @"nickName":@"垃圾费垃圾房间",
                            @"graide":@"1",
                            @"content":@"连接方式李反对党的圾费垃圾房间爱乱收费;啊; 拉伸放假啊;发;是放假啊;了解算法来释放"
                            },
                        @{
                            @"nickName":@"式李金发",
                            @"graide":@"13",
                            @"content":@"连接方式323242342432圾房间爱乱收费;啊; 拉伸放假啊;发;是放假啊;了解算法来释放"
                            },
                        @{
                            @"nickName":@"垃圾费垃圾房间",
                            @"graide":@"1",
                            @"content":@"连接方式接方式李反对党的圾费垃圾房间爱乱收费;啊; 拉伸放假啊;发;是放假啊;了解算法lkjslajflsajflasjlasjflajflj零距离圣诞节佛按实际大量积分垃圾地方啦垃圾了房间爱令肌肤拉伸件地方垃圾垃圾了极大浪费就暗恋的激发了设计费垃圾费拉激发偶尔加乱收费来释放接方式李反对党的圾费垃圾房间爱乱收费;啊; 拉伸放假啊;发;是放假啊;了解算法lkjslajflsajflasjlasjflajflj零距离圣诞节佛按实际大量积分垃圾地方啦垃圾了房间爱令肌肤拉伸件地方垃圾垃圾了极大浪费就暗恋的激发了设计费垃圾费拉激发偶尔加乱收费来释放接方式李反对党的圾费垃圾房间爱乱收费;啊; 拉伸放假啊;发;是放假啊;了解算法lkjslajflsajflasjlasjflajflj零距离圣诞节佛按实际大量积分垃圾地方啦垃圾了房间爱令肌肤拉伸件地方垃圾垃圾了极大浪费就暗恋的激发了设计费垃圾费拉激发偶尔加乱收费来释放李反对党的圾费垃圾房间爱乱收费;啊; 拉伸放假啊;发;是放假啊;了解算法来释放"
                            },
                        @{
                            @"nickName":@"式李金发",
                            @"graide":@"13",
                            @"content":@"连接方式接方式李反对党的圾费垃圾房间爱乱收费;啊; 拉伸放假啊;发;是放假啊;了解算法lkjslajflsajflasjlasjflajflj零距离圣诞节佛按实际大量积分垃圾地方啦垃圾了房间爱令肌肤拉伸件地方垃圾垃圾了极大浪费就暗恋的激发了设计费垃圾费拉激发偶尔加乱收费来释放323242342432圾房间爱乱收费;啊; 拉伸放假啊;发;是放假啊;了解算法来释放"
                            },
                        @{
                            @"nickName":@"垃圾费垃圾房间",
                            @"graide":@"1",
                            @"content":@"连接方式接方式李反对党的圾费垃圾房间爱乱收费;啊; 拉伸放假啊;发;是放假啊;了解算法lkjslajflsajflasjlasjflajflj零距离圣诞节佛按实际大量积分垃圾地方啦垃圾了房间爱令肌肤拉伸件地方垃圾垃圾了极大浪费就暗恋的激发了设计费垃圾费拉激发偶尔加乱收费来释放李反对党的圾费垃圾房间爱乱收费;啊; 拉伸放假啊;发;是放假啊;了解算法来释放"
                            },
                        @{
                            @"nickName":@"式李金发",
                            @"graide":@"13",
                            @"content":@"连接方式接方式李反对党的圾费垃圾房间爱乱收费;啊; 拉伸放假啊;发;是放假啊;了解算法lkjslajflsajflasjlasjflajflj零距离圣诞节佛按实际大量积分垃圾地方啦垃圾了房间爱令肌肤拉伸件地方垃圾垃圾了极大浪费就暗恋的激发了设计费垃圾费拉激发偶尔加乱收费来释放323242342432圾房间爱乱收费;啊; 拉伸放假啊;发;是放假啊;了解算法来释放"
                            },
                        @{
                            @"nickName":@"垃圾费垃圾房间",
                            @"graide":@"1",
                            @"content":@"连接方式接方式李反对党的圾费垃圾房间爱乱收费;啊; 拉伸放假啊;发;是放假啊;了解算法lkjslajflsajflasjlasjflajflj零距离圣诞节佛按实际大量积分垃圾地方啦垃圾了房间爱令肌肤拉伸件地方垃圾垃圾了极大浪费就暗恋的激发了设计费垃圾费拉激发偶尔加乱收费来释放李反对党的圾费垃圾房间爱乱收费;啊; 拉伸放假啊;发;是放假啊;了解算法来释放"
                            },
                        @{
                            @"nickName":@"式李金发",
                            @"graide":@"13",
                            @"content":@"连接方式接方式李反对党的圾费垃圾房间爱乱收费;啊; 拉伸放假啊;发;是放假啊;了解算法lkjslajflsajflasjlasjflajflj零距离圣诞节佛按实际大量积分垃圾地方啦垃圾了房间爱令肌肤拉伸件地方垃圾垃圾了极大浪费就暗恋的激发了设计费垃圾费拉激发偶尔加乱收费来释放323242342432圾房间爱乱收费;啊; 拉伸放假啊;发;是放假啊;了解算法来释放"
                            },
                        @{
                            @"nickName":@"垃圾费垃圾房间",
                            @"graide":@"1",
                            @"content":@"连接方式李反对党的圾费垃圾房间爱乱收费;啊; 拉伸放假啊;发;是放假啊;了解算法lkjslajflsajflasjlasjflajflj零距离圣诞节佛按实际大量积分垃圾地方啦垃圾了房间爱令肌肤拉伸件地方垃圾垃圾了极大浪费就暗恋的激发了设计费垃圾费拉激发偶尔加乱收费来释放"
                            }
                        ];

    // 将数据转换成模型
    for (NSDictionary * dict in array) {
        JXChatModel * model = [JXChatModel modelWithDict:dict];
        [self.chatArray addObject:model];
    }
    [self.tableView reloadData];
}

- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section {

    return self.chatArray.count;

}

- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {

    static NSString * identifier = @"cell";

    JXChatCell * cell = [tableView dequeueReusableCellWithIdentifier:identifier];
    if (cell == nil) {
        cell = [[JXChatCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:identifier];
    }
    cell.model = self.chatArray[indexPath.row];
    return cell;
}

- (CGFloat)tableView:(UITableView *)tableView heightForRowAtIndexPath:(NSIndexPath *)indexPath {
    JXChatModel * model = self.chatArray[indexPath.row];
    return model.cellHeight;
}

// 先给cell表格一个预估计高度
- (CGFloat)tableView:(UITableView *)tableView estimatedHeightForRowAtIndexPath:(NSIndexPath *)indexPath {
    return 100;
}
- (NSMutableArray *)chatArray{
    if (_chatArray == nil) {
        _chatArray = [NSMutableArray array];
    }
    return _chatArray;
}

- (UITableView *)tableView{
    if (_tableView == nil) {
        UITableView * tableView = [[UITableView alloc] init];
        tableView.frame = self.view.bounds;
        tableView.delegate = self;
        tableView.dataSource = self;
        [self.view addSubview:tableView];
        _tableView = tableView;
    }
    return _tableView;
}
@end

  构建运行,展示效果

时间: 2024-10-05 23:52:19

iOS UITableViewableViewCell自适应高度的相关文章

iOS 8自适应高度单元格问题

iOS 8 中通过UITableViewAutomaticDimension 常量支持自适应高度的单元格(iOS 7 就要麻烦得多).但是在实际应用中,我们需要注意以下几个问题: 1. 设置好模板单元格的自动布局 模板单元格中,subviews的自动局部必须要能够把单元格撑满.也就是说,iOS 必须能够通过内容的自动布局约束计算出 cell 的高.以下面的单元格为例: cell中有上下两个 Label,上面的Label只有一行文本(lines为1),所以高度在运行时不会改变,但下面的Label是

iOS Label 自适应高度

推荐第二个 测试一,只改变numberOfLines属性,label的高度不会自适应(会有text中的一部分内容称为......) NSString *str = @"jgreijgirjeirgjierjgiu4t9eumctuv5 vtmnvghvmc5v5tgh58tc857y"; UILabel *label = [[UILabel alloc]initWithFrame:CGRectMake(50, 50, 100, 100)]; label.font = [UIFont s

iOS UI10_cell自适应高度

#import "MainViewController.h" #import "Cell.h" @interface MainViewController ()<UITableViewDataSource, UITableViewDelegate> @property(nonatomic, retain)NSArray *picArr; @property(nonatomic, retain)NSMutableArray *ziArr; @end @im

iOS tableViewCell自适应高度 第三发类库

转自:http://www.cnblogs.com/qianLL/p/5393331.html 在github中有许多大牛封装好的第三发类库,其中有个自适应cell高度的类库 下载地址:https://github.com/gsdios/SDAutoLayout model类 commentsModel #import "JSONModel.h" #import "getCommentData.h" @interface commentsModel : JSONMo

iOS UITextView自适应高度UITextContainerView抖动问题

在打造一个类似于微信朋友圈评论输入框的时候,需要动态调整输入框的高度, 但是,在调整了UITextView的高度之后,继续输入会导致内容(UITextContainerView里的文字)抖动. scrollRangeToVisible 方法解决了我的问题(Swift 3): textView.scrollRangeToVisible(NSRange.init(location: 0, length: 0)) 获取UITextView内的文字高度以及行数的方法(Swift 3): let heig

【原】ios tableViewCell 自适应高度

原文:http://www.cnblogs.com/A--G/p/4819051.html 前言:之前在做一个类似微博的小需求时候,用table view实现了微博文字和图片等等的基本展示,由于文字和图片的数量问题,cell高度会受到影响. 以前的做法是在heightForRowAtIndexPath 里取出这条微博的model,计算图片和文字的高度,现在有一个简单一点的办法: 在heightForRowAtIndexPath里重新获取这个cell的高度即可, TableViewCell *ce

iOS UITableCell自适应高度

列如--展示新闻信息列表. 首先得有一个Model类--New New.h为: // //  News.h //  Cellhight // //  Created by Dubai on 15-5-7. //  Copyright (c) 2015年 Dubai. All rights reserved. // #import <Foundation/Foundation.h> @interface News : NSObject @property (nonatomic,retain) N

iOS UITableViewCell自适应高度

在cell.m文件中 1)初始化方法中: self.lalName=[[UILabel alloc] initWithFrame:CGRectMake(71, 5, 250, 40)]; [self addSubview:self.lalName]; 2)创建方法: //给用户介绍赋值并且实现自动换行 -(void)setIntroductionText:(NSString*)text{ //获得当前cell的高度 CGRect frame=[self frame]; //文本赋值 self.l

IOS UILabel 根据内容自适应高度

iOS Label 自适应高度  适配iOS7以后的版本 更多 self.contentLabelView = [[UILabel alloc] init]; self.contentLabelView.font = SYS_FONT(15); self.contentLabelView.lineBreakMode =NSLineBreakByTruncatingTail ; self.contentLabelView.textColor =  [UIColor colorWithHexStri