从零开始学ios开发(十二):Table Views(中)UITableViewCell定制
我们继续学习Table View的内容,这次主要是针对UITableViewCell,在前一篇的例子中我们已经使用过UITableViewCell,一个默认的UITableViewCell包含imageView、textLabel、detailTextLabel等属性,但是很多时候这些默认的属性并不能满足需要,其实更多的时候我们想自己制定UITableViewCell的内容,这篇学习的就是制定自己的UITableViewCell。
UITableViewCell继承自UIView,因此它可以加载任意的subView在上面,基于这一点,我们就可以定制自己的UITableViewCell了。制定UITableViewCell有2种方法,一种是写代码生成UITableViewCell控件上的内容,另一种是拖控件到一个UITableViewCell控件上,这两种方法都会用一个例子来进行说明。
首先我们使用code的方法,来定制自己的UITableViewCell
1)创建一个新的项目,template选择Single View Application,命名为Cells
2)添加Table View,连接delegate和data source到File's Owner 选中BIDController.xib文件,从Object Library中拖一个Table View到view上,然后选中view中的table view,打开Connections Inspector,拖动dataSource和delegate右边的小圆圈到File's Owner上
3)添加Cell 在Project navigator中选中Cells文件夹,然后command+N,添加一个新的文件。在弹出的对话框中,左边选择Cocoa Touch,右边选择Objective-C,然后点击Next
在下一个对话框中把Class命名为BIDNameAndColorCell,Subclass of选择UITableViewCell,然后点击Next
在下一个对话框中选择Create,完成创建
BIDNameAndColor文件继承自UITableViewCell,我们将先对其进行定制,添加一些我们需要的控件,当BIDViewController中调用table cell的时候,就直接调用这个文件即可。
4)添加BIDNameAndColorCell代码 打开BIDNameAndColorCell.h文件,添加如下代码
#import <UIKit/UIKit.h>@interface BIDNameAndColorCell : UITableViewCell@property (copy, nonatomic) NSString *name; @property (copy, nonatomic) NSString *color; @end
我们将在table view cell中显示2个字符串,一个是name,另一个是color,显示的内容会从之后定义的NSArray中读取。(注意,我们这里使用的是copy,而不是通常使用的strong,使用copy的好处是不会改变原有的字符串中的内容,当然在这里我们也不会改变字符串的内容,你如果使用了strong也问题不大,不过书上的建议是如果一个property是NSString,最好使用copy)
接着编辑BIDNameAndColorCell.m文件,添加下面的code
#import "BIDNameAndColorCell.h"#define kNameValueTag 1 #define kColorValueTag 2@implementation BIDNameAndColorCell @synthesize name; @synthesize color;
首先添加2个常量kNameValueTag和kColorValueTag,这2个常量用来标识table view cell中的name和color。接着就是name和color的synthesize了,和之前例子中的一样。
下面修改BIDNameAndColorCell.m中已存在的initWithStyle:reuseIdentifier:方法
- (id)initWithStyle:(UITableViewCellStyle)style reuseIdentifier:(NSString *)reuseIdentifier {self = [super initWithStyle:style reuseIdentifier:reuseIdentifier];if (self) {// Initialization code CGRect nameLabelRect = CGRectMake(0, 5, 70, 15); UILabel *nameLabel = [[UILabel alloc] initWithFrame:nameLabelRect]; nameLabel.textAlignment = UITextAlignmentRight; nameLabel.text = @"Name:"; nameLabel.font = [UIFont boldSystemFontOfSize:12]; [self.contentView addSubview:nameLabel]; CGRect colorLabelRect = CGRectMake(0, 26, 70, 15); UILabel *colorLabel = [[UILabel alloc] initWithFrame:colorLabelRect]; colorLabel.textAlignment = UITextAlignmentRight; colorLabel.text = @"Color:"; colorLabel.font = [UIFont boldSystemFontOfSize:12]; [self.contentView addSubview:colorLabel]; CGRect nameValueRect = CGRectMake(80, 5, 200, 15); UILabel *nameValue = [[UILabel alloc]initWithFrame:nameValueRect]; nameValue.tag = kNameValueTag; [self.contentView addSubview:nameValue]; CGRect colorValueRect = CGRectMake(80, 25, 200, 15); UILabel *colorValue = [[UILabel alloc]initWithFrame:colorValueRect]; colorValue.tag = kColorValueTag; [self.contentView addSubview:colorValue]; } return self; }
上面的代码应该还是比较容易理解的吧,创建了4个UILabel,设置完UILabel的属性后,把他们加入到UITableViewCell中,table view cell有一个默认的view叫做contentView,contenView负责容纳其他的subView,因此上面code中所创建的4个UILabel都会添加到contentView中,使用的语句是[self.contentView addSubview:colorValue]
再说一下上面创建的4个UILabel在这个例子中的作用,nameLabel和colorLabel的作用是纯粹的Label,它们的值不会在改变,在这只它们属性的使用已经分别为它们赋值了。nameValue和colorValue这2个label是用来显示NSArray中的值的,这也是为什么只有这2个label会有property,因为它们需要改变值。另外在code中还未这2个label制定了tag,这个tag的具体作用是通过它来标识具体的label,添加下面的code,就会有所了解。
- (void)setName:(NSString *)n {if(![n isEqualToString:name]) {name = [n copy]; UILabel *nameLabel = (UILabel *)[self.contentView viewWithTag:kNameValueTag]; nameLabel.text = name; } } - (void)setColor:(NSString *)c { if(![c isEqualToString:color]) { color = [c copy]; UILabel *colorLabel = (UILabel *)[self.contentView viewWithTag:kColorValueTag]; colorLabel.text = color; } }
@synthesize会帮我们自动创建get和set方法,但在这里我们需要自己写set方法,因此通过上面的code来覆盖系统自动为我们生成的set方法。2个set方法的实现是一样的。首先比较新赋值的字符串和旧的字符串是否一样,如果不一样就进行赋值。然后需要解释的就是这句话 UILabel *colorLabel = (UILabel *)[self.contentView viewWithTag:kColorValueTag]; 如果找到table view cell中的控件?即使使用刚才我们创建的2个常量,因为每一个控件的tag值都是不一样的,因此根据tag值就可以很方便的找到我们需要的控件,viewWithTag返回的类型是(UIView *),所以我们将类型强制转换成(UILable *),就可以得到我们需要的Label了,然后对Label进行赋值。
5)添加BIDViewController代码 打开BIDViewController.h,添加如下代码
#import <UIKit/UIKit.h>@interface BIDViewController : UIViewController <UITableViewDelegate, UITableViewDataSource>@property (strong, nonatomic) NSArray *computers;@end
很简单,不解释。
打开BIDViewController.m,添加如下代码
#import "BIDViewController.h" #import "BIDNameAndColorCell.h"@implementation BIDViewController @synthesize computers; ...... - (void)viewDidLoad { [super viewDidLoad]; // Do any additional setup after loading the view, typically from a nib. NSDictionary *row1 = [[NSDictionary alloc] initWithObjectsAndKeys: @"MacBook", @"Name", @"White", @"Color", nil]; NSDictionary *row2 = [[NSDictionary alloc] initWithObjectsAndKeys: @"MacBook Pro", @"Name", @"Silver", @"Color", nil]; NSDictionary *row3 = [[NSDictionary alloc] initWithObjectsAndKeys: @"iMac", @"Name", @"Silver", @"Color", nil]; NSDictionary *row4 = [[NSDictionary alloc] initWithObjectsAndKeys: @"Mac Mini", @"Name", @"Silver", @"Color", nil]; NSDictionary *row5 = [[NSDictionary alloc] initWithObjectsAndKeys: @"Mac Pro", @"Name", @"Silver", @"Color", nil]; self.computers = [[NSArray alloc] initWithObjects:row1, row2, row3, row4, row5, nil]; } - (void)viewDidUnload { [super viewDidUnload]; // Release any retained subviews of the main view. // e.g. self.myOutlet = nil; self.computers = nil; }
首先我们引入BIDNameAndColor的头文件,之后我们将会创建它的实例,在viewDidLoad中,创建了5个NSDictionary,用于保存name和color名值对,使用的方法是initWithObjectsAndKeys,就是说下面的内容前一个作为object,后一个作为key,举个例子,最后一个NSDictionary中,@"Mac Pro"就是object,@"Name"就是key。最后将5个NSDictionary保存到NSArray中(computers中)
在添加下面的code
#pragma mark - #pragma mark Table Data Source Methods - (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section {return [self.computers count]; } - (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath { static NSString *CellTableIdentifier = @"CellTableIdentifier"; BIDNameAndColorCell *cell = [tableView dequeueReusableCellWithIdentifier:CellTableIdentifier]; if(cell == nil) { cell = [[BIDNameAndColorCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:CellTableIdentifier]; } NSUInteger row = [indexPath row]; NSDictionary *rowData = [self.computers objectAtIndex:row]; cell.name = [rowData objectForKey:@"Name"]; cell.color = [rowData objectForKey:@"Color"]; return cell; }
tableView:numberOfRowsInSection: 返回section中的行数 tableView:cellForRowAtIndexPath: 这个方法稍微有些不同,它吃创建了一个BIDNameAndColorCell的对象,而不是创建默认的UITableViewCell,这样就可以直接使用我们自己定义的cell了,这里虽然也指定了UITableViewCellStyleDefault,但是不会起作用,因为我们自己定义了cell
之后的代码应该很好理解,很直观。
6)编译运行
Cells
7)使用UITableViewCell控件,创建项目,添加table view,连接File's Owner 现在我们使用第二种方法来定制UITableViewCell,最终的效果和上面的例子一样,创建一个新的项目,同样选择Single View Application,命名为Cells2
添加Table View,连接delegate和data source到File's Owner
8)添加BIDNameAndColorCell文件并编辑 和上面的例子一样,添加BIDNameAndColorCell文件
打开BIDNameAndColorCell.h文件,添加如下代码
#import <UIKit/UIKit.h>@interface BIDNameAndColorCell : UITableViewCell <UITableViewDelegate, UITableViewDataSource>
@property (copy, nonatomic) NSString *name; @property (copy, nonatomic) NSString *color;@property (strong, nonatomic) IBOutlet UILabel *nameLabel; @property (strong, nonatomic) IBOutlet UILabel *colorLabel; @end
和之前有所不同的是,我们多添加了2个Outlet,因为之后要添加xib,因此这2个outlet会指向xib上了2个UILabel
打开BIDNameAndColorCell.m文件,添加如下代码
#import "BIDNameAndColorCell.h"@implementation BIDNameAndColorCell @synthesize name; @synthesize color; @synthesize nameLabel; @synthesize colorLabel; - (void)setName:(NSString *)n { if(![n isEqualToString:name]) { name = [n copy]; nameLabel.text = name; } } - (void)setColor:(NSString *)c { if(![c isEqualToString:color]) { color = [c copy]; colorLabel.text = color; } }
我们重新定义了setName和setColor,这里不需要使用tag,因为我们直接使用outlet就可以找到我们需要的UILabel,另外我们也没在initWithStyle:reuseIdentifier中创建4个Label,因为我们会在之后UITableViewCell控件中添加。
9)添加xib 在Project navigator中鼠标右键单击Cells2文件夹,然后选择New File...,在填出的对话框中左边选择User Interface,右边选择Empty,点击Next
之后的Device Family中选择iphone,点击Next
命名为BIDNameAndColorCell.xib,点击Create
在Project navigator中选中BIDNameAndColorCell.xib文件,因为我们创建的是Empy,因此GUI中什么都没有,在Object library中找到Table View Cell 拖到GUI中
选中view中的table view cell,打开Attributes inspector,找到Identifier,并设置为CellTableIdentifier 这个Identifier就是之前我们code中用到过的Identifier
10)向table view cell中添加控件 往table view cell中拖4个UILable
将左上方的UILabel命名为"Name:",然后设置为粗体(在attribute inspector中设置) 将左下方的UILabel命名为"Color:",然后设置为粗体(在attribute inspector中设置) 将右上方的UILabel拉到右边出现辅助线的位置 将右下方的UILabel拉到右边出现辅助线的位置 设置完成后的样子如下 (不必将右边2个Label的文字去掉,程序运行是会为它们重新赋值)
11)关联 接着我们将BIDNameAndColorCell.xib和BIDNameAndColorCell文件关联起来,选中GUI中的view,打开Identify inspector,将Class指定为BIDNameAndColorCell
还是选中view,切换到connections inspector,里面有colorLabel和nameLabel 将colorLabel和nameLabel拖到view中对应的UILabel上,关联起来(最右边的2个label)
12)写代码 打开BIDViewController.h文件,添加如下代码
#import <UIKit/UIKit.h>@interface BIDViewController : UIViewController <UITableViewDelegate, UITableViewDataSource>@property (strong, nonatomic) NSArray *computers;@end
这个和上一个例子一样,不解释了,打开BIDViewController.m文件,添加如下代码
#import "BIDViewController.h" #import "BIDNameAndColorCell.h"@implementation BIDViewController @synthesize computers; ...... - (void)viewDidLoad { [super viewDidLoad]; // Do any additional setup after loading the view, typically from a nib. NSDictionary *row1 = [[NSDictionary alloc] initWithObjectsAndKeys: @"MacBook Air", @"Name", @"Silver", @"Color", nil]; NSDictionary *row2 = [[NSDictionary alloc] initWithObjectsAndKeys: @"MacBook Pro", @"Name", @"Silver", @"Color", nil]; NSDictionary *row3 = [[NSDictionary alloc] initWithObjectsAndKeys: @"iMac", @"Name", @"Silver", @"Color", nil]; NSDictionary *row4 = [[NSDictionary alloc] initWithObjectsAndKeys: @"Mac Mini", @"Name", @"Silver", @"Color", nil]; NSDictionary *row5 = [[NSDictionary alloc] initWithObjectsAndKeys: @"Mac Pro", @"Name", @"Silver", @"Color", nil]; self.computers = [[NSArray alloc] initWithObjects:row1, row2, row3, row4, row5, nil]; } - (void)viewDidUnload { [super viewDidUnload]; // Release any retained subviews of the main view. // e.g. self.myOutlet = nil; self.computers = nil; } #pragma mark - #pragma mark Table View Data Source Methods - (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section { return [self.computers count]; } - (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath { static NSString *CellTableIdentifier = @"CellTableIdentifier"; static BOOL nibsRegistered = NO; if(!nibsRegistered) { UINib *nib = [UINib nibWithNibName:@"BIDNameAndColorCell" bundle:nil]; [tableView registerNib:nib forCellReuseIdentifier:CellTableIdentifier]; nibsRegistered = YES; } BIDNameAndColorCell *cell = [tableView dequeueReusableCellWithIdentifier:CellTableIdentifier]; NSUInteger row = [indexPath row]; NSDictionary *rowData = [self.computers objectAtIndex:row]; cell.name = [rowData objectForKey:@"Name"]; cell.color = [rowData objectForKey:@"Color"]; return cell; }
我们所要关心的就是tableView:cellForRowAtIndexPath这个方法中的if语句这段代码:
if(!nibsRegistered) { UINib *nib = [UINib nibWithNibName:@"BIDNameAndColorCell" bundle:nil]; [tableView registerNib:nib forCellReuseIdentifier:CellTableIdentifier]; nibsRegistered = YES; }
UINib通过xib文件的名字找到xib文件,然后tableView会调用这个xib文件,nibsRegistered保证只有第一次调用这个方法的时候会去寻找并载入xib,之后则不会。
13)编译运行 编译运行程序,得到的结果和之前的一个程序应该是一样的
14)总结 这篇文章使用2种方式定制了UITableViewCell,一种是代码实现,另一种是传统的拖控件实现,2种方法应该说各有利弊,不一定拖控件就是好的,我应该已经预感到以后的界面布局应该都使用写代码来实现,已经有好几个博友通过我的例子学习但是得到的界面上面控件的布局出现了差错,目前的原因是他们使用的模拟器和我的不一样,我使用的是iPhone 5.0 Simulator,他们可以是用其他的模拟器,但是我觉得照成差错的原因是因为学习到现在我们都是使用拖控件的方法来布局的,这个会造成差错,如果都是用code来实现布局,那么情况应该会变得一致。
下一篇的内容会讲到Table View的Section、index、搜索栏等等,内容比较多也比较实用,实现的效果如下 我会尽快写完放上来的,谢谢大家的关注,有任何问题大家留言吧,如果我知道的话,我会尽量回答,谢谢!
Cells2
转载于:https://www.cnblogs.com/lovewx/p/3807557.html
从零开始学ios开发(十二):Table Views(中)UITableViewCell定制相关推荐
- 三十而立,从零开始学ios开发(十二):Table Views(上)
这次学习的控件非常重要且非常强大,是ios应用中使用率非常高的一个控件,可以说几乎每个app都会使用到它,它就是功能异常强大的Table Views.可以打开你的iphone中的phone.Messa ...
- 从零开始学 iOS 开发的15条建议
事情困难是事实,再困难的事还是要每天努力去做是更大的事实. 因为我是一路自学过来的,并且公认没什么天赋的前提下,进步得不算太慢,所以有很多打算从零开始的朋友会问我,该怎么学iOS开发.跟粉丝群的朋友交 ...
- 从零开始学ios开发(十四):Navigation Controllers and Table Views(上)
这一篇我们将学习一个新的控件Navigation Controller,很多时候Navigation Controller是和Table View紧密结合在一起的,因此在学习Navigation Co ...
- 从零开始学ios开发(十三):Table Views(下)Grouped and Indexed Sections
在前面2篇关于Table View的介绍中,我们使用的Style都是Plain,没有分组,没有index,这次学习的Table View和iphone中的通讯录很像,有一个个以字符为分割的组,最右边有 ...
- 从零开始学ios开发(三):第一个有交互的app
感谢大家的关注,也给我一份动力,让我继续前进.有了自己的家庭有了孩子,过着上有老下有小的生活,能够挤出点时间学习真的很难,每天弄好孩子睡觉已经是晚上10点左右了,然后再弄自己的事情,一转眼很快就到12 ...
- 【云原生 | 从零开始学Kubernetes】十二、k8spod的生命周期与容器钩子
该篇文章已经被专栏<从零开始学k8s>收录 上一篇文章:k8s污点.容忍度和pod状态 点击跳转 pod生命周期 Init 容器 主容器 容器钩子 创建 pod 需要经过哪些阶段? Pod ...
- 从零开始学ios开发(十):Multiview Applications(多个xib之前的切换)
这篇学习的主要内容是Multiview,在我们学习iphone旋转的时候,介绍过多个view的使用方法,不过这里的view和旋转屏幕中所指的多个view是不同的,旋转屏幕中涉及到的多个view是在一个 ...
- 从零开始学iOS开发的15条建议
事情困难是事实,再困难的事还是要每天努力去做是更大的事实. 分三部分: 第一部分:态度和电脑 1、不要关注别人的学习经历,不要关注别人加薪经历. 因为人各不同,别人的经历极有可能并不适合你.而因为每一 ...
- 从零开始学ios开发(十一):Tab Bars和Pickers
不好意思各位,本人休息了一个礼拜,所以这次的进度延后了,而且这次的学习的内容比较多,时间用的也比较长,文章发布的时间间隔有些长了,望各位谅解,下面继续我们的ios之旅. 这次我们主要学习的内容有2个, ...
最新文章
- php5.6.14,PHP 5.5.30/5.6.14 发布下载,安全修复版本
- 使用Java客户端操作elasticsearch--设置mappings、添加文档、查询数据
- python中使用opencv_如何在Python中使用OpenCV Stitcher类?
- Python2.7升级至Python3.6
- ubuntu类似sourcetree的git可视化工具安装
- 编程时,如何在vs中更换舒服的代码字体
- MySQL 数据库简介
- mac的win10蓝牙鼠标问题
- Java 生成条形码 订单条形码
- 虚拟机中试用windows 8(视频)
- Navicat Premium15 注册出现No all pattern found! file already patched?
- 超级实用的软著申请源代码材料格式文档生成辅助工具——软著源代码工具
- DirectX和OPenGL 与 UE4、U3D、Webgl(ThreeJS)的关系
- 1NF,2NF,3NF,BCNF范式(学习笔记)
- git检出新分支遇到的文件路径过长Filename too long的问题
- hbase命令集(shell 命令,如建表,清空表,增删改查)
- Android应用如何隐藏APP桌面图标
- Cuil搜尋引擎 挑戰Google
- Java实现寻找二维数组的鞍点
- Mybaits中association的用法详解
热门文章
- SAP EWM - 物料主数据 - EWM系统库存规划 - SLOTTING视图属性
- 揭榜:2018中国AI英雄风云榜,年度10位杰出领军人物!
- 资讯丨NVIDIA自造AI超级计算机:轻松进入世界前五
- torch.nn.functional.pad
- (完全解决)为什么运行.bat批处理文件但是只执行了.bat文件中的第一句(行)命令
- matplotlib如何把坐标轴一横一竖给绘制出来
- WordNet简介以及一些语言学知识。
- 2021年度人类社会发展十大科学问题发布
- 离奇的梦境,能够防范大脑过拟合
- 脑机接口技术重大突破!首次帮助瘫痪男子恢复运动和触觉