├── .gitignore ├── HMCycleView ├── HMCycleView.h └── HMCycleView.m ├── HMCycleViewDemo ├── HMCycleViewDemo.xcodeproj │ ├── project.pbxproj │ └── project.xcworkspace │ │ └── contents.xcworkspacedata └── HMCycleViewDemo │ ├── AppDelegate.h │ ├── AppDelegate.m │ ├── Assets.xcassets │ ├── AppIcon.appiconset │ │ └── Contents.json │ └── Contents.json │ ├── Base.lproj │ ├── LaunchScreen.storyboard │ └── Main.storyboard │ ├── Info.plist │ ├── ViewController.h │ ├── ViewController.m │ ├── main.m │ └── 轮播广告 │ ├── Home_Scroll_01.jpg │ ├── Home_Scroll_02.jpg │ ├── Home_Scroll_03.jpg │ ├── Home_Scroll_04.jpg │ └── Home_Scroll_05.jpg ├── LICENSE └── README.md /.gitignore: -------------------------------------------------------------------------------- 1 | # Xcode 2 | # 3 | # gitignore contributors: remember to update Global/Xcode.gitignore, Objective-C.gitignore & Swift.gitignore 4 | 5 | ## Build generated 6 | build/ 7 | DerivedData 8 | 9 | ## Various settings 10 | *.pbxuser 11 | !default.pbxuser 12 | *.mode1v3 13 | !default.mode1v3 14 | *.mode2v3 15 | !default.mode2v3 16 | *.perspectivev3 17 | !default.perspectivev3 18 | xcuserdata 19 | 20 | ## Other 21 | *.xccheckout 22 | *.moved-aside 23 | *.xcuserstate 24 | *.xcscmblueprint 25 | 26 | ## Obj-C/Swift specific 27 | *.hmap 28 | *.ipa 29 | 30 | # CocoaPods 31 | # 32 | # We recommend against adding the Pods directory to your .gitignore. However 33 | # you should judge for yourself, the pros and cons are mentioned at: 34 | # https://guides.cocoapods.org/using/using-cocoapods.html#should-i-check-the-pods-directory-into-source-control 35 | # 36 | # Pods/ 37 | 38 | # Carthage 39 | # 40 | # Add this line if you want to avoid checking in source code from Carthage dependencies. 41 | # Carthage/Checkouts 42 | 43 | Carthage/Build 44 | 45 | # fastlane 46 | # 47 | # It is recommended to not store the screenshots in the git repo. Instead, use fastlane to re-generate the 48 | # screenshots whenever they are needed. 49 | # For more information about the recommended setup visit: 50 | # https://github.com/fastlane/fastlane/blob/master/docs/Gitignore.md 51 | 52 | fastlane/report.xml 53 | fastlane/screenshots 54 | -------------------------------------------------------------------------------- /HMCycleView/HMCycleView.h: -------------------------------------------------------------------------------- 1 | // 2 | // HMCycleView.h 3 | // HMCycleView 4 | // 5 | // Created by HaoYoson on 16/1/29. 6 | // Copyright © 2016年 YosonHao. All rights reserved. 7 | // 8 | 9 | #import 10 | @class HMCycleView; 11 | 12 | typedef enum : NSUInteger { 13 | HMCycleViewPageControlPositionBottomRight, 14 | HMCycleViewPageControlPositionBottomLeft, 15 | HMCycleViewPageControlPositionBottomCenter, 16 | } HMCycleViewPageControlPosition; 17 | 18 | @protocol HMCycleViewDelegate 19 | 20 | @optional 21 | // 点击事件 - 自己,点击的view,点击的view在数组中的位置。 22 | - (void)cycleView:(HMCycleView *)cycleView didSelectItemAtIndex:(NSInteger)index; 23 | 24 | @end 25 | 26 | @interface HMCycleView : UIView 27 | 28 | // 图片URL地址的数组 29 | @property (nonatomic, strong) NSArray *imageURLs; 30 | 31 | @property (weak, nonatomic) id delegate; 32 | 33 | @property (assign, nonatomic) BOOL showPageControl; 34 | 35 | @property (assign, nonatomic) HMCycleViewPageControlPosition pageControlPosition; 36 | 37 | @property (nonatomic, strong) NSArray *titles; 38 | 39 | @end 40 | -------------------------------------------------------------------------------- /HMCycleView/HMCycleView.m: -------------------------------------------------------------------------------- 1 | // 2 | // HMCycleView.m 3 | // HMCycleView 4 | // 5 | // Created by HaoYoson on 16/1/29. 6 | // Copyright © 2016年 YosonHao. All rights reserved. 7 | // 8 | 9 | #import "HMCycleView.h" 10 | 11 | #pragma mark - HMCycleCell 12 | 13 | @interface HMCycleCell : UICollectionViewCell 14 | 15 | @property (nonatomic, weak) UIImageView *imageView; 16 | 17 | @property (nonatomic, strong) NSURL *imageURL; 18 | 19 | @end 20 | 21 | @implementation HMCycleCell 22 | 23 | - (instancetype)initWithFrame:(CGRect)frame { 24 | self = [super initWithFrame:frame]; 25 | if (self) { 26 | [self setupUI]; 27 | } 28 | return self; 29 | } 30 | 31 | - (void)awakeFromNib { 32 | [self setupUI]; 33 | } 34 | 35 | // set数据的方法 36 | - (void)setImageURL:(NSURL *)imageURL { 37 | _imageURL = imageURL; 38 | 39 | // TODO: cache 40 | self.imageView.image = nil; 41 | 42 | dispatch_async(dispatch_get_global_queue(0, 0), ^{ 43 | NSData *data = [NSData dataWithContentsOfURL:imageURL]; 44 | UIImage *image = [UIImage imageWithData:data]; 45 | 46 | dispatch_async(dispatch_get_main_queue(), ^{ 47 | self.imageView.image = image; 48 | }); 49 | }); 50 | } 51 | 52 | - (void)setupUI { 53 | // 创建imageView显示图片 54 | UIImageView *imageView = [[UIImageView alloc] init]; 55 | 56 | // 把多余的部分剪切掉 57 | imageView.clipsToBounds = YES; 58 | [self.contentView addSubview:imageView]; 59 | 60 | // 自动布局 61 | imageView.translatesAutoresizingMaskIntoConstraints = NO; // 取消 autoresizing 62 | [self.contentView addConstraint:[NSLayoutConstraint constraintWithItem:imageView attribute:NSLayoutAttributeTop relatedBy:NSLayoutRelationEqual toItem:self.contentView attribute:NSLayoutAttributeTop multiplier:1 constant:0]]; 63 | [self.contentView addConstraint:[NSLayoutConstraint constraintWithItem:imageView attribute:NSLayoutAttributeBottom relatedBy:NSLayoutRelationEqual toItem:self.contentView attribute:NSLayoutAttributeBottom multiplier:1 constant:0]]; 64 | [self.contentView addConstraint:[NSLayoutConstraint constraintWithItem:imageView attribute:NSLayoutAttributeLeft relatedBy:NSLayoutRelationEqual toItem:self.contentView attribute:NSLayoutAttributeLeft multiplier:1 constant:0]]; 65 | [self.contentView addConstraint:[NSLayoutConstraint constraintWithItem:imageView attribute:NSLayoutAttributeRight relatedBy:NSLayoutRelationEqual toItem:self.contentView attribute:NSLayoutAttributeRight multiplier:1 constant:0]]; 66 | 67 | self.imageView = imageView; 68 | } 69 | 70 | @end 71 | 72 | #pragma mark - HMCycleFlowLayout 73 | 74 | @interface HMCycleFlowLayout : UICollectionViewFlowLayout 75 | 76 | @end 77 | 78 | @implementation HMCycleFlowLayout 79 | 80 | - (void)prepareLayout { 81 | [super prepareLayout]; 82 | 83 | self.itemSize = self.collectionView.bounds.size; 84 | 85 | // 间距 86 | self.minimumLineSpacing = 0; 87 | self.minimumInteritemSpacing = 0; 88 | 89 | // 滚动方法 90 | self.scrollDirection = UICollectionViewScrollDirectionHorizontal; 91 | } 92 | 93 | @end 94 | 95 | #pragma mark - NSTimer (Addition) 96 | 97 | @interface NSTimer (Addition) 98 | 99 | /** 100 | * 暂定当前时间对象 101 | */ 102 | - (void)pauseTimer; 103 | 104 | /** 105 | * 当前时间对象 106 | */ 107 | - (void)resumeTimer; 108 | 109 | /** 110 | * 一定时间后恢复定时器对象 111 | * 112 | * @param interval 时间 113 | */ 114 | - (void)resumeTimerAfterTimeInterval:(NSTimeInterval)interval; 115 | @end 116 | 117 | @implementation NSTimer (Addition) 118 | 119 | - (void)pauseTimer { 120 | if (![self isValid]) { 121 | return; 122 | } 123 | [self setFireDate:[NSDate distantFuture]]; 124 | } 125 | 126 | - (void)resumeTimer { 127 | if (![self isValid]) { 128 | return; 129 | } 130 | [self setFireDate:[NSDate date]]; 131 | } 132 | 133 | - (void)resumeTimerAfterTimeInterval:(NSTimeInterval)interval { 134 | if (![self isValid]) { 135 | return; 136 | } 137 | [self setFireDate:[NSDate dateWithTimeIntervalSinceNow:interval]]; 138 | } 139 | 140 | @end 141 | 142 | #pragma mark - HMCycleView 143 | 144 | #define kSeed 99 145 | 146 | // 标示符 147 | static NSString *const reuseIdentifier = @"cycle_cell"; 148 | 149 | @interface HMCycleView () 150 | 151 | @property (nonatomic, weak) UICollectionView *collectionView; 152 | 153 | @property (nonatomic, weak) UIPageControl *pageControl; 154 | 155 | @property (nonatomic, strong) NSTimer *timer; 156 | 157 | @property (weak, nonatomic) UILabel *titleLabel; 158 | 159 | @end 160 | 161 | @implementation HMCycleView 162 | 163 | - (instancetype)initWithFrame:(CGRect)frame { 164 | self = [super initWithFrame:frame]; 165 | if (self) { 166 | [self setupUI]; 167 | } 168 | return self; 169 | } 170 | 171 | - (void)awakeFromNib { 172 | [self setupUI]; 173 | } 174 | 175 | - (void)setupUI { 176 | // 子控件 177 | HMCycleFlowLayout *layout = [[HMCycleFlowLayout alloc] init]; 178 | UICollectionView *collectionView = [[UICollectionView alloc] initWithFrame:CGRectZero collectionViewLayout:layout]; 179 | // 设置数据源和代理 180 | collectionView.dataSource = self; 181 | collectionView.delegate = self; 182 | // 注册单元格 183 | [collectionView registerClass:[HMCycleCell class] forCellWithReuseIdentifier:reuseIdentifier]; 184 | 185 | // 设置分页 186 | collectionView.pagingEnabled = YES; 187 | // 取消弹性效果 188 | collectionView.bounces = NO; 189 | // 取消指示器 190 | collectionView.showsVerticalScrollIndicator = NO; 191 | collectionView.showsHorizontalScrollIndicator = NO; 192 | // 添加到视图上 193 | [self addSubview:collectionView]; 194 | 195 | UIPageControl *pageControl = [[UIPageControl alloc] init]; 196 | pageControl.currentPageIndicatorTintColor = [UIColor yellowColor]; 197 | pageControl.pageIndicatorTintColor = [UIColor blueColor]; 198 | pageControl.userInteractionEnabled = NO; 199 | [self addSubview:pageControl]; 200 | 201 | // cover和title 202 | UIView *coverView = [[UIView alloc] init]; 203 | coverView.backgroundColor = [UIColor colorWithWhite:0 alpha:.5]; 204 | [self addSubview:coverView]; 205 | UILabel *titleLabel = [[UILabel alloc] init]; 206 | titleLabel.textColor = [UIColor whiteColor]; 207 | titleLabel.font = [UIFont systemFontOfSize:15]; 208 | [self addSubview:titleLabel]; 209 | 210 | // 自动布局 211 | collectionView.translatesAutoresizingMaskIntoConstraints = NO; // 取消 autoresizing 212 | [self addConstraint:[NSLayoutConstraint constraintWithItem:collectionView attribute:NSLayoutAttributeTop relatedBy:NSLayoutRelationEqual toItem:self attribute:NSLayoutAttributeTop multiplier:1 constant:0]]; 213 | [self addConstraint:[NSLayoutConstraint constraintWithItem:collectionView attribute:NSLayoutAttributeBottom relatedBy:NSLayoutRelationEqual toItem:self attribute:NSLayoutAttributeBottom multiplier:1 constant:0]]; 214 | [self addConstraint:[NSLayoutConstraint constraintWithItem:collectionView attribute:NSLayoutAttributeLeft relatedBy:NSLayoutRelationEqual toItem:self attribute:NSLayoutAttributeLeft multiplier:1 constant:0]]; 215 | [self addConstraint:[NSLayoutConstraint constraintWithItem:collectionView attribute:NSLayoutAttributeRight relatedBy:NSLayoutRelationEqual toItem:self attribute:NSLayoutAttributeRight multiplier:1 constant:0]]; 216 | 217 | // 自动布局 218 | pageControl.translatesAutoresizingMaskIntoConstraints = NO; // 取消 autoresizing 219 | [self addConstraint:[NSLayoutConstraint constraintWithItem:pageControl attribute:NSLayoutAttributeRight relatedBy:NSLayoutRelationEqual toItem:self attribute:NSLayoutAttributeRight multiplier:1 constant:-16]]; 220 | [self addConstraint:[NSLayoutConstraint constraintWithItem:pageControl attribute:NSLayoutAttributeBottom relatedBy:NSLayoutRelationEqual toItem:self attribute:NSLayoutAttributeBottom multiplier:1 constant:0]]; 221 | 222 | // coverView自动布局 223 | coverView.translatesAutoresizingMaskIntoConstraints = NO; // 取消 autoresizing 224 | [self addConstraint:[NSLayoutConstraint constraintWithItem:coverView attribute:NSLayoutAttributeHeight relatedBy:NSLayoutRelationEqual toItem:pageControl attribute:NSLayoutAttributeHeight multiplier:1 constant:0]]; 225 | [self addConstraint:[NSLayoutConstraint constraintWithItem:coverView attribute:NSLayoutAttributeBottom relatedBy:NSLayoutRelationEqual toItem:self attribute:NSLayoutAttributeBottom multiplier:1 constant:0]]; 226 | [self addConstraint:[NSLayoutConstraint constraintWithItem:coverView attribute:NSLayoutAttributeLeft relatedBy:NSLayoutRelationEqual toItem:self attribute:NSLayoutAttributeLeft multiplier:1 constant:0]]; 227 | [self addConstraint:[NSLayoutConstraint constraintWithItem:coverView attribute:NSLayoutAttributeRight relatedBy:NSLayoutRelationEqual toItem:self attribute:NSLayoutAttributeRight multiplier:1 constant:0]]; 228 | 229 | titleLabel.translatesAutoresizingMaskIntoConstraints = NO; // 取消 autoresizing 230 | [self addConstraint:[NSLayoutConstraint constraintWithItem:titleLabel attribute:NSLayoutAttributeHeight relatedBy:NSLayoutRelationEqual toItem:pageControl attribute:NSLayoutAttributeHeight multiplier:1 constant:0]]; 231 | [self addConstraint:[NSLayoutConstraint constraintWithItem:titleLabel attribute:NSLayoutAttributeBottom relatedBy:NSLayoutRelationEqual toItem:self attribute:NSLayoutAttributeBottom multiplier:1 constant:0]]; 232 | [self addConstraint:[NSLayoutConstraint constraintWithItem:titleLabel attribute:NSLayoutAttributeLeft relatedBy:NSLayoutRelationEqual toItem:self attribute:NSLayoutAttributeLeft multiplier:1 constant:16]]; 233 | [self addConstraint:[NSLayoutConstraint constraintWithItem:titleLabel attribute:NSLayoutAttributeRight relatedBy:NSLayoutRelationEqual toItem:self attribute:NSLayoutAttributeRight multiplier:1 constant:-16]]; 234 | 235 | self.collectionView = collectionView; 236 | self.pageControl = pageControl; 237 | self.titleLabel = titleLabel; 238 | 239 | [self bringSubviewToFront:pageControl]; 240 | } 241 | 242 | - (void)setShowPageControl:(BOOL)showPageControl { 243 | _showPageControl = showPageControl; 244 | 245 | self.pageControl.hidden = !showPageControl; 246 | } 247 | 248 | - (void)setPageControlPosition:(HMCycleViewPageControlPosition)pageControlPosition { 249 | _pageControlPosition = pageControlPosition; 250 | 251 | // 删除之前默认的右下角约束 252 | for (int i = 0; i < self.constraints.count; i++) { 253 | NSLayoutConstraint *constraint = self.constraints[i]; 254 | if (constraint.firstItem == self.pageControl) { 255 | [self removeConstraint:constraint]; 256 | } 257 | } 258 | 259 | switch (self.pageControlPosition) { 260 | case HMCycleViewPageControlPositionBottomCenter: 261 | [self addConstraint:[NSLayoutConstraint constraintWithItem:self.pageControl attribute:NSLayoutAttributeCenterX relatedBy:NSLayoutRelationEqual toItem:self attribute:NSLayoutAttributeCenterX multiplier:1 constant:0]]; 262 | [self addConstraint:[NSLayoutConstraint constraintWithItem:self.pageControl attribute:NSLayoutAttributeBottom relatedBy:NSLayoutRelationEqual toItem:self attribute:NSLayoutAttributeBottom multiplier:1 constant:0]]; 263 | break; 264 | case HMCycleViewPageControlPositionBottomLeft: 265 | [self addConstraint:[NSLayoutConstraint constraintWithItem:self.pageControl attribute:NSLayoutAttributeLeft relatedBy:NSLayoutRelationEqual toItem:self attribute:NSLayoutAttributeLeft multiplier:1 constant:16]]; 266 | [self addConstraint:[NSLayoutConstraint constraintWithItem:self.pageControl attribute:NSLayoutAttributeBottom relatedBy:NSLayoutRelationEqual toItem:self attribute:NSLayoutAttributeBottom multiplier:1 constant:0]]; 267 | break; 268 | case HMCycleViewPageControlPositionBottomRight: 269 | [self addConstraint:[NSLayoutConstraint constraintWithItem:self.pageControl attribute:NSLayoutAttributeRight relatedBy:NSLayoutRelationEqual toItem:self attribute:NSLayoutAttributeRight multiplier:1 constant:-16]]; 270 | [self addConstraint:[NSLayoutConstraint constraintWithItem:self.pageControl attribute:NSLayoutAttributeBottom relatedBy:NSLayoutRelationEqual toItem:self attribute:NSLayoutAttributeBottom multiplier:1 constant:0]]; 271 | break; 272 | 273 | default: 274 | break; 275 | } 276 | } 277 | 278 | // 当图片数据传过来的时候一定会调用这个方法 279 | - (void)setImageURLs:(NSArray *)imageURLs { 280 | _imageURLs = imageURLs; 281 | 282 | // 刷新数据(重新加载数据源) 283 | [self.collectionView reloadData]; 284 | 285 | // 设置pageControl的总页数 286 | self.pageControl.numberOfPages = imageURLs.count; 287 | } 288 | 289 | // 已经显示 290 | - (void)didMoveToWindow { 291 | [super didMoveToWindow]; 292 | 293 | [self layoutIfNeeded]; 294 | NSIndexPath *indexPath = [NSIndexPath indexPathForItem:self.imageURLs.count * kSeed inSection:0]; 295 | [self.collectionView scrollToItemAtIndexPath:indexPath atScrollPosition:UICollectionViewScrollPositionLeft animated:NO]; 296 | 297 | // 设置一个时钟装置 创建一个计时器对象 把这个计时器添加到运行循环当中 298 | [[NSRunLoop currentRunLoop] addTimer:self.timer forMode:NSRunLoopCommonModes]; 299 | 300 | if (self.pageControlPosition == HMCycleViewPageControlPositionBottomLeft) { 301 | self.titleLabel.textAlignment = NSTextAlignmentRight; 302 | } 303 | } 304 | 305 | - (void)updateTimer { 306 | // 获取当前的位置 307 | // 这个方法 表示 获取当前collectionView多有可见的cell的位置(indexPath) 308 | // 因为就我们这个轮播器而言,当前可见的cell只有一个,所以可以根据last 或者 first 或者 [0] 来获取 309 | NSIndexPath *indexPath = [self.collectionView indexPathsForVisibleItems].lastObject; 310 | 311 | // 根据当前页 创建下一页的位置 312 | NSIndexPath *nextPath = [NSIndexPath indexPathForItem:indexPath.item + 1 inSection:indexPath.section]; 313 | 314 | [self.collectionView scrollToItemAtIndexPath:nextPath atScrollPosition:UICollectionViewScrollPositionLeft animated:YES]; 315 | } 316 | 317 | // 开始拖拽 318 | - (void)scrollViewWillBeginDragging:(UIScrollView *)scrollView { 319 | [self.timer pauseTimer]; 320 | } 321 | 322 | // 结束拖拽 323 | - (void)scrollViewDidEndDragging:(UIScrollView *)scrollView willDecelerate:(BOOL)decelerate { 324 | [self.timer resumeTimerAfterTimeInterval:2]; 325 | } 326 | 327 | // 滚动动画结束的时候调用 328 | - (void)scrollViewDidEndScrollingAnimation:(UIScrollView *)scrollView { 329 | // 手动调用减速完成的方法 330 | [self scrollViewDidEndDecelerating:self.collectionView]; 331 | } 332 | 333 | // 监听手动减速完成(停止滚动) 334 | - (void)scrollViewDidEndDecelerating:(UIScrollView *)scrollView { 335 | // x 偏移量 336 | CGFloat offsetX = scrollView.contentOffset.x; 337 | // 计算页数 338 | NSInteger page = offsetX / self.bounds.size.width; 339 | 340 | // 获取某一组有多少行 341 | NSInteger itemsCount = [self.collectionView numberOfItemsInSection:0]; 342 | 343 | if (page == 0) { // 第一页 344 | self.collectionView.contentOffset = CGPointMake(offsetX + self.imageURLs.count * kSeed * self.bounds.size.width, 0); 345 | } else if (page == itemsCount - 1) { // 最后一页 346 | self.collectionView.contentOffset = CGPointMake(offsetX - self.imageURLs.count * kSeed * self.bounds.size.width, 0); 347 | } 348 | } 349 | 350 | - (void)scrollViewDidScroll:(UIScrollView *)scrollView { 351 | CGFloat offsetX = scrollView.contentOffset.x; 352 | 353 | CGFloat page = offsetX / self.bounds.size.width + 0.5; 354 | page = (NSInteger)page % self.imageURLs.count; 355 | self.pageControl.currentPage = page; 356 | 357 | if (self.titles.count) { 358 | if (self.titles.count < self.imageURLs.count) { 359 | NSMutableArray *tempStrings = [NSMutableArray array]; 360 | 361 | for (int i = 0; i < self.imageURLs.count; i++) { 362 | if (i > self.titles.count - 1) { 363 | [tempStrings addObject:@""]; 364 | continue; 365 | } 366 | [tempStrings addObject:self.titles[i]]; 367 | } 368 | self.titles = tempStrings.copy; 369 | } 370 | self.titleLabel.text = self.titles[(NSInteger)page]; 371 | } 372 | } 373 | 374 | - (NSInteger)collectionView:(UICollectionView *)collectionView numberOfItemsInSection:(NSInteger)section { 375 | return self.imageURLs.count * 2 * kSeed; 376 | } 377 | 378 | - (UICollectionViewCell *)collectionView:(UICollectionView *)collectionView cellForItemAtIndexPath:(NSIndexPath *)indexPath { 379 | HMCycleCell *cell = [collectionView dequeueReusableCellWithReuseIdentifier:reuseIdentifier forIndexPath:indexPath]; 380 | cell.imageURL = self.imageURLs[indexPath.item % self.imageURLs.count]; 381 | return cell; 382 | } 383 | 384 | - (void)collectionView:(UICollectionView *)collectionView didSelectItemAtIndexPath:(NSIndexPath *)indexPath { 385 | if ([self.delegate respondsToSelector:@selector(cycleView:didSelectItemAtIndex:)]) { 386 | [self.delegate cycleView:self didSelectItemAtIndex:indexPath.item % self.imageURLs.count]; 387 | } 388 | } 389 | 390 | - (void)removeFromSuperview { 391 | [super removeFromSuperview]; 392 | [self.timer invalidate]; 393 | } 394 | 395 | - (NSTimer *)timer { 396 | if (!_timer) { 397 | NSTimer *timer = [NSTimer timerWithTimeInterval:2 target:self selector:@selector(updateTimer) userInfo:nil repeats:YES]; 398 | _timer = timer; 399 | } 400 | return _timer; 401 | } 402 | 403 | @end 404 | -------------------------------------------------------------------------------- /HMCycleViewDemo/HMCycleViewDemo.xcodeproj/project.pbxproj: -------------------------------------------------------------------------------- 1 | // !$*UTF8*$! 2 | { 3 | archiveVersion = 1; 4 | classes = { 5 | }; 6 | objectVersion = 46; 7 | objects = { 8 | 9 | /* Begin PBXBuildFile section */ 10 | 46A80DCC1D5200F10072D35A /* Home_Scroll_01.jpg in Resources */ = {isa = PBXBuildFile; fileRef = 46A80DC71D5200F10072D35A /* Home_Scroll_01.jpg */; }; 11 | 46A80DCD1D5200F10072D35A /* Home_Scroll_02.jpg in Resources */ = {isa = PBXBuildFile; fileRef = 46A80DC81D5200F10072D35A /* Home_Scroll_02.jpg */; }; 12 | 46A80DCE1D5200F10072D35A /* Home_Scroll_03.jpg in Resources */ = {isa = PBXBuildFile; fileRef = 46A80DC91D5200F10072D35A /* Home_Scroll_03.jpg */; }; 13 | 46A80DCF1D5200F10072D35A /* Home_Scroll_04.jpg in Resources */ = {isa = PBXBuildFile; fileRef = 46A80DCA1D5200F10072D35A /* Home_Scroll_04.jpg */; }; 14 | 46A80DD01D5200F10072D35A /* Home_Scroll_05.jpg in Resources */ = {isa = PBXBuildFile; fileRef = 46A80DCB1D5200F10072D35A /* Home_Scroll_05.jpg */; }; 15 | 46BA88AF1C61F70B00FC4320 /* main.m in Sources */ = {isa = PBXBuildFile; fileRef = 46BA88AE1C61F70B00FC4320 /* main.m */; }; 16 | 46BA88B21C61F70B00FC4320 /* AppDelegate.m in Sources */ = {isa = PBXBuildFile; fileRef = 46BA88B11C61F70B00FC4320 /* AppDelegate.m */; }; 17 | 46BA88B51C61F70B00FC4320 /* ViewController.m in Sources */ = {isa = PBXBuildFile; fileRef = 46BA88B41C61F70B00FC4320 /* ViewController.m */; }; 18 | 46BA88B81C61F70B00FC4320 /* Main.storyboard in Resources */ = {isa = PBXBuildFile; fileRef = 46BA88B61C61F70B00FC4320 /* Main.storyboard */; }; 19 | 46BA88BA1C61F70B00FC4320 /* Assets.xcassets in Resources */ = {isa = PBXBuildFile; fileRef = 46BA88B91C61F70B00FC4320 /* Assets.xcassets */; }; 20 | 46BA88BD1C61F70B00FC4320 /* LaunchScreen.storyboard in Resources */ = {isa = PBXBuildFile; fileRef = 46BA88BB1C61F70B00FC4320 /* LaunchScreen.storyboard */; }; 21 | 46BA88D11C620EF000FC4320 /* HMCycleView.m in Sources */ = {isa = PBXBuildFile; fileRef = 46BA88D01C620EF000FC4320 /* HMCycleView.m */; }; 22 | /* End PBXBuildFile section */ 23 | 24 | /* Begin PBXFileReference section */ 25 | 46A80DC71D5200F10072D35A /* Home_Scroll_01.jpg */ = {isa = PBXFileReference; lastKnownFileType = image.jpeg; path = Home_Scroll_01.jpg; sourceTree = ""; }; 26 | 46A80DC81D5200F10072D35A /* Home_Scroll_02.jpg */ = {isa = PBXFileReference; lastKnownFileType = image.jpeg; path = Home_Scroll_02.jpg; sourceTree = ""; }; 27 | 46A80DC91D5200F10072D35A /* Home_Scroll_03.jpg */ = {isa = PBXFileReference; lastKnownFileType = image.jpeg; path = Home_Scroll_03.jpg; sourceTree = ""; }; 28 | 46A80DCA1D5200F10072D35A /* Home_Scroll_04.jpg */ = {isa = PBXFileReference; lastKnownFileType = image.jpeg; path = Home_Scroll_04.jpg; sourceTree = ""; }; 29 | 46A80DCB1D5200F10072D35A /* Home_Scroll_05.jpg */ = {isa = PBXFileReference; lastKnownFileType = image.jpeg; path = Home_Scroll_05.jpg; sourceTree = ""; }; 30 | 46BA88AA1C61F70B00FC4320 /* HMCycleViewDemo.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = HMCycleViewDemo.app; sourceTree = BUILT_PRODUCTS_DIR; }; 31 | 46BA88AE1C61F70B00FC4320 /* main.m */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.objc; path = main.m; sourceTree = ""; }; 32 | 46BA88B01C61F70B00FC4320 /* AppDelegate.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = AppDelegate.h; sourceTree = ""; }; 33 | 46BA88B11C61F70B00FC4320 /* AppDelegate.m */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.objc; path = AppDelegate.m; sourceTree = ""; }; 34 | 46BA88B31C61F70B00FC4320 /* ViewController.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = ViewController.h; sourceTree = ""; }; 35 | 46BA88B41C61F70B00FC4320 /* ViewController.m */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.objc; path = ViewController.m; sourceTree = ""; }; 36 | 46BA88B71C61F70B00FC4320 /* Base */ = {isa = PBXFileReference; lastKnownFileType = file.storyboard; name = Base; path = Base.lproj/Main.storyboard; sourceTree = ""; }; 37 | 46BA88B91C61F70B00FC4320 /* Assets.xcassets */ = {isa = PBXFileReference; lastKnownFileType = folder.assetcatalog; path = Assets.xcassets; sourceTree = ""; }; 38 | 46BA88BC1C61F70B00FC4320 /* Base */ = {isa = PBXFileReference; lastKnownFileType = file.storyboard; name = Base; path = Base.lproj/LaunchScreen.storyboard; sourceTree = ""; }; 39 | 46BA88BE1C61F70B00FC4320 /* Info.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist.xml; path = Info.plist; sourceTree = ""; }; 40 | 46BA88CF1C620EF000FC4320 /* HMCycleView.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = HMCycleView.h; sourceTree = ""; }; 41 | 46BA88D01C620EF000FC4320 /* HMCycleView.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = HMCycleView.m; sourceTree = ""; }; 42 | /* End PBXFileReference section */ 43 | 44 | /* Begin PBXFrameworksBuildPhase section */ 45 | 46BA88A71C61F70B00FC4320 /* Frameworks */ = { 46 | isa = PBXFrameworksBuildPhase; 47 | buildActionMask = 2147483647; 48 | files = ( 49 | ); 50 | runOnlyForDeploymentPostprocessing = 0; 51 | }; 52 | /* End PBXFrameworksBuildPhase section */ 53 | 54 | /* Begin PBXGroup section */ 55 | 46A80DC61D5200F10072D35A /* 轮播广告 */ = { 56 | isa = PBXGroup; 57 | children = ( 58 | 46A80DC71D5200F10072D35A /* Home_Scroll_01.jpg */, 59 | 46A80DC81D5200F10072D35A /* Home_Scroll_02.jpg */, 60 | 46A80DC91D5200F10072D35A /* Home_Scroll_03.jpg */, 61 | 46A80DCA1D5200F10072D35A /* Home_Scroll_04.jpg */, 62 | 46A80DCB1D5200F10072D35A /* Home_Scroll_05.jpg */, 63 | ); 64 | path = "轮播广告"; 65 | sourceTree = ""; 66 | }; 67 | 46BA88A11C61F70B00FC4320 = { 68 | isa = PBXGroup; 69 | children = ( 70 | 46BA88AC1C61F70B00FC4320 /* HMCycleViewDemo */, 71 | 46BA88AB1C61F70B00FC4320 /* Products */, 72 | ); 73 | sourceTree = ""; 74 | }; 75 | 46BA88AB1C61F70B00FC4320 /* Products */ = { 76 | isa = PBXGroup; 77 | children = ( 78 | 46BA88AA1C61F70B00FC4320 /* HMCycleViewDemo.app */, 79 | ); 80 | name = Products; 81 | sourceTree = ""; 82 | }; 83 | 46BA88AC1C61F70B00FC4320 /* HMCycleViewDemo */ = { 84 | isa = PBXGroup; 85 | children = ( 86 | 46BA88CE1C620EF000FC4320 /* HMCycleView */, 87 | 46A80DC61D5200F10072D35A /* 轮播广告 */, 88 | 46BA88B01C61F70B00FC4320 /* AppDelegate.h */, 89 | 46BA88B11C61F70B00FC4320 /* AppDelegate.m */, 90 | 46BA88B31C61F70B00FC4320 /* ViewController.h */, 91 | 46BA88B41C61F70B00FC4320 /* ViewController.m */, 92 | 46BA88B61C61F70B00FC4320 /* Main.storyboard */, 93 | 46BA88B91C61F70B00FC4320 /* Assets.xcassets */, 94 | 46BA88BB1C61F70B00FC4320 /* LaunchScreen.storyboard */, 95 | 46BA88BE1C61F70B00FC4320 /* Info.plist */, 96 | 46BA88AD1C61F70B00FC4320 /* Supporting Files */, 97 | ); 98 | path = HMCycleViewDemo; 99 | sourceTree = ""; 100 | }; 101 | 46BA88AD1C61F70B00FC4320 /* Supporting Files */ = { 102 | isa = PBXGroup; 103 | children = ( 104 | 46BA88AE1C61F70B00FC4320 /* main.m */, 105 | ); 106 | name = "Supporting Files"; 107 | sourceTree = ""; 108 | }; 109 | 46BA88CE1C620EF000FC4320 /* HMCycleView */ = { 110 | isa = PBXGroup; 111 | children = ( 112 | 46BA88CF1C620EF000FC4320 /* HMCycleView.h */, 113 | 46BA88D01C620EF000FC4320 /* HMCycleView.m */, 114 | ); 115 | name = HMCycleView; 116 | path = ../../HMCycleView; 117 | sourceTree = ""; 118 | }; 119 | /* End PBXGroup section */ 120 | 121 | /* Begin PBXNativeTarget section */ 122 | 46BA88A91C61F70B00FC4320 /* HMCycleViewDemo */ = { 123 | isa = PBXNativeTarget; 124 | buildConfigurationList = 46BA88C11C61F70B00FC4320 /* Build configuration list for PBXNativeTarget "HMCycleViewDemo" */; 125 | buildPhases = ( 126 | 46BA88A61C61F70B00FC4320 /* Sources */, 127 | 46BA88A71C61F70B00FC4320 /* Frameworks */, 128 | 46BA88A81C61F70B00FC4320 /* Resources */, 129 | ); 130 | buildRules = ( 131 | ); 132 | dependencies = ( 133 | ); 134 | name = HMCycleViewDemo; 135 | productName = HMCycleViewDemo; 136 | productReference = 46BA88AA1C61F70B00FC4320 /* HMCycleViewDemo.app */; 137 | productType = "com.apple.product-type.application"; 138 | }; 139 | /* End PBXNativeTarget section */ 140 | 141 | /* Begin PBXProject section */ 142 | 46BA88A21C61F70B00FC4320 /* Project object */ = { 143 | isa = PBXProject; 144 | attributes = { 145 | LastUpgradeCheck = 0720; 146 | ORGANIZATIONNAME = YosonHao; 147 | TargetAttributes = { 148 | 46BA88A91C61F70B00FC4320 = { 149 | CreatedOnToolsVersion = 7.2; 150 | }; 151 | }; 152 | }; 153 | buildConfigurationList = 46BA88A51C61F70B00FC4320 /* Build configuration list for PBXProject "HMCycleViewDemo" */; 154 | compatibilityVersion = "Xcode 3.2"; 155 | developmentRegion = English; 156 | hasScannedForEncodings = 0; 157 | knownRegions = ( 158 | en, 159 | Base, 160 | ); 161 | mainGroup = 46BA88A11C61F70B00FC4320; 162 | productRefGroup = 46BA88AB1C61F70B00FC4320 /* Products */; 163 | projectDirPath = ""; 164 | projectRoot = ""; 165 | targets = ( 166 | 46BA88A91C61F70B00FC4320 /* HMCycleViewDemo */, 167 | ); 168 | }; 169 | /* End PBXProject section */ 170 | 171 | /* Begin PBXResourcesBuildPhase section */ 172 | 46BA88A81C61F70B00FC4320 /* Resources */ = { 173 | isa = PBXResourcesBuildPhase; 174 | buildActionMask = 2147483647; 175 | files = ( 176 | 46A80DCE1D5200F10072D35A /* Home_Scroll_03.jpg in Resources */, 177 | 46A80DCC1D5200F10072D35A /* Home_Scroll_01.jpg in Resources */, 178 | 46BA88BD1C61F70B00FC4320 /* LaunchScreen.storyboard in Resources */, 179 | 46A80DCD1D5200F10072D35A /* Home_Scroll_02.jpg in Resources */, 180 | 46A80DD01D5200F10072D35A /* Home_Scroll_05.jpg in Resources */, 181 | 46BA88BA1C61F70B00FC4320 /* Assets.xcassets in Resources */, 182 | 46A80DCF1D5200F10072D35A /* Home_Scroll_04.jpg in Resources */, 183 | 46BA88B81C61F70B00FC4320 /* Main.storyboard in Resources */, 184 | ); 185 | runOnlyForDeploymentPostprocessing = 0; 186 | }; 187 | /* End PBXResourcesBuildPhase section */ 188 | 189 | /* Begin PBXSourcesBuildPhase section */ 190 | 46BA88A61C61F70B00FC4320 /* Sources */ = { 191 | isa = PBXSourcesBuildPhase; 192 | buildActionMask = 2147483647; 193 | files = ( 194 | 46BA88D11C620EF000FC4320 /* HMCycleView.m in Sources */, 195 | 46BA88B51C61F70B00FC4320 /* ViewController.m in Sources */, 196 | 46BA88B21C61F70B00FC4320 /* AppDelegate.m in Sources */, 197 | 46BA88AF1C61F70B00FC4320 /* main.m in Sources */, 198 | ); 199 | runOnlyForDeploymentPostprocessing = 0; 200 | }; 201 | /* End PBXSourcesBuildPhase section */ 202 | 203 | /* Begin PBXVariantGroup section */ 204 | 46BA88B61C61F70B00FC4320 /* Main.storyboard */ = { 205 | isa = PBXVariantGroup; 206 | children = ( 207 | 46BA88B71C61F70B00FC4320 /* Base */, 208 | ); 209 | name = Main.storyboard; 210 | sourceTree = ""; 211 | }; 212 | 46BA88BB1C61F70B00FC4320 /* LaunchScreen.storyboard */ = { 213 | isa = PBXVariantGroup; 214 | children = ( 215 | 46BA88BC1C61F70B00FC4320 /* Base */, 216 | ); 217 | name = LaunchScreen.storyboard; 218 | sourceTree = ""; 219 | }; 220 | /* End PBXVariantGroup section */ 221 | 222 | /* Begin XCBuildConfiguration section */ 223 | 46BA88BF1C61F70B00FC4320 /* Debug */ = { 224 | isa = XCBuildConfiguration; 225 | buildSettings = { 226 | ALWAYS_SEARCH_USER_PATHS = NO; 227 | CLANG_CXX_LANGUAGE_STANDARD = "gnu++0x"; 228 | CLANG_CXX_LIBRARY = "libc++"; 229 | CLANG_ENABLE_MODULES = YES; 230 | CLANG_ENABLE_OBJC_ARC = YES; 231 | CLANG_WARN_BOOL_CONVERSION = YES; 232 | CLANG_WARN_CONSTANT_CONVERSION = YES; 233 | CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR; 234 | CLANG_WARN_EMPTY_BODY = YES; 235 | CLANG_WARN_ENUM_CONVERSION = YES; 236 | CLANG_WARN_INT_CONVERSION = YES; 237 | CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR; 238 | CLANG_WARN_UNREACHABLE_CODE = YES; 239 | CLANG_WARN__DUPLICATE_METHOD_MATCH = YES; 240 | "CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "iPhone Developer"; 241 | COPY_PHASE_STRIP = NO; 242 | DEBUG_INFORMATION_FORMAT = dwarf; 243 | ENABLE_STRICT_OBJC_MSGSEND = YES; 244 | ENABLE_TESTABILITY = YES; 245 | GCC_C_LANGUAGE_STANDARD = gnu99; 246 | GCC_DYNAMIC_NO_PIC = NO; 247 | GCC_NO_COMMON_BLOCKS = YES; 248 | GCC_OPTIMIZATION_LEVEL = 0; 249 | GCC_PREPROCESSOR_DEFINITIONS = ( 250 | "DEBUG=1", 251 | "$(inherited)", 252 | ); 253 | GCC_WARN_64_TO_32_BIT_CONVERSION = YES; 254 | GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR; 255 | GCC_WARN_UNDECLARED_SELECTOR = YES; 256 | GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE; 257 | GCC_WARN_UNUSED_FUNCTION = YES; 258 | GCC_WARN_UNUSED_VARIABLE = YES; 259 | IPHONEOS_DEPLOYMENT_TARGET = 9.2; 260 | MTL_ENABLE_DEBUG_INFO = YES; 261 | ONLY_ACTIVE_ARCH = YES; 262 | SDKROOT = iphoneos; 263 | }; 264 | name = Debug; 265 | }; 266 | 46BA88C01C61F70B00FC4320 /* Release */ = { 267 | isa = XCBuildConfiguration; 268 | buildSettings = { 269 | ALWAYS_SEARCH_USER_PATHS = NO; 270 | CLANG_CXX_LANGUAGE_STANDARD = "gnu++0x"; 271 | CLANG_CXX_LIBRARY = "libc++"; 272 | CLANG_ENABLE_MODULES = YES; 273 | CLANG_ENABLE_OBJC_ARC = YES; 274 | CLANG_WARN_BOOL_CONVERSION = YES; 275 | CLANG_WARN_CONSTANT_CONVERSION = YES; 276 | CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR; 277 | CLANG_WARN_EMPTY_BODY = YES; 278 | CLANG_WARN_ENUM_CONVERSION = YES; 279 | CLANG_WARN_INT_CONVERSION = YES; 280 | CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR; 281 | CLANG_WARN_UNREACHABLE_CODE = YES; 282 | CLANG_WARN__DUPLICATE_METHOD_MATCH = YES; 283 | "CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "iPhone Developer"; 284 | COPY_PHASE_STRIP = NO; 285 | DEBUG_INFORMATION_FORMAT = "dwarf-with-dsym"; 286 | ENABLE_NS_ASSERTIONS = NO; 287 | ENABLE_STRICT_OBJC_MSGSEND = YES; 288 | GCC_C_LANGUAGE_STANDARD = gnu99; 289 | GCC_NO_COMMON_BLOCKS = YES; 290 | GCC_WARN_64_TO_32_BIT_CONVERSION = YES; 291 | GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR; 292 | GCC_WARN_UNDECLARED_SELECTOR = YES; 293 | GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE; 294 | GCC_WARN_UNUSED_FUNCTION = YES; 295 | GCC_WARN_UNUSED_VARIABLE = YES; 296 | IPHONEOS_DEPLOYMENT_TARGET = 9.2; 297 | MTL_ENABLE_DEBUG_INFO = NO; 298 | SDKROOT = iphoneos; 299 | VALIDATE_PRODUCT = YES; 300 | }; 301 | name = Release; 302 | }; 303 | 46BA88C21C61F70B00FC4320 /* Debug */ = { 304 | isa = XCBuildConfiguration; 305 | buildSettings = { 306 | ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon; 307 | INFOPLIST_FILE = HMCycleViewDemo/Info.plist; 308 | LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/Frameworks"; 309 | PRODUCT_BUNDLE_IDENTIFIER = com.hao.HMCycleViewDemo; 310 | PRODUCT_NAME = "$(TARGET_NAME)"; 311 | }; 312 | name = Debug; 313 | }; 314 | 46BA88C31C61F70B00FC4320 /* Release */ = { 315 | isa = XCBuildConfiguration; 316 | buildSettings = { 317 | ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon; 318 | INFOPLIST_FILE = HMCycleViewDemo/Info.plist; 319 | LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/Frameworks"; 320 | PRODUCT_BUNDLE_IDENTIFIER = com.hao.HMCycleViewDemo; 321 | PRODUCT_NAME = "$(TARGET_NAME)"; 322 | }; 323 | name = Release; 324 | }; 325 | /* End XCBuildConfiguration section */ 326 | 327 | /* Begin XCConfigurationList section */ 328 | 46BA88A51C61F70B00FC4320 /* Build configuration list for PBXProject "HMCycleViewDemo" */ = { 329 | isa = XCConfigurationList; 330 | buildConfigurations = ( 331 | 46BA88BF1C61F70B00FC4320 /* Debug */, 332 | 46BA88C01C61F70B00FC4320 /* Release */, 333 | ); 334 | defaultConfigurationIsVisible = 0; 335 | defaultConfigurationName = Release; 336 | }; 337 | 46BA88C11C61F70B00FC4320 /* Build configuration list for PBXNativeTarget "HMCycleViewDemo" */ = { 338 | isa = XCConfigurationList; 339 | buildConfigurations = ( 340 | 46BA88C21C61F70B00FC4320 /* Debug */, 341 | 46BA88C31C61F70B00FC4320 /* Release */, 342 | ); 343 | defaultConfigurationIsVisible = 0; 344 | defaultConfigurationName = Release; 345 | }; 346 | /* End XCConfigurationList section */ 347 | }; 348 | rootObject = 46BA88A21C61F70B00FC4320 /* Project object */; 349 | } 350 | -------------------------------------------------------------------------------- /HMCycleViewDemo/HMCycleViewDemo.xcodeproj/project.xcworkspace/contents.xcworkspacedata: -------------------------------------------------------------------------------- 1 | 2 | 4 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /HMCycleViewDemo/HMCycleViewDemo/AppDelegate.h: -------------------------------------------------------------------------------- 1 | // 2 | // AppDelegate.h 3 | // HMCycleViewDemo 4 | // 5 | // Created by HaoYoson on 16/2/3. 6 | // Copyright © 2016年 YosonHao. All rights reserved. 7 | // 8 | 9 | #import 10 | 11 | @interface AppDelegate : UIResponder 12 | 13 | @property (strong, nonatomic) UIWindow *window; 14 | 15 | @end 16 | -------------------------------------------------------------------------------- /HMCycleViewDemo/HMCycleViewDemo/AppDelegate.m: -------------------------------------------------------------------------------- 1 | // 2 | // AppDelegate.m 3 | // HMCycleViewDemo 4 | // 5 | // Created by HaoYoson on 16/2/3. 6 | // Copyright © 2016年 YosonHao. All rights reserved. 7 | // 8 | 9 | #import "AppDelegate.h" 10 | 11 | @interface AppDelegate () 12 | 13 | @end 14 | 15 | @implementation AppDelegate 16 | 17 | - (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions { 18 | // Override point for customization after application launch. 19 | 20 | self.window = [[UIWindow alloc] initWithFrame:[UIScreen mainScreen].bounds]; 21 | self.window.rootViewController = [[NSClassFromString(@"ViewController") alloc] init]; 22 | [self.window makeKeyAndVisible]; 23 | 24 | return YES; 25 | } 26 | 27 | - (void)applicationWillResignActive:(UIApplication *)application { 28 | // Sent when the application is about to move from active to inactive state. This can occur for certain types of temporary interruptions (such as an incoming phone call or SMS message) or when the user quits the application and it begins the transition to the background state. 29 | // Use this method to pause ongoing tasks, disable timers, and throttle down OpenGL ES frame rates. Games should use this method to pause the game. 30 | } 31 | 32 | - (void)applicationDidEnterBackground:(UIApplication *)application { 33 | // Use this method to release shared resources, save user data, invalidate timers, and store enough application state information to restore your application to its current state in case it is terminated later. 34 | // If your application supports background execution, this method is called instead of applicationWillTerminate: when the user quits. 35 | } 36 | 37 | - (void)applicationWillEnterForeground:(UIApplication *)application { 38 | // Called as part of the transition from the background to the inactive state; here you can undo many of the changes made on entering the background. 39 | } 40 | 41 | - (void)applicationDidBecomeActive:(UIApplication *)application { 42 | // Restart any tasks that were paused (or not yet started) while the application was inactive. If the application was previously in the background, optionally refresh the user interface. 43 | } 44 | 45 | - (void)applicationWillTerminate:(UIApplication *)application { 46 | // Called when the application is about to terminate. Save data if appropriate. See also applicationDidEnterBackground:. 47 | } 48 | 49 | @end 50 | -------------------------------------------------------------------------------- /HMCycleViewDemo/HMCycleViewDemo/Assets.xcassets/AppIcon.appiconset/Contents.json: -------------------------------------------------------------------------------- 1 | { 2 | "images" : [ 3 | { 4 | "idiom" : "iphone", 5 | "size" : "29x29", 6 | "scale" : "2x" 7 | }, 8 | { 9 | "idiom" : "iphone", 10 | "size" : "29x29", 11 | "scale" : "3x" 12 | }, 13 | { 14 | "idiom" : "iphone", 15 | "size" : "40x40", 16 | "scale" : "2x" 17 | }, 18 | { 19 | "idiom" : "iphone", 20 | "size" : "40x40", 21 | "scale" : "3x" 22 | }, 23 | { 24 | "idiom" : "iphone", 25 | "size" : "60x60", 26 | "scale" : "2x" 27 | }, 28 | { 29 | "idiom" : "iphone", 30 | "size" : "60x60", 31 | "scale" : "3x" 32 | } 33 | ], 34 | "info" : { 35 | "version" : 1, 36 | "author" : "xcode" 37 | } 38 | } -------------------------------------------------------------------------------- /HMCycleViewDemo/HMCycleViewDemo/Assets.xcassets/Contents.json: -------------------------------------------------------------------------------- 1 | { 2 | "info" : { 3 | "version" : 1, 4 | "author" : "xcode" 5 | } 6 | } -------------------------------------------------------------------------------- /HMCycleViewDemo/HMCycleViewDemo/Base.lproj/LaunchScreen.storyboard: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | -------------------------------------------------------------------------------- /HMCycleViewDemo/HMCycleViewDemo/Base.lproj/Main.storyboard: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 | 30 | 31 | 32 | 33 | 34 | 35 | 36 | 37 | 38 | 39 | 40 | 41 | 42 | 43 | 44 | 45 | 46 | 47 | 48 | 49 | 50 | 51 | 52 | 53 | 54 | 55 | 56 | 57 | 58 | 59 | 60 | 61 | 62 | -------------------------------------------------------------------------------- /HMCycleViewDemo/HMCycleViewDemo/Info.plist: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | NSAppTransportSecurity 6 | 7 | NSAllowsArbitraryLoads 8 | 9 | 10 | CFBundleDevelopmentRegion 11 | en 12 | CFBundleExecutable 13 | $(EXECUTABLE_NAME) 14 | CFBundleIdentifier 15 | $(PRODUCT_BUNDLE_IDENTIFIER) 16 | CFBundleInfoDictionaryVersion 17 | 6.0 18 | CFBundleName 19 | $(PRODUCT_NAME) 20 | CFBundlePackageType 21 | APPL 22 | CFBundleShortVersionString 23 | 1.0 24 | CFBundleSignature 25 | ???? 26 | CFBundleVersion 27 | 1 28 | LSRequiresIPhoneOS 29 | 30 | UILaunchStoryboardName 31 | LaunchScreen 32 | UIRequiredDeviceCapabilities 33 | 34 | armv7 35 | 36 | UISupportedInterfaceOrientations 37 | 38 | UIInterfaceOrientationPortrait 39 | UIInterfaceOrientationLandscapeLeft 40 | UIInterfaceOrientationLandscapeRight 41 | 42 | 43 | 44 | -------------------------------------------------------------------------------- /HMCycleViewDemo/HMCycleViewDemo/ViewController.h: -------------------------------------------------------------------------------- 1 | // 2 | // ViewController.h 3 | // HMCycleViewDemo 4 | // 5 | // Created by HaoYoson on 16/2/3. 6 | // Copyright © 2016年 YosonHao. All rights reserved. 7 | // 8 | 9 | #import 10 | 11 | @interface ViewController : UIViewController 12 | 13 | @end 14 | -------------------------------------------------------------------------------- /HMCycleViewDemo/HMCycleViewDemo/ViewController.m: -------------------------------------------------------------------------------- 1 | // 2 | // ViewController.m 3 | // HMCycleViewDemo 4 | // 5 | // Created by HaoYoson on 16/2/3. 6 | // Copyright © 2016年 YosonHao. All rights reserved. 7 | // 8 | 9 | #import "HMCycleView.h" 10 | #import "ViewController.h" 11 | 12 | @interface ViewController () 13 | 14 | @end 15 | 16 | @implementation ViewController 17 | 18 | - (void)viewDidLoad { 19 | [super viewDidLoad]; 20 | // Do any additional setup after loading the view, typically from a nib. 21 | 22 | self.view.backgroundColor = [UIColor whiteColor]; 23 | 24 | // 1. create cycleView(set 'frame' or 'autoLayout'). 25 | HMCycleView *cycleView = [[HMCycleView alloc] initWithFrame:CGRectMake(0, 0, 300, 100)]; 26 | 27 | NSURL *url1 = [[NSBundle mainBundle] URLForResource:@"Home_Scroll_01.jpg" withExtension:nil]; 28 | NSURL *url2 = [[NSBundle mainBundle] URLForResource:@"Home_Scroll_02.jpg" withExtension:nil]; 29 | NSURL *url3 = [[NSBundle mainBundle] URLForResource:@"Home_Scroll_03.jpg" withExtension:nil]; 30 | NSURL *url4 = [[NSBundle mainBundle] URLForResource:@"Home_Scroll_04.jpg" withExtension:nil]; 31 | NSURL *url5 = [[NSBundle mainBundle] URLForResource:@"Home_Scroll_05.jpg" withExtension:nil]; 32 | 33 | // 2. set array with image's URL. 34 | cycleView.imageURLs = @[ url1, url2, url3, url4, url5 ]; 35 | 36 | cycleView.delegate = self; 37 | 38 | cycleView.pageControlPosition = HMCycleViewPageControlPositionBottomLeft; 39 | 40 | cycleView.showPageControl = YES; 41 | 42 | cycleView.titles = @[ @"1", @"", @"3", @"4" ]; 43 | 44 | // 3. add this cycleView. 45 | [self.view addSubview:cycleView]; 46 | 47 | cycleView.translatesAutoresizingMaskIntoConstraints = NO; // 取消 autoresizing 48 | [self.view addConstraint:[NSLayoutConstraint constraintWithItem:cycleView attribute:NSLayoutAttributeTop relatedBy:NSLayoutRelationEqual toItem:self.view attribute:NSLayoutAttributeTop multiplier:1 constant:20]]; 49 | [self.view addConstraint:[NSLayoutConstraint constraintWithItem:cycleView attribute:NSLayoutAttributeLeft relatedBy:NSLayoutRelationEqual toItem:self.view attribute:NSLayoutAttributeLeft multiplier:1 constant:0]]; 50 | [self.view addConstraint:[NSLayoutConstraint constraintWithItem:cycleView attribute:NSLayoutAttributeRight relatedBy:NSLayoutRelationEqual toItem:self.view attribute:NSLayoutAttributeRight multiplier:1 constant:0]]; 51 | [self.view addConstraint:[NSLayoutConstraint constraintWithItem:cycleView attribute:NSLayoutAttributeHeight relatedBy:NSLayoutRelationEqual toItem:nil attribute:NSLayoutAttributeNotAnAttribute multiplier:1 constant:150]]; 52 | } 53 | 54 | - (void)cycleView:(HMCycleView *)cycleView didSelectItemAtIndex:(NSInteger)index { 55 | NSLog(@"%zd", index); 56 | } 57 | 58 | // 轮播器广告数据 59 | - (NSArray *)loadImageURLs { 60 | NSMutableArray *array = [NSMutableArray array]; 61 | 62 | for (int i = 0; i < 5; i++) { 63 | NSString *imageName = [NSString stringWithFormat:@"Home_Scroll_0%d.jpg", i + 1]; 64 | 65 | // 获取图片的url 66 | NSURL *url = [[NSBundle mainBundle] URLForResource:imageName withExtension:nil]; 67 | 68 | [array addObject:url]; 69 | } 70 | 71 | return array.copy; 72 | } 73 | 74 | @end 75 | -------------------------------------------------------------------------------- /HMCycleViewDemo/HMCycleViewDemo/main.m: -------------------------------------------------------------------------------- 1 | // 2 | // main.m 3 | // HMCycleViewDemo 4 | // 5 | // Created by HaoYoson on 16/2/3. 6 | // Copyright © 2016年 YosonHao. All rights reserved. 7 | // 8 | 9 | #import "AppDelegate.h" 10 | #import 11 | 12 | int main(int argc, char *argv[]) { 13 | @autoreleasepool { 14 | return UIApplicationMain(argc, argv, nil, NSStringFromClass([AppDelegate class])); 15 | } 16 | } 17 | -------------------------------------------------------------------------------- /HMCycleViewDemo/HMCycleViewDemo/轮播广告/Home_Scroll_01.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/itheima-developer/HMCycleView/3c18546262318dd54b06e218d62468683c57f992/HMCycleViewDemo/HMCycleViewDemo/轮播广告/Home_Scroll_01.jpg -------------------------------------------------------------------------------- /HMCycleViewDemo/HMCycleViewDemo/轮播广告/Home_Scroll_02.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/itheima-developer/HMCycleView/3c18546262318dd54b06e218d62468683c57f992/HMCycleViewDemo/HMCycleViewDemo/轮播广告/Home_Scroll_02.jpg -------------------------------------------------------------------------------- /HMCycleViewDemo/HMCycleViewDemo/轮播广告/Home_Scroll_03.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/itheima-developer/HMCycleView/3c18546262318dd54b06e218d62468683c57f992/HMCycleViewDemo/HMCycleViewDemo/轮播广告/Home_Scroll_03.jpg -------------------------------------------------------------------------------- /HMCycleViewDemo/HMCycleViewDemo/轮播广告/Home_Scroll_04.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/itheima-developer/HMCycleView/3c18546262318dd54b06e218d62468683c57f992/HMCycleViewDemo/HMCycleViewDemo/轮播广告/Home_Scroll_04.jpg -------------------------------------------------------------------------------- /HMCycleViewDemo/HMCycleViewDemo/轮播广告/Home_Scroll_05.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/itheima-developer/HMCycleView/3c18546262318dd54b06e218d62468683c57f992/HMCycleViewDemo/HMCycleViewDemo/轮播广告/Home_Scroll_05.jpg -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | The MIT License (MIT) 2 | 3 | Copyright (c) 2016 黑马程序员 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 21 | SOFTWARE. 22 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # HMCycleView 2 | HMCycleView is a open source iOS library provide infinity scroll show a group of views in view. 3 | 4 | ##Demo 5 | Build and run the `HMCycleViewDemo` project in Xcode to see `HMCycleView` in action. 6 | 7 | ##Setup 8 | To enable fantasitic feature in your project with the following simple steps: 9 | 10 | 1. Download the project from GitHub. 11 | 2. Drop `HMCycleView` files into your project. 12 | 3. Add `#include "HMCycleView.h"` to the top of classes that will use it. 13 | 14 | ##Usage 15 | #####Code example 16 | ``` objective-c 17 | 18 | // 1. create cycleView(set 'frame' or 'autoLayout'). 19 | HMCycleView *cycleView = [[HMCycleView alloc] initWithFrame:CGRectMake(0, 0, 300, 100)]; 20 | 21 | NSURL *url1 = [[NSBundle mainBundle] URLForResource:@"Home_Scroll_01.jpg" withExtension:nil]; 22 | NSURL *url2 = [[NSBundle mainBundle] URLForResource:@"Home_Scroll_02.jpg" withExtension:nil]; 23 | NSURL *url3 = [[NSBundle mainBundle] URLForResource:@"Home_Scroll_03.jpg" withExtension:nil]; 24 | NSURL *url4 = [[NSBundle mainBundle] URLForResource:@"Home_Scroll_04.jpg" withExtension:nil]; 25 | NSURL *url5 = [[NSBundle mainBundle] URLForResource:@"Home_Scroll_05.jpg" withExtension:nil]; 26 | // 2. set array with image's URL. 27 | cycleView.imageURLs = @[ url1, url2, url3, url4, url5 ]; 28 | 29 | // 3. add this cycleView. 30 | [self.view addSubview:cycleView]; 31 | 32 | ``` 33 | 34 | ##TODO 35 | ~~Each item click.~~ 36 | 37 | Each item description. 38 | 39 | ~~Page control.~~ 40 | 41 | Page control custom color. 42 | 43 | Scroll duration. 44 | 45 | ##Author 46 | **Yoson Hao** 47 | 48 | Weibo:[@郝悦兴][1] 49 | 50 | Github:[Hao Y.Xing][2] 51 | 52 | ##Thanks 53 | **刀哥** 54 | 55 | Github:[刘凡][3] 56 | 57 | Blog:[Joy iOS][4] 58 | 59 | ##License 60 | HMCycleView is released under the MIT license. See LICENSE for details. 61 | 62 | [1]: http://weibo.com/haoyuexing 63 | [2]: https://github.com/haoyuexing 64 | [3]: https://github.com/liufan321 65 | [4]: http://www.joyios.com/ 66 | --------------------------------------------------------------------------------