多分组多列的不规则布局实现原理(复杂首页布局)

本文介绍了如何使用自定义UICollectionViewLayout来实现包含广告栏、按钮和商品信息展示等元素的复杂首页布局。通过实现prepareLayout、collectionViewContentSize等关键方法,创建私有分类并处理数据初始化,实现多分组多列的不规则布局。最终展示出自定义布局的效果。
摘要由CSDN通过智能技术生成

在常见的UI布局中,往往会含有广告栏banner,按钮,商品信息展示等等元素。例如如下的布局格式

其解决方式优先想到的是采用瀑布流自定义布局去实现类似的布局格式

自定义CollectionViewLayout

自定义CollectionViewLayout需要去实现如下的基础方法

1、prepareLayout预先布局方法

2、collectionViewContentSize 返回collectionView的内容尺寸方法

3、layoutAttributesForElementsInRect:(CGRect)rect 返回可见范围内的所有布局

4、layoutAttributesForItemAtIndexPath:(NSIndexPath *)indexPath 返回某个item的布局属性

5、layoutAttributesForSupplementaryViewOfKind:(NSString *)elementKind atIndexPath:(NSIndexPath *)indexPath 返回附加视图的布局属性

下面直接上代码去实现类似上图的多分组多列的不规则布局

自定义CollectionViewLayout,方法声明文件

#import <UIKit/UIKit.h>
@class CLCollectionViewLayout;
//MARK: 代理方法
@protocol CLCollectionViewLayoutDataSource<NSObject>
@required
/**根据每一个分组返回每个分组中含有多少列数*/
- (NSInteger)collectionView:(UICollectionView *)collectionView layout:(CLCollectionViewLayout *)layout numberOfColumnInSection:(NSInteger)section;
/**返回每一列的高度*/
- (CGFloat)collectionView:(UICollectionView *)collectionView layout:(CLCollectionViewLayout *)layout itemHeight:(CGFloat)height heightForItemAtIndexPath:(NSIndexPath *)indexPath;
@optional
/**返回item之间的行间距*/
- (CGFloat)collectionView:(UICollectionView *)collectionView layout:(CLCollectionViewLayout *)layout minimumLineSpacingForSectionAtIndex:(NSInteger)section;
/**返回item之间的列间距*/
- (CGFloat)collectionView:(UICollectionView *)collectionView layout:(CLCollectionViewLayout *)layout minimumInteritemSpacingForSectionAtIndex:(NSInteger)section;
/**返回每个section附件视图的内容偏移尺寸*/
- (UIEdgeInsets)collectionView:(UICollectionView *)collectionView layout:(CLCollectionViewLayout *)layout insetForSectionAtIndex:(NSInteger)section;
/**返回header的高度*/
- (CGFloat)collectionView:(UICollectionView *)collectionView layout:(CLCollectionViewLayout *)layout referenceHeightForHeaderInSection:(NSInteger)section;
/**返回footer的高度*/
- (CGFloat)collectionView:(UICollectionView *)collectionView layout:(CLCollectionViewLayout *)layout referenceHeightForFooterInSection:(NSInteger)section;
@end

@interface CLCollectionViewLayout : UICollectionViewLayout
/*
 @ dataSource 代理属性
 @ minimumLineSpacing 最小行间距
 @ minimumInteritemSpacing 最小列间距
 @ sectionHeadersPinToVisibleBounds sessionHeader是否可滚动,默认可以滚动
 */
@property (nonatomic,weak) id <CLCollectionViewLayoutDataSource> dataSource;
@property (nonatomic,assign) CGFloat minimumLineSpacing;
@property (nonatomic,assign) CGFloat minimumInteritemSpacing;
@property (nonatomic,assign) BOOL sectionHeadersPinToVisibleBounds;
@end

方法实现文件如下

1、创建私有分类

@interface CLCollectionViewLayout()
@property (nonatomic, strong) 
/*属性数组*/
NSMutableArray<NSMutableArray<UICollectionViewLayoutAttributes *> *> *itemLayoutAttributes;
@property (nonatomic, strong) NSMutableArray<UICollectionViewLayoutAttributes *> *headerLayoutAttributes;
@property (nonatomic, strong) NSMutableArray<UICollectionViewLayoutAttributes *> *footerLayoutAttributes;

/*sessionHeader数组*/
@property (nonatomic, strong) NSMutableArray<NSNumber *> *heightOfSections;
@property (nonatomic, assign) CGFloat contentHeight;
@property (strong, nonatomic) NSMutableArray *shouldanimationArr;
@end

2、数据与集合的初始化

-(void)initData {
    self.contentHeight = 0.0;
    self.itemLayoutAttributes = [[NSMutableArray alloc] init];
    self.headerLayoutAttributes = [[NSMutableArray alloc] init];
    self.footerLayoutAttributes = [[NSMutableArray alloc] init];
    self.heightOfSections = [[NSMutableArray alloc] init];
    self.shouldanimationArr = [[NSMutableArray alloc] init];
}

3、重写prepareLayout方法,在重写此方法之前,我们需要对属性数组和变量进行清空布局属性。

- (void)prepareLayout {
    [super prepareLayout];
    /*断言判断dataSource是否实现*/
    NSAssert(self.dataSource != nil, @"CommonLayout.dat
  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值