iOS 动态调整tableViewCell 高度

效果图:

分析:从plist文件中读取数据源,plist最外层是一个Array,Array中存放的是字典,每个字典存放的key值并不完全相同。

    

一、单元格复用问题

1、首先读取数据源,建立数据模型,这里我只创建了一个数据模型,包含plist中所有的key值所对应的属性。

2、创建tableView,同时定制Cell,

  根据category,可以分成四种单元格,在tableView创建单元格时创建4种代码如下:

 1 -(UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
 2 {
 3
 4     CustomCell * appcustomCell = [tableView dequeueReusableCellWithIdentifier:@"appcustomCell"];
 5
 6     if (!appcustomCell) {
 7         appcustomCell = [[CustomCell alloc]initWithStyle:UITableViewCellStyleDefault reuseIdentifier:@"appcustomCell"];
 8         NSLog(@"appcustomCell");
 9     }
10
11     CustomCell * listcustomCell = [tableView dequeueReusableCellWithIdentifier:@"listcustomCell"];
12
13     if (!listcustomCell) {
14         listcustomCell = [[CustomCell alloc]initWithStyle:UITableViewCellStyleDefault reuseIdentifier:@"listcustomCell"];
15         NSLog(@"listcustomCell");
16     }
17
18     CustomCell * origincustomCell = [tableView dequeueReusableCellWithIdentifier:@"origincustomCell"];
19
20     if (!origincustomCell) {
21         origincustomCell = [[CustomCell alloc]initWithStyle:UITableViewCellStyleDefault reuseIdentifier:@"news"];
22         NSLog(@"origincustomCell");
23     }
24
25     CustomCell * largecustomCell = [tableView dequeueReusableCellWithIdentifier:@"largecustomCell"];
26
27     if (!largecustomCell) {
28         largecustomCell = [[CustomCell alloc]initWithStyle:UITableViewCellStyleDefault reuseIdentifier:@"largecustomCell"];
29         NSLog(@"largecustomCell");
30     }
31
32
33
34     Model *model = [_dataSource objectAtIndex:indexPath.row];
35
36
37     if ([model.category isEqualToString:@"list"]) {
38         listcustomCell.category = model.category;
39         listcustomCell.message = model.title ;
40
41         listcustomCell.imageNames =  model.pics;
42         listcustomCell.source = model.source;
43         listcustomCell.time = model.time ;
44         return listcustomCell;
45
46
47     }
48     if ([model.category isEqualToString:@"origin"]) {
49         origincustomCell.category = model.category;
50         origincustomCell.message = model.title ;
51
52        origincustomCell.picture = model.picture ;
53        origincustomCell.source =  model.source;
54         return origincustomCell;
55     }
56
57     if ([model.category isEqualToString:@"large"]) {
58        largecustomCell.category = model.category;
59         largecustomCell.message = model.title ;
60
61        largecustomCell.picture =  model.picture;
62         largecustomCell.source = model.source;
63         largecustomCell.time = model.time;
64         return largecustomCell;
65     }
66
67     if ([model.category isEqualToString:@"app"]) {
68         appcustomCell.category = model.category;
69         appcustomCell.message = model.title ;
70
71        appcustomCell.icon = model.icon;
72        appcustomCell.appname = model.appname;
73         return appcustomCell;
74     }
75     return nil;
76 }

上面是防止复用时出错的办法

二、题目的重点:Cell动态调整高度

1、动态调整单元格的高度,那么肯定要调用tableView代理的一个方法,换回单元格高度,代码如下: 1 -(CGFloat)tableView:(UITableView *)tableView heightForRowAtIndexPath:(NSIndexPath *)indexPath

 2 {
 3     //用来返回每一行的高度
 4     //只有确定了数据,能才知道行的高度,所以在这先要去取得数据
 5     Model * model = [_dataSource objectAtIndex:indexPath.row];
 6     //因为计算行高这个事是cell来计算的,所以还得需要创建一个cell对象
 7     //为了去避免在计算行高时,开辟多个cell对象空间,造成资源的浪费
 8     //所以在这里,要实现cell的复用
 9      cell = [[CustomCell alloc]initWithStyle:UITableViewCellStyleDefault reuseIdentifier:@"xx"];
10     if (!cell) {
11         cell = [[CustomCell alloc]initWithStyle:UITableViewCellStyleDefault reuseIdentifier:@"xx"];
12
13     }
14
15     //将数据赋给cell,然后cell去计算行高
16     //这里说的计算是,数据赋值给Cell的时候,都要调用定制Cell类中的对应属性的set方法,在set方法中返回rowHight,rowHight也是Cell的属性
17     //这样按照单元格中的各个控件的顺序返回相应的高度,一定要注意控件的排放顺序
18     cell.category = model.category;
19      cell.message = model.title ;
20     if ([model.category isEqualToString:@"list"]) {
21         cell.imageNames =  model.pics;
22         cell.source = model.source;
23         cell.time = model.time ;
24
25
26     }
27     if ([model.category isEqualToString:@"origin"]) {
28          cell.picture = model.picture ;
29          cell.source =  model.source;
30     }
31
32     if ([model.category isEqualToString:@"large"]) {
33         cell.picture =  model.picture;
34         cell.source = model.source;
35         cell.time = model.time;
36     }
37
38     if ([model.category isEqualToString:@"app"]) {
39         cell.icon = model.icon;
40         cell.appname = model.appname;
41
42     }
43
44
45
46
47     //因为cell里赋值后可以利用赋值内容来计算出行高,所以在赋值后,直接返回行高
48     return cell.rowHeight;
49
50
51 }

2、在定制单元格中返回该控件的高度,通过重写控件的set方法确定该控件是否显示,代码:

 1 -(void)setSource:(NSString *)source
 2 {
 3
 4     _source = source;
 5     if (![_category isEqualToString:@"app"]) {
 6         sourceLabel.hidden = NO;
 7         sourceLabel.text = _source;
 8         sourceLabel.frame = CGRectMake(10, _rowHeight, 100, 15);
 9     }

   //消息所有的工作做完后,要重新云计算一下行高


//下面这个方法是用来取一个控件的最大y值


//这个值是从原点y坐标 + 控件高度


//实际行高等于 上个值 再加 5

10  _rowHeight = CGRectGetMaxY(sourceLabel.frame) + 5;
11
12 }

在Cell定制类中首先加一个Label控件,设置为隐藏,因为不知道这个控件是不是真的需要,所以当调用控件对应内容的set方法时时肯定要使用这个控件了,将控件隐藏属性设置为NO,这里需要重新为控件布局。因为在这个控件之前不知道已有的控件占了多少高度,这里通过rowHight属性获得前面的高度,然后返回时加上自己的高度,加上5是为了调整控件之间的距离吧.

3、不得不说的是label中内容很多时怎么计算其高度,

 1 -(void)setMessage:(NSString *)message
 2 {
 3
 4     //判断一下有没有消息
 5     if (message.length == 0) {
 6         //如果没有消息
 7         messageLabel.hidden = YES;
 8         _rowHeight = 60.0f;
 9         return;
10     }
11     //如果有消息
12     //将参数消息赋给属性
13     _message = message;
14     //有消息要显示,那么就将控件显示出来
15     messageLabel.hidden = NO;
16     //求出这条消息实际占用的高度
17     //下面这个方法用来求出消息内容实际占的size
18     //    message sizeWithFont:(UIFont *)
19     CGSize size = [message boundingRectWithSize:CGSizeMake(255, 9999) options:NSStringDrawingUsesLineFragmentOrigin attributes:@{NSFontAttributeName:[UIFont systemFontOfSize:15]} context:nil].size;
20     //根据计算过后的消息所占的宽高,来调整messageLabel的frame
21     if ([_category isEqualToString:@"origin"]) {
22         messageLabel.frame = CGRectMake(5, 20, 180, size.height);
23     }
24     else
25     {
26         messageLabel.frame = CGRectMake(5, 5, 310, size.height);
27     }
28
29     //给消息控件赋值
30     messageLabel.text = message;
31
32     //消息所有的工作做完后,要重新云计算一下行高
33     //下面这个方法是用来取一个控件的最大y值
34     //这个值是从原点y坐标 + 控件高度
35     //实际行高等于 上个值 再加 5
36     _rowHeight = CGRectGetMaxY(messageLabel.frame) + 5;
37
38
39 }

最重要的应该是这个方法了:

CGSize size = [message boundingRectWithSize:CGSizeMake(255, 9999) options:NSStringDrawingUsesLineFragmentOrigin attributes:@{NSFontAttributeName:[UIFont systemFontOfSize:15]} context:nil].size;不太清除是什么意思,只知道根据message字体大小计算出了一个CGSize,

总结:前面说了要做出的效果,然后说了不同单单元格解决复用重叠的方法,最后说了自动调整高度。
时间: 2024-09-29 17:10:29

iOS 动态调整tableViewCell 高度的相关文章

ios动态获得键盘高度,并改变对话框的位置

NSNotificationCenter:键盘出现.消失时的通知 UIKeyboardWillShowNotification;UIKeyboardDidShowNotification;UIKeyboardWillHideNotification;UIKeyboardDidHideNotification; 在要使用键盘的视图控制器中(既viewDidLoad中),接收键盘事件的通知: - (void) registerForKeyboardNotifications{ //键盘改变时候会调用

05---MVC模式下动态调整Cell高度三部曲

动态调整Cell高度三部曲 我们在做项目开发的过程中经常会遇到每一个cell的高度及cell的子控件的显示个数不同,以我最近开发的微格为例,讲解一下MVC模式动态的调整Cell宽高的三部曲 1>.自定义Cell,重写- (id)initWithStyle:(UITableViewCellStyle)style reuseIdentifier:(NSString *)reuseIdentifier方法 在此方法中添加所有的可能显示的子控件 子控件的frame通过构建的cellFrame模型进行设置

使用jQuery动态调整iframe高度,以及jQuery对dom元素的监听

大家可能会遇到子页面内容较多但iframe高度不够的情况.给iframe设置scrolling="no"的话子页面内容显示不全,不设置又会出现滚动条从而影响美观.当我们点击不同的菜单让iframe加载不同的html文件时,iframe的高度就需要做相应的调整. 主题思路:子页面加载完成后根据具体body的高度给iframe设置一个适合的高度 情况1:各个子页面内容与高度比较固定 <script> $(function(){ $("#Frame_Content&qu

Android - 动态调整ListView高度

布局中,如果设计ListView的高度为包裹内容,那么ListView的高度是随着它的子条目的数量的变化而改变的, 这就可能会导致ListView下面的一些控件的位置也会随着ListView的高度的变化而变化. 项目中可能会碰到需要动态调整或控制ListView的高度的情况,下面就分享一下我自己使用的一种办法. 我遇到的问题: ListView下面有一个Button,如果ListView子条目的数量较少,Button可以正常显示在屏幕上,但如果ListView子条目的数量较多时,Button就会

iOS 动态计算cell高度实用API

// Use the estimatedHeight methods to quickly calcuate guessed values which will allow for fast load times of the table. // If these methods are implemented, the above -tableView:heightForXXX calls will be deferred until views are ready to be display

根据文字动态调整 UILabel 高度

#import <UIKit/UIKit.h> @interface UILabel (dynamicSize) -(float)resizeToFit; -(float)expectedHeight; @end #import "UILabel+dynamicSize.h" @implementation UILabel (dynamicSize) -(float)resizeToFit{ float height = [self expectedHeight]; CGR

[转] iOS TableViewCell 动态调整高度

原文: http://blog.csdn.net/crayondeng/article/details/8899577 最近遇到了一个cell高度变化的问题,在找解决办法的时候,参考了这篇文章,觉得不错 在写sina 微博的显示微博内容时,用到cell进行显示,那么就要考虑到不同微博内容导致的cell高度问题.在微博显示的内容中包括了文字和图片,那么就要计算文字部分的高度和图片部分的高度.这篇博文就记录一下如何处理cell高度的动态调整问题吧! 一.传统的方法 在 tableview的deleg

ios开发之根据内容行数调整cell 高度,与label高度

设置cell高度 - (CGFloat)tableView:(UITableView *)tableView heightForRowAtIndexPath:(NSIndexPath *)indexPath { NoticeMessage* msg = [arrayNoticeMessage objectAtIndex:indexPath.section];//取出对应的section或者cell UIFont *msgFont = [UIFont fontWithName:@"arial&qu

iOS开发笔记-根据frame大小动态调整fontSize的自适应文本及圆形进度条控件的实现

最近同样是新App,设计稿里出现一种圆形进度条的设计,如下: 想了想,圆形进度条实现起来不难,但是其中显示百分比的文本确需要自适应,虽然可以使用时自己设定文本字体的大小,但是这样显得很麻烦,也很low. 查了一圈,目前实现的自适应UILabel,都是根据font大小动态调整frame的size,并不能满足我们的需求.  那么问题来了 如何实现一种能够根据frame大小自适应调整文本font size的圆形进度条呢? 我的实现思路很简单,首先计算出能够给予UILabel的frame最大尺寸,然后根