iOS学习之UITableView

时间:2022-10-10 04:49:06

一、UITableView的概念

  • UITabelView继承于UIScrollView,可以滚动。
  @interface UITableView : UIScrollView <NSCoding>
  • UITableView的每一条数据对应的单元格叫做Cell,是UITableViewCell的一个对象,继承于UIView。
  @interface UITableViewCell : UIView <NSCoding, UIGestureRecognizerDelegate>
  • UITableView可以分区显示,每一个分区称为section,每一行称为row,编号都从0开始。
  • 系统提供了一个专门的类来整合section和row,叫做NSIndexPath。
  • UITableView的分区,叫做section;每一行,叫做row。

iOS学习之UITableView

二、UITableView的基本使用

  • UITableView的创建
    // 创建对象
    // 初始化对象并设置样式
    // 系统为我们提供了两种样式(UITableViewStyleGrouped,UITableViewStylePlain)
    self.tableView = [[UITableView alloc] initWithFrame:self.bounds style:UITableViewStylePlain];
  • UITableView显示的相关属性
   // 设置分割线颜色(Plain样式下)
    self.tableView.separatorColor = [UIColor blackColor];

    // 设置分割线的样式
    self.tableView.separatorStyle = UITableViewCellSeparatorStyleSingleLine;

    // 设置行高
    self.tableView.rowHeight = ;

    // 添加头视图,脚视图
    UIView *headerView = [[UIView alloc] initWithFrame:CGRectMake(, , self.frame.size.width, )];
    headerView.backgroundColor = [UIColor grayColor];   UIView *footView = [[UIView alloc] initWithFrame:CGRectMake(0, self.frame.size.height - 200, self.frame.size.width,200)];    footView.backgroundColor = [UIColor grayColor];    self.tableView.tableHeaderView = headerView;    self.tableView.tableFooterView = footView;

三、UITableView显示数据

  • UITableView中有两个重要的属性:
  // 显示数据相关的代理
  @property (nonatomic, weak, nullable) id<UITableViewDataSource> dataSource;
  // 视图操作相关的代理
  @property (nonatomic, weak, nullable) id<UITableViewDelegate> delegate;
  • UITableView代理的实现代码
    // 设置TableView数据源代理
    self.rootView.tableView.dataSource = self;   // 设置TableView代理 
    self.rootView.tableView.delegate = self;
  • UITableView的DataSource是负责给UITableView对象提供数据的代理,遵循UITableViewDataSource协议。协议中有两个必须实现的协议方法:
  // 每一个分区显示的行数(当前方法必须实现)
  - (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section;

  // 返回cell对象,每一行显示的内容(当前方法必须实现)
  - (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath;
  • UITableView的每一个单元格是UITableViewCell类的对象,继承于UIView。UITableViewCell默认提供了3个视图属性:
    // 标题视图
    cell.textLabel.text = [NSString stringWithFormat:@"朋友圈%ld", indexPath.row];
    // 副标题视图
    cell.detailTextLabel.text = @"分享";
    // 图片视图
    cell.imageView.image = [UIImage imageNamed:@"Action_Moments"];
    // 右侧配件(系统样式)
    cell.accessoryType = UITableViewCellAccessoryDisclosureIndicator;
    // 右侧配件(自定义样式)
    cell.accessoryView = [[UIImageView alloc]initWithImage:[UIImage imageNamed:@"Expression_3"]];

四、UITableViewCell的重用机制

  • 按照上面的方法,如果tableView要显示成百上千条数据时,会因创建过多的cell而导致内存过大程序不能运行。
  • 因此UITableView有一个重用池机制管理cell,目的是使用尽可能少的cell显示所有数据。
  • UITableView重用Cell的流程:

    1)当一个cell被滑出屏幕,这个cell会被系统放到相应的重用池中。

    2)当tableView需要显示一个cell,会先去重用池中尝试获取一个cell。

    3)如果重用池没有cell,就会创建一个cell。

    4)取得cell之后会重新赋值进行使用。

#pragma mark UITableViewCell重用的第一种方法
     // 返回cell对象
    - (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
    {
    static NSString *identifier = @"cell";
    // 1.优先从重用队列中查找标识符为cell的UITableViewCell对象
    UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:identifier];
    if (cell == nil) {
        // 如果cell为空,说明重用队列中没有标识符为cell的对象,那么创建标识符为cell的UITableViewCell的对象
        cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleSubtitle reuseIdentifier:identifier];
    }
    // 设置cell显示的数据
    cell.textLabel.text = @"阿福";
    return cell;
    }
#pragma mark UITableViewCell重用的第二种方法
    // 第一步:注册cell
    [self.tableView registerClass:[UITableViewCell class] forCellReuseIdentifier:@"cell"];
    // 第二步:根据重用标识符查找cell
    // 如果在重用池中找到就返回,找不到就会自动创建一个并返回
    UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:@"cell" forIndexPath:indexPath];

五、UITableView和数组的结合使用

  • 在延展里定义数组:
  // 定义数组用来存放所有的数据
  @property (nonatomic, strong) NSMutableArray *dataArray;
  • 初始化大数组
    // 初始化大数组
    self.dataArray = [NSMutableArray arrayWithArray:@[@"女神", @"傻逼", @"晒到", @"而且"]];
  • 实现协议方法
    // tableView每个分区要显示的个数
    - (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section
    {
    // 根据元素个数设置行数
    return self.dataArray.count;
    }
    // 返回cell
    - (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
    {
    // cell重用
    UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:@"cell" forIndexPath:indexPath];
    // 根据row从数组中取值
    cell.textLabel.text = self.dataArray[indexPath.row];
    return cell;
    }

六、UITableView的常用协议方法

    // 设置分区个数
    - (NSInteger)numberOfSectionsInTableView:(UITableView *)tableView;
    // 设置每一个cell的高度
    - (CGFloat)tableView:(UITableView *)tableView heightForRowAtIndexPath:(NSIndexPath *)indexPath;
    // 设置分区头的高度
    - (CGFloat)tableView:(UITableView *)tableView heightForHeaderInSection:(NSInteger)section;
    // 设置分区尾的高度
    - (CGFloat)tableView:(UITableView *)tableView heightForFooterInSection:(NSInteger)section;
    // 自定义header视图
    - (UIView *)tableView:(UITableView *)tableView viewForHeaderInSection:(NSInteger)section;
    // 自定义footer视图
    - (UIView *)tableView:(UITableView *)tableView viewForFooterInSection:(NSInteger)section;
    // 点击cell
    - (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath;
    // 设置分区头标题
    - (NSString *)tableView:(UITableView *)tableView titleForHeaderInSection:(NSInteger)section;
    // 设置分区尾标题
    - (NSString *)tableView:(UITableView *)tableView titleForFooterInSection:(NSInteger)section;
    // 设置分区索引
    - (NSArray<NSString *> *)sectionIndexTitlesForTableView:(UITableView *)tableView;