美文网首页Android_花式组件,自定义组件
TableView折叠(展开与收起)

TableView折叠(展开与收起)

作者: MixBlog | 来源:发表于2018-07-26 18:41 被阅读504次

    前言:tableView的折叠效果在很多场景上都会使用,类似QQ联系人;下面我们通过对数据模型灵活运用来实现这一功能

    设计思路:

    • 定义数据模型结构
    • 使用sectionHeader为一级分类,tableViewCell为二级分类
    • 字典存储折叠标记(也可以在模型中添加相关标记来实现)

    实现思路:

    1.数据模型定义:

    @class RoomVRecordDetailsModel;
    @interface RoomVRecordModel : BaseModel
    /**
     开启时间
     */
    @property(nonatomic, assign)NSTimeInterval  time;
    /**
     投票名称
     */
    @property(nonatomic, copy)NSString * voteName;
    /**
     总票数
     */
    @property(nonatomic, assign)int  count;
    @property(nonatomic, strong)NSArray <RoomVRecordDetailsModel *> *vote;
    @end
    
    #pragma mark -- 展开之后的子模型
    @interface RoomVRecordDetailsModel : BaseModel
    /**
     id
     */
    @property(nonatomic, assign)int64_t  PlayerId;
    /**
     昵称
     */
    @property(nonatomic, copy)NSString * nickName;
    /**
     头像
     */
    @property(nonatomic, copy)NSString * icon;
    /**
     票数
     */
    @property(nonatomic, assign)NSInteger Vote;
    @end
    

    2.tableView代理实现:

    #pragma mark -- UITableViewDelegate
    -(NSInteger)numberOfSectionsInTableView:(UITableView *)tableView {
        return self.listArray.count;
    }
    
    -(NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section {
        NSNumber *isCheck = [self.cacheDict objectForKey:@(section)];
        if (isCheck.boolValue) {
            RoomVRecordModel * model;
            if (section < self.listArray.count) {
                model = self.listArray[section];
            }
            return model.vote.count+1; //这里的+1根据需求来定夺,楼主这里+1是因为功能中,展开的子模型有个类似表头的cell
        }else {
            return 0;
        }
    }
    
    -(CGFloat)tableView:(UITableView *)tableView heightForHeaderInSection:(NSInteger)section {
        return 50;
    }
    
    -(CGFloat)tableView:(UITableView *)tableView heightForRowAtIndexPath:(NSIndexPath *)indexPath {
        if (indexPath.row == 0) {
            return 40;
        }
        return 50;
    }
    
    -(UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {
        if (indexPath.row == 0) {
            static NSString *identifier2 = @"RoomVoteRecordFormCell";
            RoomVoteRecordFormCell * formCell = [tableView dequeueReusableCellWithIdentifier:identifier2 forIndexPath:indexPath];
            return formCell;
        }
        static NSString *identifier = @"RoomVoteRecordCell";
        RoomVoteRecordCell *cell=[tableView dequeueReusableCellWithIdentifier:identifier forIndexPath:indexPath];
        if (indexPath.section < self.listArray.count) {
            RoomVRecordModel * model = self.listArray[indexPath.section];
            if (indexPath.row <= model.vote.count) {
                RoomVRecordDetailsModel * dModel = model.vote[indexPath.row-1];
                cell.model = dModel;
            }
        }
        return cell;
    }
    
    -(UIView *)tableView:(UITableView *)tableView viewForHeaderInSection:(NSInteger)section {
        static NSString *identifier = @"RoomVoteHeaderView";
        RoomVoteHeaderView * headerView = [tableView dequeueReusableHeaderFooterViewWithIdentifier:identifier];
        if (!headerView) {
            headerView = [[RoomVoteHeaderView alloc] initWithReuseIdentifier:identifier];
        }
        NSNumber *isSelected = [self.cacheDict objectForKey:@(section)];
        headerView.selected = isSelected.boolValue;
        if (section < self.listArray.count) {
            RoomVRecordModel * model = self.listArray[section];
            headerView.model = model;
        }
        [headerView setDidClickHeaderViewBlock:^(RoomVoteHeaderView *header) {
            NSNumber *isCheck = [self.cacheDict objectForKey:@(section)];
            if (isCheck.boolValue) {
                [self.cacheDict setObject:@(NO) forKey:@(section)];
            }else {
                [self.cacheDict setObject:@(YES) forKey:@(section)];
            }
    //        [self.tableView reloadData];
            [tableView reloadSections:[[NSIndexSet alloc] initWithIndex:section] withRowAnimation:UITableViewRowAnimationNone];
        }];
        return headerView;
    }
    

    3.关于字典存储折叠标记:这里添加了一个NSMutableDictionary类型的cacheDict,使用方式已经在上面的tableView的代理方法中体现出来,这样做的好处是在下拉刷新或者上拉加载过程中,都能保留原来用户的折叠记忆情况,提高用户体验;

    -(NSMutableDictionary *)cacheDict {
        if (!_cacheDict) {
            _cacheDict = [NSMutableDictionary dictionary];
        }
        return _cacheDict;
    }
    

    注意事项:

    在简单写完这些代码之后,发现在滑动或者折叠的时候,页面会出现数据刷新不流畅问题,这里通过分析可能与tableView的某个设置/配置有关,通过设置section的预估行高则可以完美解决这个问题,self.tableView.estimatedSectionHeaderHeight = 50;使tableView变得更流畅;

    欢迎看官们点赞评论~~

    相关文章

      网友评论

      本文标题:TableView折叠(展开与收起)

      本文链接:https://www.haomeiwen.com/subject/mvibmftx.html