核心思想:由于cell是复用的,可以把Cell的个数设置成一个比较大的数。(我的totalNumbPage = 10000*imgUrlArr.count)
- (NSInteger)collectionView:(UICollectionView *)collectionView numberOfItemsInSection:(NSInteger)section {
return self.imgUrlArr.count * 1000;
}
这时候要注意在- (UICollectionViewCell *)collectionView:(UICollectionView *)collectionView cellForItemAtIndexPath:(NSIndexPath *)indexPath拿取图片数据
- (UICollectionViewCell *)collectionView:(UICollectionView *)collectionView cellForItemAtIndexPath:(NSIndexPath *)indexPath {
EBImageCycleViewCell *cell = [collectionView dequeueReusableCellWithReuseIdentifier:EBImageCycleViewCellID forIndexPath:indexPath];
NSInteger index = indexPath.row%self.imgUrlArr.count;//这个是重点,确保拿到的是self.imgUrlArr里面的数据源
id defautImage = self.imgUrlArr[index];
if ([defautImage isKindOfClass:[NSString class]]) {
if ([defautImage hasPrefix:@"http"]) {
[cell.imageView sd_setImageWithURL:[NSURL URLWithString:defautImage] placeholderImage:self.placeHolderImage];
}else {
UIImage *image = [UIImage imageNamed:defautImage];
image = image?image:self.placeHolderImage;
cell.imageView.image = image;
}
}else if ([defautImage isKindOfClass:[UIImage class]]){
cell.imageView.image = defautImage;
}
return cell;
}
接下来就是计时器的实现方法,
- (void)automaticScroll {
if (self.totalNumbPage==0) return;
int currentIndex = self.collectionView.contentOffset.x/self.layout.itemSize.width;
int targetIndex = currentIndex+1;
if (targetIndex==self.totalNumbPage) {
[self.collectionView scrollToItemAtIndexPath:[NSIndexPath indexPathForItem:0 inSection:0] atScrollPosition:UICollectionViewScrollPositionNone animated:NO];
return;
}
[self.collectionView scrollToItemAtIndexPath:[NSIndexPath indexPathForItem:targetIndex inSection:0] atScrollPosition:UICollectionViewScrollPositionNone animated:YES];
}
使用ScrollViewDelegate保证pageControl跟着变化
- (void)scrollViewDidScroll:(UIScrollView *)scrollView {
int itemIndex = (scrollView.contentOffset.x+self.layout.itemSize.width*0.5)/self.layout.itemSize.width;
if (!self.imgUrlArr.count) return;
[self.pageControl setCurrentPage:itemIndex%self.imgUrlArr.count];
}
详细代码:
#import@interface EBImageCycleView : UIView
@property (nonatomic, strong) UIPageControl *pageControl;
@property (nonatomic, strong) UIColor *currentPageTintColor;//当前轮播点的颜色 默认whiteColor
@property (nonatomic, strong) UIColor *defautPageTintColor;//轮播点的颜色 默认grayColor
@property (nonatomic, strong) NSMutableArray *imgUrlArr;//数据数组
@property (nonatomic, assign) int autoScrollTimeInterval;//滑动时间,默认5秒
@property (nonatomic, strong) UIImage *placeHolderImage;//默认背景图片
@property (nonatomic,assign) NSInteger pagecontrolConstBottom;//pagecontrol到底部的距离
- (instancetype)initWithFrame:(CGRect)frame andUrls:(NSMutableArray *)urls andPlaceHolderImage:(UIImage *)image selectAction:(void(^)(NSInteger index))block;
- (void)reloadData;
- (void)setupTimer;
- (void)destoryTimer;
@end
@interface EBImageCycleViewCell : UICollectionViewCell
@property (nonatomic, strong) UIImageView *
@end
.m部分
#import "EBImageCycleView.h"
#import "UIImageView+WebCache.h"
static NSString *const EBImageCycleViewCellID = @"EBImageCycleViewCell";
@interface EBImageCycleView ()
@property (nonatomic, strong) UICollectionView *collectionView;
@property (nonatomic, strong) UICollectionViewFlowLayout *layout;
@property (nonatomic, assign) NSInteger totalNumbPage;//Cell的个数
@property (nonatomic,strong) NSLayoutConstraint *pagecontrolBottomConst;//轮播点到底部的距离
@property (nonatomic,copy) NSTimer *timer;//定时器
//Cell点击的block
@property (nonatomic,copy) void(^selectBlock)(NSInteger index);
@end
@implementation EBImageCycleView
#pragma mark - 给子控件添加约束
- (void)addConstraintToSubviews {
//PageControl的约束
self.pageControl.translatesAutoresizingMaskIntoConstraints = NO;
NSLayoutConstraint *constCenterX = [NSLayoutConstraint constraintWithItem:self.pageControl attribute:NSLayoutAttributeCenterX relatedBy:NSLayoutRelationEqual toItem:self attribute:NSLayoutAttributeCenterX multiplier:1 constant:0];
self.pagecontrolBottomConst = [NSLayoutConstraint constraintWithItem:self.pageControl attribute:NSLayoutAttributeBottom relatedBy:NSLayoutRelationEqual toItem:self attribute:NSLayoutAttributeBottom multiplier:1 constant:0];
[self addConstraint:constCenterX];
[self addConstraint:self.pagecontrolBottomConst];
}
- (UIPageControl *)pageControl {
if (!_pageControl) {
_pageControl = [[UIPageControl alloc] init];
_pageControl.numberOfPages = 0;
_pageControl.currentPage = 0;
_pageControl.pageIndicatorTintColor = self.defautPageTintColor;
_pageControl.currentPageIndicatorTintColor = self.currentPageTintColor;
_pageControl.userInteractionEnabled = NO;
[self addSubview:_pageControl];
}
return _pageControl;
}
- (void)setCurrentPageTintColor:(UIColor *)currentPageTintColor {
if (currentPageTintColor) {
_currentPageTintColor = currentPageTintColor;
}else {
_currentPageTintColor = [UIColor whiteColor];
}
self.pageControl.currentPageIndicatorTintColor = currentPageTintColor;
}
- (void)setDefautPageTintColor:(UIColor *)defautPageTintColor {
if (defautPageTintColor) {
_defautPageTintColor = defautPageTintColor;
}else {
_defautPageTintColor = [UIColor grayColor];
}
self.pageControl.pageIndicatorTintColor = defautPageTintColor;
}
- (void)setTotalNumbPage:(NSInteger)totalNumbPage {
_totalNumbPage = totalNumbPage * 10000;
}
- (void)setImgUrlArr:(NSMutableArray *)imgUrlArr {
_imgUrlArr = imgUrlArr;
self.pageControl.numberOfPages = imgUrlArr.count;
self.pageControl.currentPage = 0;
self.totalNumbPage = imgUrlArr.count;
}
- (UICollectionView *)collectionView {
if (!_collectionView) {
_collectionView = [[UICollectionView alloc] initWithFrame:self.bounds collectionViewLayout:self.layout];
_collectionView.delegate = self;
_collectionView.dataSource = self;
_collectionView.showsVerticalScrollIndicator = NO;
_collectionView.showsHorizontalScrollIndicator = NO;
_collectionView.pagingEnabled = YES;
_collectionView.backgroundColor = [UIColor clearColor];
[self addSubview:_collectionView];
[_collectionView registerClass:[EBImageCycleViewCell class] forCellWithReuseIdentifier:EBImageCycleViewCellID];
}
return _collectionView;
}
- (UICollectionViewFlowLayout *)layout {
if (!_layout) {
_layout = [[UICollectionViewFlowLayout alloc] init];
_layout.minimumLineSpacing = 0.f;
_layout.scrollDirection = UICollectionViewScrollDirectionHorizontal;
_layout.itemSize = self.bounds.size;
}
return _layout;
}
#pragma mark - 创建定时器
- (void)setupTimer {
if (self.timer) {
[self destoryTimer];
}
NSTimer *timer = [NSTimer scheduledTimerWithTimeInterval:self.autoScrollTimeInterval target:self selector:@selector(automaticScroll) userInfo:nil repeats:YES];
_timer = timer;
[[NSRunLoop mainRunLoop] addTimer:timer forMode:NSRunLoopCommonModes];
}
#pragma mark - 销毁定时器
- (void)destoryTimer {
[self.timer invalidate];
self.timer = nil;
}
- (void)automaticScroll {
if (self.totalNumbPage==0) return;
int currentIndex = self.collectionView.contentOffset.x/self.layout.itemSize.width;
int targetIndex = currentIndex+1;
if (targetIndex==self.totalNumbPage) {
[self.collectionView scrollToItemAtIndexPath:[NSIndexPath indexPathForItem:0 inSection:0] atScrollPosition:UICollectionViewScrollPositionNone animated:NO];
return;
}
[self.collectionView scrollToItemAtIndexPath:[NSIndexPath indexPathForItem:targetIndex inSection:0] atScrollPosition:UICollectionViewScrollPositionNone animated:YES];
}
- (instancetype)initWithFrame:(CGRect)frame {
self = [super initWithFrame:frame];
if (self) {
if (self.autoScrollTimeInterval==0) {
self.autoScrollTimeInterval = 5;
}
self.currentPageTintColor = [UIColor whiteColor];
self.defautPageTintColor = [UIColor grayColor];
[self.pageControl setCurrentPage:0];
[self addConstraintToSubviews];
}
return self;
}
- (instancetype)initWithFrame:(CGRect)frame andUrls:(NSMutableArray *)urls andPlaceHolderImage:(UIImage *)image selectAction:(void (^)(NSInteger))block{
EBImageCycleView * cycleView = [[EBImageCycleView alloc] initWithFrame:frame];
cycleView.imgUrlArr = urls;
cycleView.placeHolderImage = image;
[cycleView reloadData];
[cycleView setupTimer];
cycleView.selectBlock = block;
//将pagecontrol提前
[cycleView bringSubviewToFront:cycleView.pageControl];
cycleView.backgroundColor = [UIColor clearColor];
return cycleView;
}
- (void)setPagecontrolConstBottom:(NSInteger)pagecontrolConstBottom {
_pagecontrolConstBottom = pagecontrolConstBottom;
self.pagecontrolBottomConst.constant = pagecontrolConstBottom;
}
- (void)reloadData {
[self.collectionView reloadData];
}
- (NSInteger)numberOfSectionsInCollectionView:(UICollectionView *)collectionView {
return 1;
}
- (NSInteger)collectionView:(UICollectionView *)collectionView numberOfItemsInSection:(NSInteger)section {
return self.imgUrlArr.count * 1000;
}
- (UICollectionViewCell *)collectionView:(UICollectionView *)collectionView cellForItemAtIndexPath:(NSIndexPath *)indexPath {
EBImageCycleViewCell *cell = [collectionView dequeueReusableCellWithReuseIdentifier:EBImageCycleViewCellID forIndexPath:indexPath];
NSInteger index = indexPath.row%self.imgUrlArr.count;
id defautImage = self.imgUrlArr[index];
if ([defautImage isKindOfClass:[NSString class]]) {
if ([defautImage hasPrefix:@"http"]) {
[cell.imageView sd_setImageWithURL:[NSURL URLWithString:defautImage] placeholderImage:self.placeHolderImage];
}else {
UIImage *image = [UIImage imageNamed:defautImage];
image = image?image:self.placeHolderImage;
cell.imageView.image = image;
}
}else if ([defautImage isKindOfClass:[UIImage class]]){
cell.imageView.image = defautImage;
}
return cell;
}
- (void)collectionView:(UICollectionView *)collectionView didSelectItemAtIndexPath:(NSIndexPath *)indexPath {
if (self.selectBlock) {
self.selectBlock(indexPath.row%self.imgUrlArr.count);
}
}
#pragma mark - ScrollViewDelegate
- (void)scrollViewDidScroll:(UIScrollView *)scrollView {
int itemIndex = (scrollView.contentOffset.x+self.layout.itemSize.width*0.5)/self.layout.itemSize.width;
if (!self.imgUrlArr.count) return;
[self.pageControl setCurrentPage:itemIndex%self.imgUrlArr.count];
}
- (void)scrollViewWillBeginDragging:(UIScrollView *)scrollView {
[self destoryTimer];
}
- (void)scrollViewDidEndDragging:(UIScrollView *)scrollView willDecelerate:(BOOL)decelerate {
[self setupTimer];
}
@end
@implementation EBImageCycleViewCell
- (void)addConstraintToSubViews {
self.clipsToBounds = YES;
UIImageView *imageView = self.imageView;
self.imageView.translatesAutoresizingMaskIntoConstraints = NO;
NSString *hVFL = @"H:|-(0)-[imageView]-(0)-|";
NSString *vVFL = @"V:|-(0)-[imageView]-(0)-|";
NSArray *hConsts = [NSLayoutConstraint constraintsWithVisualFormat:hVFL options:0 metrics:nil views:NSDictionaryOfVariableBindings(imageView)];
NSArray *vConsts = [NSLayoutConstraint constraintsWithVisualFormat:vVFL options:0 metrics:nil views:NSDictionaryOfVariableBindings(imageView)];
[self.contentView addConstraints:hConsts];
[self.contentView addConstraints:vConsts];
}
- (UIImageView *)imageView {
if (!_imageView) {
UIImageView *imageView = [UIImageView new];
[self.contentView addSubview:imageView];
_imageView = imageView;
imageView.contentMode = UIViewContentModeScaleToFill;
[self addConstraintToSubViews];
}
return _imageView;
}
@end