(iOS)商城筛选

商城筛选的功能的Demo,实现如下功能:【CollectionView】初步展示数据,Section展开/折叠,以及用户选择。

先展示几张Demo界面图
Demo初始界面值
点击选择

分析实现步骤

1.数据
手动创建一个FiltrateItem.plist,如下图展示数据模型结构
plist
2.懒加载初始化CollectionView,字典转模型,设置数据源
- (UICollectionView *)collectionView
{
    if (!_collectionView) {
        UICollectionViewFlowLayout *layout = [UICollectionViewFlowLayout new];
        layout.minimumLineSpacing = 10; //竖间距
        layout.itemSize = CGSizeMake((FiltrateViewScreenW - 6 * 5) / 3, 30);
        _collectionView = [[UICollectionView alloc] initWithFrame:CGRectZero collectionViewLayout:layout];
        _collectionView.delegate = self;
        _collectionView.dataSource = self;
        _collectionView.alwaysBounceVertical = YES;
        _collectionView.frame = CGRectMake(5, 0, FiltrateViewScreenW - DCMargin, ScreenH - 50);
        _collectionView.showsVerticalScrollIndicator = NO;
        
        [_collectionView registerClass:[DCAttributeItemCell class] forCellWithReuseIdentifier:DCAttributeItemCellID];//cell
        [_collectionView registerNib:[UINib nibWithNibName:NSStringFromClass([DCHeaderReusableView class]) bundle:nil] forSupplementaryViewOfKind:UICollectionElementKindSectionHeader withReuseIdentifier:DCHeaderReusableViewID]; //头部
        [_collectionView registerClass:[DCFooterReusableView class] forSupplementaryViewOfKind:UICollectionElementKindSectionFooter withReuseIdentifier:DCFooterReusableViewID]; //尾部
    }
    return _collectionView;
}
#pragma mark - 筛选Item数据
- (void)setUpFiltrateData
{
    _filtrateItem = [DCFiltrateItem mj_objectArrayWithFilename:@"FiltrateItem.plist"];
}

#pragma mark - <UICollectionViewDelegate>
- (NSInteger)collectionView:(UICollectionView *)collectionView numberOfItemsInSection:(NSInteger)section {
    //这里默认第一组品牌展示两行数据其余展示一行数据(3个一行)
    return (_filtrateItem[section].isOpen == YES) ? self.filtrateItem[section].content.count : (section == 0) ? 6 : 3 ;
}

Demo中筛选控制的宽度我定义宏为窗口的宽度*0.8 ,每个Item的宽度为(FiltrateViewScreenW - 6 * 5) / 3,已经手动算上间距 如下图

间距图
#define FiltrateViewScreenW ScreenW * 0.8  //筛选宽宏
layout.itemSize = CGSizeMake((FiltrateViewScreenW - 6 * 5) / 3, 30); //算横间距
layout.minimumLineSpacing = 10; //竖间距

判断是否展开或关闭,判断Item是否点击,模型中加入两个BooL值

/** 用于判断当前cell是否展开 */
@property (nonatomic, assign) BOOL isOpen;
/** 是否点击 */
@property (nonatomic,assign)BOOL isSelect;

在DCAttributeItemCell中创建一个按钮,按钮contentButton尺寸为DCAttributeItemCell的尺寸,根据模型数据的isSelect数据,改变字体,背景颜色等设置,注意一定记得要把按钮的enabled设置为NO,不然点击事件就在按钮上不在DCAttributeItemCell上,didSelectItemAtIndexPath方法也就失效了

#pragma mark - Setter Getter Methods
- (void)setContentItem:(DCContentItem *)contentItem
{
    _contentItem = contentItem;
    [_contentButton setTitle:contentItem.content forState:0];
    
    if (contentItem.isSelect) { //已选
        [_contentButton setImage:[UIImage imageNamed:@"isSelectYes"] forState:0];//钩图片
        [_contentButton setTitleColor:[UIColor redColor] forState:UIControlStateNormal];
        _contentButton.backgroundColor = [UIColor whiteColor];

        [DCSpeedy dc_chageControlCircularWith:self AndSetCornerRadius:3 SetBorderWidth:1 SetBorderColor:[UIColor redColor] canMasksToBounds:YES];
    }else{
        [_contentButton setImage:nil forState:0];
        [_contentButton setTitleColor:[UIColor blackColor] forState:UIControlStateNormal];
        _contentButton.backgroundColor = [UIColor colorWithRed:230/255.0 green:230/255.0 blue:230/255.0 alpha:1.0];
        
        [DCSpeedy dc_chageControlCircularWith:self AndSetCornerRadius:3 SetBorderWidth:1 SetBorderColor:[UIColor clearColor] canMasksToBounds:YES];
    }
}
3.根据模型获取每组选择的数据和最后总获得数据

点击事件,通过模型讲已选的属性加入数组中,这个主意我初始化的数组内部还嵌套了多个数组层次结构类似:@[@[],@[],@[]],这样我们根据内部数组的值来给每个Header赋值

#pragma mark - <UICollectionViewDelegate>
- (void)collectionView:(UICollectionView *)collectionView didSelectItemAtIndexPath:(NSIndexPath *)indexPath
{

    _filtrateItem[indexPath.section].content[indexPath.row].isSelect = !_filtrateItem[indexPath.section].content[indexPath.row].isSelect;
    
    //数组mutableCopy初始化,for循环加数组 结构大致:@[@[],@[]] 如此
    _seleArray = [@[] mutableCopy];
    for (NSInteger i = 0; i < _filtrateItem.count; i++) {
        NSMutableArray *section = [@[] mutableCopy];
        [_seleArray addObject:section];
    }
    
    //把所选的每组Item分别加入每组的数组中
    for (NSInteger i = 0; i < _filtrateItem.count; i++) {
        for (NSInteger j = 0; j < _filtrateItem[i].content.count; j++) {
            if (_filtrateItem[i].content[j].isSelect == YES) {
                [_seleArray[i] addObject:_filtrateItem[i].content[j].content];
            }else{
                [_seleArray[i] removeObject:_filtrateItem[i].content[j].content];
            }
        }
    }
    
    [collectionView reloadData];
    
}

header头部折叠展开点击Block回调和赋值已选属性

__weak typeof(self)weakSelf = self;
headerView.sectionClick = ^{
    weakSelf.filtrateItem[indexPath.section].isOpen = !weakSelf.filtrateItem[indexPath.section].isOpen; //打开取反
    
    [collectionView reloadData]; //刷新
};

//给每组的header的已选label赋值~
NSArray *array = _seleArray[indexPath.section];
NSString *selectName = @"";
for (NSInteger i = 0; i < array.count; i ++ ) {
    if (i == array.count - 1) {
        selectName = [selectName stringByAppendingString:[NSString stringWithFormat:@"%@",array[i]]];
    }else{
        selectName = [selectName stringByAppendingString:[NSString stringWithFormat:@"%@,",array[i]]];
    }
    
}

headerView.selectHeadLabel.text = (selectName.length == 0) ? @"全部" : selectName;
headerView.selectHeadLabel.textColor = ([headerView.selectHeadLabel.text isEqualToString:@"全部"]) ?  [UIColor darkGrayColor] : [UIColor redColor];
4.底部重置,确定点击事件处理
#pragma mark - 点击事件
- (void)bottomButtonClick:(UIButton *)button
{
    if (button.tag == 0) {//重置点击
        for (NSInteger i = 0; i < _filtrateItem.count; i++) {
            for (NSInteger j = 0; j < _filtrateItem[i].content.count; j++) {
                _filtrateItem[i].content[j].isSelect = NO;
                [_seleArray[i] removeAllObjects];
            }
        }
        [self.collectionView reloadData];
    }else if (button.tag == 1){//确定点击
        for (NSInteger i = 0; i < _seleArray.count; i++) {
            NSArray *array = _seleArray[i];
            NSString *selectName = @"";
            for (NSInteger i = 0; i < array.count; i ++ ) {
                if (i == array.count - 1) {
                    selectName = [selectName stringByAppendingString:[NSString stringWithFormat:@"%@",array[i]]];
                }else{
                    selectName = [selectName stringByAppendingString:[NSString stringWithFormat:@"%@,",array[i]]];
                }
                
            }
            if (selectName.length != 0) {
                NSLog(@"已选:第%zd组 的 %@",i,selectName);
            }
        }

    }
}
这样我们商品的筛选就简单的实现了,下面附上一个演示GIF
演示GIF

总结:Demo只是初步展示除电商类APP的筛选功能的思路,近期我将完善下,更新到我的开源电商CDDMall项目上,有需要的可以去GitHub上下载~

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 203,324评论 5 476
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 85,303评论 2 381
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 150,192评论 0 337
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 54,555评论 1 273
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 63,569评论 5 365
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 48,566评论 1 281
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 37,927评论 3 395
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 36,583评论 0 257
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 40,827评论 1 297
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 35,590评论 2 320
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 37,669评论 1 329
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 33,365评论 4 318
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 38,941评论 3 307
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 29,928评论 0 19
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 31,159评论 1 259
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 42,880评论 2 349
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 42,399评论 2 342

推荐阅读更多精彩内容