ChainedDroplist 0.1.0

ChainedDroplist 0.1.0

seuzxh维护。



  • 作者
  • seuzxh

ChainedDroplist

链式Droplist,提供基本的DataSource和Delegate封装

尽量做到最大化的Cell扩展

欢迎提交issues和PRs,帮助改进

在最近的项目中,经常遇到下拉/上拉列表(droplist)的需求,共性比较多,但是会有细微的差异;当然首选是用UITableView,但是如果每个droplist都创建个datasourcedelegate,也未免也太麻烦了;所以抽出点时间封装了一个简单的链式Droplist,主要满足以下几种需求:

  • 使用链式编程(在一个方法中完成droplist cell组装、展示、选择的处理)
  • 提供可选的droplist hostview(并不是所有droplist都直接加载在KeyWindow上)
  • 提供可选的tap rotation icon(点击、展示droplist应该伴随着icon的旋转,不是吗?)
  • 提供可选的droplist baseView(droplist应该在点击view的下沿或上沿进行展开)
  • 如果上方/下发展示空间不足,将自动调整展开方向(相信我,虽然用户不在意,但是测试总会遇到这个bug)
  • 默认展示5行,如果展示空间不足,将自动**-1**直至满足展示条件(小屏用户的体验也要考虑)
  • Cell支持可最大化扩展,目前建议使用继承方式(你永远不知道下一个设计师会设计出什么)

先来看个简单的说明:

先看使用方法,有一个基本思路:

- (void)showDroplist:(UIView *)baseView icon:(UIView *)icon hostView:(UIView *)hostView
{
    [[[[[ChainedDroplistView alloc] initWithConfig:^(ChainedDroplistView *droplist) {
        droplist.hostView = self.view; /* 展示droplist的父view,默认为Window */
        droplist.baseView = baseView; /* 用于确定 droplist 的 top/bottom */
        droplist.rotationView = icon; /* 展示droplist的同时做旋转的view */
        droplist.cellHeight = 60; /* 默认Cell height */
        droplist.datas = [self createTestDatas]; /* 创建 cell datas */
    }] registCustomerCellsWithConfig:^(UITableView *tableView) {
        /* 绑定 Cell Identifier */ 
        [tableView registerClass:ChainedDroplistBaseCell.class forCellReuseIdentifier:kChainedDroplistBaseCellIdentifier];
    }] show] /* 调用 show 之后会执行展示动画 */
        processAfterSelected:^(NSInteger index) {
        /* 用户选中某个 Cell 后会执行该 block */
        NSLog(@"U have selected index -> [%@]", @(index));
    }];
    
}

代码结构

基于UITableView封装,通过ChainedDroplistModelProtocolChainedDroplistCellProtocol来关联Cell和Model

ChainedDroplistModelProtocol
  • 提供registerClass:forCellReuseIdentifier:的identifier
  • 可以直接继承ChainedDroplistBaseModel,重写- (NSString *)strCellIdentifier方法提供自定义identifier
Cell
  • configCellWithModel:在每个tableView:cellForRowAtIndexPath:方法中都会调用,该方法可以用于根据model更新Cell

关键代码:

- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
    
    NSInteger index = indexPath.row;
    NSAssert(index < self.cellDatas.count, @"index[%@] beyonds the max count[%@] of datas", @(index), @(self.cellDatas.count));

    // 根据 ChainedDroplistModelProtocol strCellIdentifier 获取指定Cell
    id<ChainedDroplistModelProtocol> model = self.cellDatas[index];
    UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:model.strCellIdentifier];
    NSAssert([cell conformsToProtocol:@protocol(ChainedDroplistCellProtocol)],
             @"cell[%@] from identifier[%@] must conforms protocol [%@]",
             cell, model.strCellIdentifier, NSStringFromProtocol(@protocol(ChainedDroplistCellProtocol)));
    UITableViewCell <ChainedDroplistCellProtocol> * droplistCell = (UITableViewCell <ChainedDroplistCellProtocol> *)cell;
    
    if ([droplistCell respondsToSelector:@selector(configCellWithModel:)]) {
        // 刷新Cell
        [droplistCell configCellWithModel:model];
    }
    
    return droplistCell;
}
  • ChainedDroplistBaseCellinitWithStyle:reuseIdentifier:调用了setupUIsetupConstraints用于设置UI和约束,可以直接继承ChainedDroplistBaseCell,重写setupUIsetupConstraints来完成Customer cell的定义
- (instancetype)initWithStyle:(UITableViewCellStyle)style reuseIdentifier:(NSString *)reuseIdentifier
{
    self = [super initWithStyle:style reuseIdentifier:reuseIdentifier];
    if (self) {
        self.selectionStyle = UITableViewCellSelectionStyleNone;

        [self setupUI];
        [self setupConstraints];
    }
    
    return self;
}

identifier的声明和定义

  • 在Model中通过FOUNDATION_EXPORT NSString *const identifier声明identifier
  • 在Cell中定义相关的identifierNSString *const identifier=@"identifier"

这么做只是为了通过简单的 identifier 搜索就可以找出 cell 和对应的 model

示例

想了解的同学可以参考示例中的使用方法

  1. cd Example/
  2. 运行 pod update --no-repo-update
  3. 打开 ChainedDroplist.xcworkspace/

为了尽可能说明ChainDroplist的设计初衷,示例中列举了比较详细的使用场景,包括:

  1. 默认场景:向下展开,5行可见
  2. 向下展示空间不足:根据 hostViewcellHeight 来计算可视空间,如果下方空间不足会改为向上展示
  3. rotationView用于在展开droplist时做同步旋转
  4. 如果 上方、下方 空间均不足以展示5行,主动计算最少可展示行数并展示
  5. 通过继承 ChainedDroplistBaseCellChainedDroplistBaseModel 来实现自定义样式

需求

安装

ChainedDroplist 通过 CocoaPods 提供使用。要安装它,只需在你的 Podfile 中添加以下行

pod 'ChainedDroplist'

作者

seuzxh, [email protected]

许可协议

ChainedDroplist 在 MIT 许可协议下提供。有关更多信息,请参阅 LICENSE 文件。