本文共 13921 字,大约阅读时间需要 46 分钟。
========使用举例==========
/**使用: LYBcollectioview *settingTab=[[LYBcollectioview alloc]initWithFrame:CGRectMake(0, 88, WIDTH, HEIGHT-32-88)]; settingTab.didselectCollectionviecellBlock = ^(NSInteger index, NSString * _Nonnull info) { NSLog(@"点击了第%ld个cell",index); }; settingTab.DictArr=@[@{@"title":@"one", @"imagname":@"one" }, @{@"title":@"one", @"imagname":@"one" }, @{@"title":@"one", @"imagname":@"one" } ]; [self.view addSubview:settingTab]; */#importNS_ASSUME_NONNULL_BEGIN@interface LYBcollectioview : UIView@property(nonatomic,strong)UICollectionView *collec;@property(nonatomic,strong)NSArray *DictArr;@property(nonatomic,copy)void (^didselectCollectionviecellBlock)(NSInteger index,NSString *info);//点击cell回调@endNS_ASSUME_NONNULL_END********************************#import "LYBcollectioview.h"#import "LYBCollectionviewcell.h"#import "LYBcollectionViewSectionHeader.h"#import "LYBcollectionViewSectionFooter.h"@interface LYBcollectioview() @end@implementation LYBcollectioview-(instancetype)initWithFrame:(CGRect)frame{ if(self=[super initWithFrame:frame]){ [self createViews]; } return self;}-(void)createViews{ self.backgroundColor=[UIColor whiteColor]; UICollectionViewFlowLayout *flow=[[UICollectionViewFlowLayout alloc]init]; flow.itemSize=CGSizeMake(100, 100); flow.headerReferenceSize=CGSizeMake([UIScreen mainScreen].bounds.size.width,30);//组头高度 flow.footerReferenceSize=CGSizeMake([UIScreen mainScreen].bounds.size.width,30);//组尾高度 flow.sectionInset=UIEdgeInsetsMake(0, 10, 0, 10);//内缩进 UICollectionView *collect=[[UICollectionView alloc]initWithFrame:CGRectMake(0, 0, [UIScreen mainScreen].bounds.size.width, [UIScreen mainScreen].bounds.size.height) collectionViewLayout:flow]; self.collec=collect; collect.delegate=self; collect.dataSource=self; collect.showsVerticalScrollIndicator=NO; [self addSubview:collect]; collect.backgroundColor=[UIColor whiteColor]; [collect registerClass:[LYBCollectionviewcell class] forCellWithReuseIdentifier:@"LYBCollectionviewcell"];//注册cell [collect registerClass:[LYBcollectionViewSectionHeader class] forSupplementaryViewOfKind:UICollectionElementKindSectionHeader withReuseIdentifier:@"collectionviwHeader"];//注册组头 [collect registerClass:[LYBcollectionViewSectionFooter class] forSupplementaryViewOfKind:UICollectionElementKindSectionFooter withReuseIdentifier:@"collectionviwFoot"];//注册组尾 }-(NSInteger)numberOfSectionsInCollectionView:(UICollectionView *)collectionView{ return 1;}-(NSInteger)collectionView:(UICollectionView *)collectionView numberOfItemsInSection:(NSInteger)section{ return self.DictArr.count;}- (UICollectionViewCell *)collectionView:(UICollectionView *)collectionView cellForItemAtIndexPath:(NSIndexPath *)indexPath{ LYBCollectionviewcell *cell=[collectionView dequeueReusableCellWithReuseIdentifier:@"LYBCollectionviewcell" forIndexPath:indexPath]; [cell setCellWithDict:self.DictArr[indexPath.row]]; return cell;}-(void)collectionView:(UICollectionView *)collectionView didSelectItemAtIndexPath:(NSIndexPath *)indexPath{ self.didselectCollectionviecellBlock(indexPath.row, @"");}//组头或组尾-(UICollectionReusableView *)collectionView:(UICollectionView *)collectionView viewForSupplementaryElementOfKind:(NSString *)kind atIndexPath:(NSIndexPath *)indexPath{ LYBcollectionViewSectionHeader *header; if ([kind isEqual:UICollectionElementKindSectionHeader]){ header=[collectionView dequeueReusableSupplementaryViewOfKind:UICollectionElementKindSectionHeader withReuseIdentifier:@"collectionviwHeader" forIndexPath:indexPath]; }LYBcollectionViewSectionFooter *foot;if ([kind isEqual:UICollectionElementKindSectionFooter]){ foot=[collectionView dequeueReusableSupplementaryViewOfKind:UICollectionElementKindSectionFooter withReuseIdentifier:@"collectionviwFoot" forIndexPath:indexPath]; return foot;} return header;}-(NSArray *)DictArr{ if(nil==_DictArr) { _DictArr=[[NSArray alloc]init]; } return _DictArr;}@end******************************/** collectionviewcell */#import NS_ASSUME_NONNULL_BEGIN@interface LYBCollectionviewcell : UICollectionViewCell-(void)setCellWithDict:(NSDictionary *)dict;@endNS_ASSUME_NONNULL_END****************#import "LYBCollectionviewcell.h"@interface LYBCollectionviewcell()@property(nonatomic,strong)UIImageView *imagV;@property(nonatomic,strong)UILabel *titlelbl;@end@implementation LYBCollectionviewcell-(instancetype)initWithFrame:(CGRect)frame{ if(self=[super initWithFrame:frame]){ [self createviews]; } return self;}-(void)createviews{ UIImageView *imagev=[[UIImageView alloc]initWithFrame:CGRectMake(0, 0, self.frame.size.width, self.frame.size.height*0.7)]; imagev.image=[UIImage imageNamed:@"one"]; [self addSubview:imagev]; self.imagV=imagev; UILabel *titleLbl=[[UILabel alloc]initWithFrame:CGRectMake(0, self.frame.size.height*0.7+10, self.frame.size.width, self.frame.size.height*0.3-10)]; titleLbl.text=@"标题"; titleLbl.textAlignment=NSTextAlignmentCenter; [self addSubview:titleLbl]; self.titlelbl=titleLbl;}-(void)setCellWithDict:(NSDictionary *)dict{ if([[dict allKeys] containsObject:@"imagname"]){ self.imagV.image=[UIImage imageNamed:dict[@"imagname"]]; } if([[dict allKeys]containsObject:@"title"]){ self.titlelbl.text=dict[@"title"]; } }@end********************/** collectionview的组头 */#import NS_ASSUME_NONNULL_BEGIN@interface LYBcollectionViewSectionHeader : UICollectionReusableView@endNS_ASSUME_NONNULL_END************************#import "LYBcollectionViewSectionHeader.h"@implementation LYBcollectionViewSectionHeader-(instancetype)initWithFrame:(CGRect)frame{ if(self=[super initWithFrame:frame]){ [self createviews]; } return self;}-(void)createviews{ self.backgroundColor=[UIColor redColor];}@end*********************/** collectionview的组尾 */#import NS_ASSUME_NONNULL_BEGIN@interface LYBcollectionViewSectionFooter : UICollectionReusableView@endNS_ASSUME_NONNULL_END**************************#import "LYBcollectionViewSectionFooter.h"@implementation LYBcollectionViewSectionFooter-(instancetype)initWithFrame:(CGRect)frame{ if(self=[super initWithFrame:frame]){ [self createviews]; } return self;}-(void)createviews{ self.backgroundColor=[UIColor redColor];}@end
UICollectionViewController的使用详解
// 设置 collectionView 的数据源代理
_collectionView.dataSource =self;
// 修改collectionView的背景色
_collectionView.backgroundColor = [UIColorwhiteColor];
// 隐藏滚动条
_collectionView.showsHorizontalScrollIndicator =NO;
// 设置分页效果
_collectionView.pagingEnabled =YES;
// 设置弹簧效果
_collectionView.bounces = NO;
/**
collectionView 必须有一个 layout
在storyboard上拖拽的时候,已经自动添加一个流水布局
UICollectionView must be initialized with a non-nil layout parameter
*/
/**
实例化一个layout对象
collectionView 如果要使用layout必须在实例化的时候就进行设置
UICollectionViewLayout 是流水布局的父类, 最纯净的layout
UICollectionViewFlowLayout 是在父类上做了一些相应的扩展
*/
UICollectionViewFlowLayout *flowLayout = [[UICollectionViewFlowLayoutalloc]init];
// 修改cell 的大小 ,默认是 50 , 50
flowLayout.itemSize = CGSizeMake(100, 100);
// 修改cell距离view的边距
_flowLayout.sectionInset =UIEdgeInsetsMake(40,10,0,10);
// 修改滚动方向
// _flowLayout.scrollDirection = UICollectionViewScrollDirectionHorizontal;
// 下面两个属性是和滚动方向有关的
// 最小列之间的间距
_flowLayout.minimumInteritemSpacing =50;
// 设置最小行间距
// flowLayout.minimumLineSpacing = 100;
// 实例化一个collectionView
UICollectionView *collectionView = [[UICollectionViewalloc]initWithFrame:self.view.bounds collectionViewLayout:flowLayout];
collectionView.dataSource = self;
// 添加到控制器的view上
[self.viewaddSubview:collectionView];
// 设置背景色
collectionView.backgroundColor = [UIColorwhiteColor];
// 注册一个cell
[collectionView registerClass:[UICollectionViewCellclass]forCellWithReuseIdentifier:identifier];
//通过Nib生成cell,然后注册 Nib的view需要继承 UICollectionViewCell
[self.collectionView registerNib:[UINib nibWithNibName:@"SQCollectionCell" bundle:nil] forCellWithReuseIdentifier:kcellIdentifier];
//+++++++++++++++++
//使用collectionview的header和foot时,自定义的headerview和footview要继承自继承UICollectionReusableView;
//注册headerView Nib的view需要继承UICollectionReusableView
[self.collectionView registerNib:[UINib nibWithNibName:@"SQSupplementaryView" bundle:nil] forSupplementaryViewOfKind:UICollectionElementKindSectionHeader withReuseIdentifier:kheaderIdentifier];
//注册footerView Nib的view需要继承UICollectionReusableView
[self.collectionView registerNib:[UINib nibWithNibName:@"SQSupplementaryView" bundle:nil] forSupplementaryViewOfKind:UICollectionElementKindSectionFooter withReuseIdentifier:kfooterIdentifier];
//+++++++++++++++++
/**
取出 collectionView的 flowlayout
self.collectionViewLayout 只读的
self.collectionView.collectionViewLayout 做一步强转
*/
UICollectionViewFlowLayout *folowLayout = (UICollectionViewFlowLayout *)self.collectionView.collectionViewLayout;
folowLayout.itemSize = CGSizeMake(100, 100);
// Pin 钉住, 类似tableView的悬浮效果
folowLayout.sectionFootersPinToVisibleBounds =YES;
folowLayout.sectionHeadersPinToVisibleBounds =YES;
// 在垂直滚动的时候,设置宽度无效
// 水平滚动的时候,设置高度无效
// folowLayout.headerReferenceSize = CGSizeMake(10, 50);//设置头部宽度
// folowLayout.footerReferenceSize = CGSizeMake(20, 70);
// 取消选中
- (void)collectionView:(UICollectionView *)collectionView didDeselectItemAtIndexPath:(NSIndexPath *)indexPath {
NSLog(@"取消选中 - %ld", indexPath.item);
}
// 被选中
- (void)collectionView:(UICollectionView *)collectionView didSelectItemAtIndexPath:(NSIndexPath *)indexPath {
// item 就相当于row
NSLog(@"%ld", indexPath.item);
}
#pragma mark - 这个方法会反回所有cell的属性设置
// 反回的数组中, 是 UICollectionViewLayoutAttributes 对象, 包含了cell的属性
- (NSArray<UICollectionViewLayoutAttributes *> *)layoutAttributesForElementsInRect:(CGRect)rect {
// 1. 取出所有的item 的 UICollectionViewLayoutAttributes
NSArray *superAttributes = [superlayoutAttributesForElementsInRect:rect];
// 2. 计算出屏幕的中心点, 中心点必须加上 collectionView的偏移量.x
CGFloat screenCenter =self.collectionView.contentOffset.x +self.collectionView.frame.size.width/2;
// 通过循环遍历可以对 item的属性进行修改
for (UICollectionViewLayoutAttributes *itemAttributesin superAttributes) {
// 3. 计算差值 ABS() 取绝对值
CGFloat deltaMargin = ABS(screenCenter - itemAttributes.center.x);
// 4. 计算一个放大比率 , cell 和中心点的距离 和方大的比率成反比
CGFloat scaleDelta = 1.1 - deltaMargin / (self.collectionView.frame.size.width/2 + itemAttributes.size.width);
itemAttributes.transform = CGAffineTransformMakeScale(scaleDelta, scaleDelta);
}
return superAttributes;
}
#pragma mark -
#pragma mark - 当手指离开collectionView的时候会调用
/**
targetContentOffset --- > 最终停留的位置 (进行干预后停留的位置)
ProposedContentOffset ---> 本应该停留的位置
velocity 力度,速度
*/
- (CGPoint)targetContentOffsetForProposedContentOffset:(CGPoint)proposedContentOffset withScrollingVelocity:(CGPoint)velocity {
// 1. 取出屏幕的中心点
CGFloat screenCenter = proposedContentOffset.x +self.collectionView.frame.size.width/2;
// 2. 取出可见范围内的cell
CGRect visibleRect = CGRectZero;
visibleRect.size =self.collectionView.frame.size;
visibleRect.origin = proposedContentOffset;
// 得到的是可见范围内的cell属性集合 调用super的方法,是避免重新计算比率
NSArray *visibleArray = [superlayoutAttributesForElementsInRect:visibleRect];
//定义最小的间距
CGFloat minMargin=MAXFLOAT;
for(UICollectionViewLayoutAttributes *attributesin visibleArray){
//取出cell的中心和屏幕中心的间距
CGFloat delMargin=attributes.center.x-screenCenter;
if (ABS(minMargin)>ABS(delMargin)) {
minMargin=delMargin;
}
}
return CGPointMake(proposedContentOffset.x+minMargin, proposedContentOffset.y);
}
#pragma mark -
#pragma mark - 当屏幕的可见范围发生变化的时候,要重新刷新布局
- (BOOL)shouldInvalidateLayoutForBoundsChange:(CGRect)newBounds {
return YES;
}
#pragma mark -
#pragma mark - 当布局刷新的时候,就会自动调用这个方法
// 建议在这个方法里进行初始化的设置
- (void)prepareLayout {
[superprepareLayout];
// 修改滚动方向
self.scrollDirection =UICollectionViewScrollDirectionHorizontal;
// 取出collectionView的size
CGSize collectionViewSize = self.collectionView.frame.size;
// 设置item的宽高
CGFloat itemWidth = collectionViewSize.height *0.6;
// 设置item的高度
CGFloat itemHeight = collectionViewSize.height *0.8;
// 修改item的size
self.itemSize =CGSizeMake(itemWidth, itemHeight);
// 设置头部和尾部的初始间距
CGFloat margin = collectionViewSize.width/2 - itemWidth/2;
self.sectionInset =UIEdgeInsetsMake(0, margin,0, margin);
}
=============
把collection view 的delegate 由 <UICollectionViewDelegate>换成<UICollectionViewDelegateFlowLayout>并实现
- (CGSize)collectionView:(UICollectionView *)collectionView layout:(UICollectionViewLayout*)collectionViewLayout sizeForItemAtIndexPath:(NSIndexPath *)indexPath {return CGSizeMake(width, height);}
这样就可以实现根据不同的indexpath确定cell的大小.
=========自定义的组头组尾设置,缓存池复用,-----必须先在前面注册
//设置headview
-(UICollectionReusableView*)collectionView:(UICollectionView *)collectionView viewForSupplementaryElementOfKind:(NSString *)kind atIndexPath:(NSIndexPath *)indexPath{
if (indexPath.section == 0) {
SPStoreHeadView* headView;
if ([kindisEqual:UICollectionElementKindSectionHeader]) {
headView = (SPStoreHeadView*)[self.collectionViewdequeueReusableSupplementaryViewOfKind:UICollectionElementKindSectionHeaderwithReuseIdentifier:collectionHeadViewCellIdentifierforIndexPath:indexPath];
//别在这对headView坐标做处理
}
headView.delegate =self;
[headView initDataWithStore:self.store];
return headView;
}else{
SPProduct* product =self.products[indexPath.section];
SPCategoryHeadView* headView;
if ([kindisEqual:UICollectionElementKindSectionHeader]) {
headView = (SPCategoryHeadView*)[self.collectionViewdequeueReusableSupplementaryViewOfKind:UICollectionElementKindSectionHeaderwithReuseIdentifier:collectionTitleViewCellIdentifierforIndexPath:indexPath];
//别在这对headView坐标做处理
}
NSString* title = product.goodsName;
[headView setLabelText:title];
return headView;
}
}
=============
// collec.contentInset=UIEdgeInsetsMake(0, 5, 0,5);/collectionView内偏移
UICollectionViewFlowLayout *layout=[[UICollectionViewFlowLayoutalloc]init];
layout.itemSize=CGSizeMake((WIDTH-20)/3-5, 30);
layout.sectionInset=UIEdgeInsetsMake(5, 5, 0, 25);//组内偏移
转载地址:http://vqlgi.baihongyu.com/