iOS基础——通过案例学知识之UITableView(上)

iOS基础——通过案例学知识之UITableView(上)



对于UITableView的知识点特别多,因为它是iOS用得最多控件之一,我会尽我最大努力和语言的组织,将所有知识点介绍到位,今天要实现的效果图

吐槽

  • 与Android对比,可以说跟ListView的实现几乎一样,跟RecyclerView一模一样
  • Android写起来似乎比iOS复杂一点,因为iOS大部分都被封装好了,这一点iOS做得好
  • 对于iOS的方法的命名只能说又长又臭

知识点包括

  • UITableView的UITableViewDataSource
  • UITableView的UITableViewDelegate
  • UITableView的cell的重用

一、准备工作

1、准备数据源(plist)

2、布局文件

二、Model读取数据

分析plist数据的格式,然后创建对应的对象模型,并提供相应的初始化方法,这是mvc中经典的一个步骤

  • 特别注意:@property中属性不可以使用weak属性,否则在UITableView复用机制中会被回收,导致画面显示不出来
@interface HeroModel : NSObject
@property(nonatomic,strong) NSString *icon;
@property(nonatomic,strong) NSString *intro;
@property(nonatomic,strong) NSString *name;

-(instancetype)initWithDict:(NSDictionary *)dict;
+(instancetype)HeroModelWithDict:(NSDictionary *)dict;
@end

在m文件中实现初始化方法,方法中实现字典转换为对象

@implementation HeroModel

-(instancetype)initWithDict:(NSDictionary *)dict{
    if(self = [super init]){
        [self setValuesForKeysWithDictionary:dict];
    }
    return self;
}

+(instancetype)HeroModelWithDict:(NSDictionary *)dict{
    return [[self alloc]initWithDict:dict];
}
@end

三、UITableView

1、声明委托代理,声明属性

要想UITableView有数据,那么就必须通过它的委托代理方法才能显示UITableView中的数据

@interface ViewController ()<UITableViewDataSource>
//存放数据的可变数组
@property (strong, nonatomic) NSMutableArray *dataArray;
//tableview
@property (strong, nonatomic) IBOutlet UITableView *tableView;
@end

2、实现属性的转换

毫无疑问是通过懒加载将plist的内容转为模型存进我们声明的可变数组中

#pragma 复写get方法
#pragma 懒加载,读取plist文件并转换为模型
- (NSMutableArray *)dataArray{
    if(nil == _dataArray){
        //初始化数组
        _dataArray = [NSMutableArray array];
        //获取plist文件路径
        NSString *path = [[NSBundle mainBundle]pathForResource:@"heros.plist" ofType:nil];
        //读取plist文件内容
        NSArray *tempArray = [NSArray arrayWithContentsOfFile:path];
        //遍历plist文件内容,存到可变数组中
        for (NSDictionary * dict in tempArray) {
            HeroModel *heroModel = [HeroModel HeroModelWithDict:dict];
            [_dataArray addObject:heroModel];
        }
    }
    //返回
    return _dataArray;
}

3、交付委托

//交付委托
_tableView.dataSource = self;

4、实现代理的方法

通过实现UITableViewDataSource代理的方法,来显示数据,类似于ListView的Adapter

#pragma UITableViewDataSource委托方法
#pragma 返回一共有多少组
-(NSInteger)numberOfSectionsInTableView:(UITableView *)tableView{
    //默认返回1组
    return 1;
}

#pragma UITableViewDataSource委托方法
#pragma 返回一个组由多少行
-(NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section{
    //返回数据的数量
    return self.dataArray.count;
}

#pragma UITableViewDataSource委托方法
#pragma 返回每一行Item的内容
-(UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath{
    //创建tableview的item
    UITableViewCell *cell = [[UITableViewCell alloc]initWithStyle:UITableViewCellStyleSubtitle reuseIdentifier:nil];
    //通过indexPath的行属性,取出对应的模型
    HeroModel *heroModel = _dataArray[indexPath.row];
    //设置文本信息
    cell.textLabel.text = heroModel.name;
    //设置图片信息
    UIImage *image = [UIImage imageNamed:heroModel.icon];
    cell.imageView.image = image;
    //设置详细信息文本
    cell.detailTextLabel.text = heroModel.intro;
    //设置最右边的箭头
    cell.accessoryType = UITableViewCellAccessoryDisclosureIndicator;
    //返回
    return cell;
}

① UITableView的显示有两种方式,在storyboard中可以设置

1.plain:数据平铺显示,中间没有空隙,数组的头标题有悬浮效果

2.group:数据分组显示,中间留有空隙

② UITableViewDataSource的委托方法,程序会按以下顺序执行

  1. numberOfSectionsInTableView:数据中有呈多少组展示(可选实现,默认返回1组)
  2. numberOfRowsInSection:数据中每组有多少行(必须实现,否则会报错)
  3. cellForRowAtIndexPath:数据中每行的内容(必须实现,否则会报错)

③ UITableViewCell的四种样式

1.UITableViewCellStyleDefault

2.UITableViewCellStyleValue1

3.UITableViewCellStyleValue2

4.UITableViewCellStyleSubtitle

④ cell.accessoryType的五种样式,用得不多就不解释了

  1. UITableViewCellAccessoryNone
  2. UITableViewCellAccessoryDisclosureIndicator
  3. UITableViewCellAccessoryDetailDisclosureButton
  4. UITableViewCellAccessoryCheckmark
  5. UITableViewCellAccessoryDetailButton

5、UITableViewDataSource其他代理方法

这两个代理方法会在group样式上展示得比较清晰

#pragma UITableViewDataSource委托方法
#pragma 返回tableview中头部的标题
-(NSString *)tableView:(UITableView *)tableView titleForHeaderInSection:(NSInteger)section{
    return @"header";
}

#pragma UITableViewDataSource委托方法
#pragma 返回tableview中底部的标题
-(NSString *)tableView:(UITableView *)tableView titleForFooterInSection:(NSInteger)section{
    return @"footer";
}

6、cell的重用

  • cell与ListView的Item中是一样的,它也是要对Item进行重用的
  • 这里的重用主要是用到重用标识符
  • 在cellForRowAtIndexPath方法中改一下cell的创建代码即可
//重用标识符,需要用static修饰,避免多次分配内存给NSString
static NSString *identifier = @"h1";
//从缓存池中取出tableview的item
UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:identifier];
//创建cell
if(nil == cell){
    cell = [[UITableViewCell alloc]initWithStyle:UITableViewCellStyleSubtitle reuseIdentifier:identifier];
}

7、tableView的属性介绍

  1. _tableView.separatorColor:分割线颜色
  2. _tableView.separatorInset:分割线缩进
  3. _tableView.separatorStyle:分割线类型
  4. _tableView.allowsMultipleSelection:允许选项多选
  5. _tableView.tableHeaderView:可以添加一个在头部的View
  6. _tableView.tableFooterView:可以添加一个在底部的View
  7. _tableView.sectionHeaderHeight:每个组的间隔

8、实现cell的点击事件

① 声明委托与交付委托

cell的点击事件是在UITableViewDelegate的实现方法

//声明委托
@interface ViewController ()<UITableViewDataSource,UITableViewDelegate>
//交付委托
_tableView.delegate = self;

② 实现点击事件函数

#pragma UITableViewDelegate委托方法
#pragma 反选数据时调用
-(void)tableView:(UITableView *)tableView didDeselectRowAtIndexPath:(NSIndexPath *)indexPath{

}

#pragma UITableViewDelegate委托方法
#pragma 选择数据时调用
-(void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath{

}

9、实现cell的编辑模式和cell的增加插入

cell的编辑模式和cell的增加插入也是在UITableViewDelegate的实现方法

#pragma UITableViewDelegate委托方法
#pragma 决定哪一行可进入编辑模式
-(BOOL)tableView:(UITableView *)tableView canEditRowAtIndexPath:(NSIndexPath *)indexPath{
    if(indexPath.row == 2){
        return NO;
    }else{
        return YES;
    }
}

#pragma UITableViewDelegate委托方法
#pragma 点击delete和insert的回调函数,该函数同时回开启侧滑删除功能
-(void)tableView:(UITableView *)tableView commitEditingStyle:(UITableViewCellEditingStyle)editingStyle forRowAtIndexPath:(NSIndexPath *)indexPath{
    if(editingStyle == UITableViewCellEditingStyleDelete){
        //删除数组中的数据
        [_dataArray removeObjectAtIndex:indexPath.row];
        //tableview完成删除操作,更新UI
        [_tableView deleteRowsAtIndexPaths:@[indexPath] withRowAnimation:UITableViewRowAnimationLeft];
    }else if(editingStyle == UITableViewCellEditingStyleInsert){
        //模拟添加数据
        HeroModel *hero = [[HeroModel alloc]init];
        hero.name = @"寒冰射手";
        //添加到数组中
        [_dataArray insertObject:hero atIndex:indexPath.row];
        //tableview完成添加操作,更新UI
        [_tableView insertRowsAtIndexPaths:@[indexPath] withRowAnimation:UITableViewRowAnimationRight];
    }
}

#pragma UITableViewDelegate委托方法
#pragma 决定哪一行开启的编辑模式是插入模式还是删除模式
-(UITableViewCellEditingStyle)tableView:(UITableView *)tableView editingStyleForRowAtIndexPath:(NSIndexPath *)indexPath{
    if(indexPath.row <= 5){
        return UITableViewCellEditingStyleInsert;
    }else{
        return UITableViewCellEditingStyleDelete;
    }
}

#pragma UITableViewDelegate委托方法
#pragma 删除模式下的删除按钮文字显示
-(NSString *)tableView:(UITableView *)tableView titleForDeleteConfirmationButtonForRowAtIndexPath:(NSIndexPath *)indexPath{
    return @"蹦瞎卡拉卡";
}

① UITableViewDelegate的委托方法

  1. canEditRowAtIndexPath:允许哪一行开启编辑模式
  2. commitEditingStyle:点击事件的回调,同时开启侧滑删除
  3. editingStyleForRowAtIndexPath:决定哪一行的编辑模式

② indexPath属性

  1. indexPath.row:行的索引
  2. indexPath.section:组的索引

③ 编辑模式动画,大家看名字应该都可以猜得出

  1. UITableViewRowAnimationFade
  2. UITableViewRowAnimationRight
  3. UITableViewRowAnimationLeft
  4. UITableViewRowAnimationTop
  5. UITableViewRowAnimationBottom
  6. UITableViewRowAnimationNone
  7. UITableViewRowAnimationMiddle
  8. UITableViewRowAnimationAutomatic

④ 最后只要开启编辑模式

_tableView.editing = YES;

结语

学习过一次UITableView之后,最遗憾的就是没有能够记住其方法名,只是记住一部分单词而已,当然,这些都是熟能生巧的事情。对于UITableView的知识点还有很多,这里只是其中一部分,后面我会陆续推出UITableView的用法

源码下载

时间: 2024-10-28 11:25:23

iOS基础——通过案例学知识之UITableView(上)的相关文章

iOS基础——通过案例学知识之LaunchScreen、APPIcon、StatusBar、UIScrollView、UIPageControl

iOS基础--通过案例学知识之LaunchScreen.APPIcon.StatusBar.UIScrollView.UIPageControl 今天要实现的案例效果图 一.LaunchScreen 1.设置程序的LaunchScreen 在项目配置文件中配置启动页,并且在LaunchScreen.storyboard中进行布局 2.设置LaunchScreen时间 //单位:秒 [NSThread sleepForTimeInterval:1.5f]; 二.APPIcon 1.命名规则:iOS

iOS基础篇(十三)——UITableView(一)重用机制

UITableView是app开发中常用到的控件,功能很强大,常用于数据的显示.在学习UITableView使用之前,我们先简单了解一下: 1.UITableView的重用机制 UITableView最核心的思想就是UITableViewCell的重用机制,对于一个UITableView而言,可能需要显示成百上千个Cell,如果每个cell都单独创建的话,会消耗很大的内存,为了避免这种情况,重用机制就诞生了. UITableView的重用机制的实现关键在于下面这个的函数:UITableViewC

[iOS基础控件 - 6.0] UITableView

A.需要掌握的 1.基本属性和方法 设置UITableView的dataSource.delegate UITableView多组数据和单组数据的展示 UITableViewCell的常见属性 UITableView的性能优化(cell的循环利用) 自定义cell 2.UITableView的概念 UITableView就是表格数据 UITableView继承自UIScrollView,支持垂直滚动,而且性能好 3.UITableView的两种样式 UITableViewStylePlain U

iOS回顾笔记(07) -- UITableView的使用和性能优化

iOS回顾笔记(07) -- UITableView的使用和性能优化 如果问iOS中最重要的最常用的UI控件是什么,我觉得UITableView当之无愧!似乎所有常规APP都使用到了UITableView.下面就讲一讲UITableView的常用知识和使用原理及性能优化! 1.简介 UITableView故名思议是一种表格控件,是iOS应用中常用的表格控件.常见UITableView如图: UITableView继承于UIScrollview,因此它默认支持垂直滚动(只支持垂直滚动) UITab

iOS基础问答面试题连载(一)-附答案

「Tim的博客」iOS基础问答面试题连载(一)-附答案 「Tim的博客」iOS基础问答面试题连载(二)-附答案 「Tim的博客」iOS基础问答面试题连载(三)-附答案 「Tim的博客」iOS基础问答面试题连载(四) 以下是一些自己收集的比较基础的问题(大神可以忽略),附上答案,方便大家阅读.俗话说得好,基础不牢,地动山摇.文章末尾会提供PDF版的文档,方便大家木有网的时候也可以用移动设备观看. 1.简单的描述下类扩展和分类的区别?(说2点) 类扩展没有名字,分类有名字. 类扩展可以为某个类增加额

ios基础-XCode使用技巧

(一)代码规范pragma mark 1.定义 #pragma 开头的代码是一条编译器指令,是一个特定于程序或编译器的指令.不一定适用于其它编译器或其它环境.如果编译器不能识别该指令,则会将其忽略. 2.作用 在编辑器窗格顶部,方法和函数弹出菜单中将代码分隔开,规范化代码,方便阅读查找. 3.使用 在需要加注释的地方加上#pragma mark - #pragma mark - 视图将要显示的时候 - (void)viewWillAppear:(BOOL)animated { //初始化选号的数

iOS基础问答面试

<简书社区 — Timhbw>iOS基础问答面试题连载(一)-附答案:http://www.jianshu.com/p/1ebf7333808d <简书社区 — Timhbw>iOS基础问答面试题连载(二)-附答案:http://www.jianshu.com/p/ce50261f8907 <简书社区 — Timhbw>iOS基础问答面试题连载(三)-附答案:http://www.jianshu.com/p/5fd65c20912e 以下是一些自己收集的比较基础的问题(

iOS基础 01 构建HelloWorld,剖析并真机测试

iOS基础 01 构建HelloWorld,剖析并真机测试 前言: 从控制台输出HelloWorld是我们学习各种语言的第一步,也是我们人生中非常重要的一步. 多年之后,我希望我们仍能怀有学习上进的心情,继续以HelloWorld去认识这世界上更多的东西. 本篇以HelloWorld作为切入点,向大家系统介绍什么事iOS应用以及如何使用Xcode创建iOS应用. 目录: 1. 创建HelloWorld工程 1.1. 设计界面 1.2. 真机测试 2. Xcode中的iOS工程模板 2.1. Ap

iOS 基础 第二天(0805)

0805 面向对象三大特性 封装.继承和多态 oc的方法都是在运行过程中才会检测的.编译时方法没实现只会出现警告,运行时出错.如果方法实现了但没有声明,运行时对象仍然可以调用方法不会出错.这是OC中弱语法的表现 说白了oc中的弱语法就是因为运行时检测合理性和可用性.编译时不会出错顶多是警告,运行时才警告.这个现象不仅仅体验在方法的声明和实现上,比较好的一个例子是MPMoviePlayerController的截屏通知事件,它需要传入float类型的数组,如果你在编译写了整型不会报错也不会警告,但