文档章节

外卖App双列表联动

杭城小刘
 杭城小刘
发布于 2017/09/24 16:04
字数 820
阅读 13
收藏 0

双列表联动

用过了那么多的外卖App,总结出一个规律,那就是“所有的外卖App都有双列表联动功能”。哈哈哈哈,这是一个玩笑。

这次我也需要开发具有联动效果的双列表。也是首次开发这种类型的UI,记录下步骤与心得

一、关键思路

  • 懒加载左右2个UITableView
  • 根据需要自定义Cell
  • 2个UITableView加载到界面上的时候注意下部剧就好
  • 因为需要联动效果,所有左侧的UITableView一般是大的分类,右边的UITableView一般是大分类小的小分类,所以有了这样的特点
    • 左边的UITableView是只有1个section和n个row
    • 右边的UITableView具有n个section(这里的section 个数恰好是左边UITableView的row数量),且每个section下的row由对应的数据源控制

二、第一版代码

#pragma mark -- UITableViewDelegate
-(NSInteger)numberOfSectionsInTableView:(UITableView *)tableView{
    if (tableView == self.leftTablview) {
        return 1;
    }
    return self.datas.count;
}

-(NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section{
    if (tableView == self.leftTablview) {
        return self.datas.count;
    }
    QuestionCollectionModel *model = self.datas[section];
    NSArray *questions =model.questions;
    return questions.count;
}

-(CGFloat)tableView:(UITableView *)tableView heightForRowAtIndexPath:(NSIndexPath *)indexPath{
    if (tableView == self.leftTablview) {
        return LeftCellHeight;
    }
    return RightCellHeight;
}

-(UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath{
    if (tableView == self.leftTablview) {
        PregnancyPeriodCell *cell = [tableView dequeueReusableCellWithIdentifier:PregnancyPeriodCellID forIndexPath:indexPath];
        if (self.collectionType == CollectionType_Wrong || self.collectionType == CollectionType_Miss) {
            QuestionCollectionModel *model = self.datas[indexPath.row];
            cell.week = model.tag;
        }

        return cell;
    }
    QuestionCell *cell = [tableView dequeueReusableCellWithIdentifier:QuestionCellID forIndexPath:indexPath];
    QuestionCollectionModel *model = self.datas[indexPath.section];
    NSArray *questions =model.questions;
    QuestionModel *questionModel = questions[indexPath.row];
    cell.model = questionModel;
    return cell;
}


-(void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath{
    if (tableView == self.leftTablview) {
        NSIndexPath *indexpath = [NSIndexPath indexPathForRow:0 inSection:indexPath.row];
        [self.rightTableview scrollToRowAtIndexPath:indexpath atScrollPosition:UITableViewScrollPositionTop animated:YES];
    }
}

-(void)scrollViewDidScroll:(UIScrollView *)scrollView{
    if (scrollView == self.rightTableview) {
        NSIndexPath *indexpath = [self.rightTableview indexPathsForVisibleRows].firstObject;
        NSIndexPath *leftScrollIndexpath = [NSIndexPath indexPathForRow:indexpath.section inSection:0];
        [self.leftTablview selectRowAtIndexPath:leftScrollIndexpath animated:YES scrollPosition:UITableViewScrollPositionMiddle];

    }
}

缺陷:虽然实现了效果,但是有缺陷。点击左侧的UITableView,右侧的UITableViewe滚动到相应的位置,这是没问题的,但是滚动

右边,需要根据右边indexPath.section将选中左侧相应的indexPath。这样左侧选中的时候,又会触发右边滚动的事件,整体看上去不是很流畅。

三、解决方案

观察了下,发现右侧滚动的时候左侧会上下选中,所以也就是只要让右侧滚动的时候,左侧的UITableView单方向选中,不要滚动就好,所以由于UITableView也是UIScrollview,所以在scrollViewDidScroll方法中判断右侧的UITableView是向上还是向下滚动,以此作为判断条件来让左侧的UITableView选中相应的行。

且之前是在scrollview代理方法中让左侧的tableview选中,这样子又会触发左侧tableview的选中事件,从而导致右侧的tablview滚动,造成不严谨的联动逻辑

改进后的方法:

  1. 点击左侧的UITableView,在代理方法didSelectRowAtIndexPath中拿到相应的indexPath.row,计算出右侧UITableView需要滚动的indexPath的位置。
     [self.rightTableview scrollToRowAtIndexPath:[NSIndexPath indexPathForRow:0 inSection:indexPath.row] atScrollPosition:UITableViewScrollPositionTop animated:YES];
    
  2. 在willDisplayCell和didEndDisplayingCell代理方法中选中左侧UITableView相应的行。
-(void)tableView:(UITableView *)tableView willDisplayCell:(UITableViewCell *)cell forRowAtIndexPath:(NSIndexPath *)indexPath{

    if (tableView == self.rightTableview  && !self.isScrollDown && self.rightTableview.isDragging ) {
        [self.leftTablview selectRowAtIndexPath:[NSIndexPath indexPathForRow:indexPath.section inSection:0] animated:YES scrollPosition:UITableViewScrollPositionTop];
    }
}



-(void)tableView:(UITableView *)tableView didEndDisplayingCell:(UITableViewCell *)cell forRowAtIndexPath:(NSIndexPath *)indexPath{
    if (tableView == self.rightTableview && self.isScrollDown && self.rightTableview.isDragging) {
        [self.leftTablview selectRowAtIndexPath:[NSIndexPath indexPathForRow:indexPath.section+1 inSection:0] animated:YES scrollPosition:UITableViewScrollPositionTop];

    }
}


- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(nonnull NSIndexPath *)indexPath
{
    if (self.leftTablview == tableView)
    {
        [self.rightTableview scrollToRowAtIndexPath:[NSIndexPath indexPathForRow:0 inSection:indexPath.row] atScrollPosition:UITableViewScrollPositionTop animated:YES];
    }else{
        NSLog(@"嗡嗡嗡");
    }
}


#pragma mark - UIScrollViewDelegate

- (void)scrollViewDidScroll:(UIScrollView *)scrollView{

    static CGFloat lastOffsetY = 0;

    UITableView *tableView = (UITableView *)scrollView;
    if (self.rightTableview == tableView){
        self.isScrollDown = (lastOffsetY < scrollView.contentOffset.y);
        lastOffsetY = scrollView.contentOffset.y;
    }

}
效果图

效果图

附上Demo:Demo

© 著作权归作者所有

共有 人打赏支持
杭城小刘
粉丝 14
博文 109
码字总数 54955
作品 0
杭州
iOS工程师
私信 提问
【iOS开发实战】经典的外卖列表(双Table联动)

我们经常使用美团外卖、饿了么、口碑等外卖软件点餐,几乎所有的外卖软件所展示的商品类别都无一例外,采用双列表的形式呈现,商品的分类,以及对商品的下单操作。我们拿美团外卖为例,截图如...

魔笛GNR
2017/05/05
0
0
WeX5 V3.4 预览版发布,快速开发平台

WeX5_v3.4Pre(Windows/Mac) 下载地址: http://pan.baidu.com/s/1jGZoAMy WeX5 V3.4预览版较抢鲜版做了如下更新: 1、新增com.justep.cordova.plugin.touchid 指纹识别插件,只支持iOS; ...

muyu
2016/03/22
4.3K
6
智察大数据:2018年1月饿了么、美团外卖对比报告

  2017年外卖行业经历了一系列变革。年初各外卖平台迎来大量融资,在业务快速扩张的同时,也引发一系列食品安全问题,国家监管部门迅速应对,陆续推出多项文件规范外卖市场。阿里巴巴集团加...

智察大数据
03/23
0
0
WeX5 快速开发平台 V3.4 正式版发布

WeX5 V3.4 正式版下载地址 http://pan.baidu.com/s/1jHBUDtc WeX5 V3.4正式版发布说明: 1、新增移动端模板32个:包括首页、数据列表、数据展示、注册、登录、搜索等常用单页面模板和完整应用...

muyu
2016/04/01
5.8K
17
Wex5 3.3版本外卖教程

外卖数据交互 外卖概述 第一讲 搭建页面框架 第二讲 开发菜品列表页 第三讲 开发购物车页 第四讲 开发我的信息页 第五讲 开发订单页 第六讲 细节处理 第七讲 开发后端服务 第八讲 在App中支付...

muyu
2016/01/17
688
0

没有更多内容

加载失败,请刷新页面

加载更多

border实现等高布局

效果图 实现上图效果的全部html+css代码 <div class="box"> <nav> <h3 class="nav">导航1</h3> <h3 class="nav">导航2</h3> </nav> <section> <div cla......

呵呵闯
6分钟前
0
0
MaxCompute 表(Table)设计规范

表的限制项 表(Table)设计规范 表设计主要目标 表设计的影响 表设计步骤 表数据存储规范 按数据分层规范数据生命周期 按数据的变更和历史规范数据的保存 数据导入通道与表设计 分区设计与逻辑...

阿里云云栖社区
12分钟前
0
0
局域网共享文件读写的实现方式

首先是设置共享目录,支持用户和密码等权限控制 然后我们可以使用Windows资源管理器操作共享目录下的文件 这中间隐藏了资源管理器帮我们建立目录映射和连接的过程,如果设置了用户名和密码,...

夏至如沫
22分钟前
2
0
Elasticsearch安装与配置

一、Docker安装ES 开发模式 可以使用以下命令快速启动Elasticsearch以进行开发或测试: $ docker run -p 9200:9200 -p 9300:9300 -d --name es -e "discovery.type=single-node" docker.ela...

吴伟祥
28分钟前
1
0
移动页面滚动穿透解决方案(荐)

移动页面滚动穿透解决方法目前有多种解决方案,我介绍下几种方案: 解决方案1:阻止冒泡。 //关键代码$(".sliders,.modals").on("touchmove",function(event){    event.preventDefau...

壹峰
28分钟前
1
0

没有更多内容

加载失败,请刷新页面

加载更多

返回顶部
顶部