A.概念
例子就是桌面的APP列表,当APP数量超过一个屏幕,自动进行分页
 
B.实现思路
1.创建一个UIScrollView,这里设置为宽度跟屏幕相同,高度1/4屏幕高度左右
2.使用代码在UIScrollView中添加ImageView,横向放入多张ImageView
3.设置UIScrollView的contentSize为所有图片的宽度总和
4.要保证UIScrollView的宽度等于一张ImageView的宽度,才能正确分页
 
C.相关属性
设置属性pageEnable = YES,UIScrollView会被分割成多个独立页面,进行分页显示
一般使用UIPageControl增强效果,UIPageControl常见属性:
     // 总页数
@property(nonatomic) NSInteger numberOfPages; // default is 0
// 当前页码
@property(nonatomic) NSInteger currentPage;
// 只有一页的时候隐藏页码
@property(nonatomic) BOOL hidesForSinglePage; // hide the the indicator if there is only one page. default is NO
// 其他页码指示颜色
@property(nonatomic,retain) UIColor *pageIndicatorTintColor;
// 当前页码指示颜色
@property(nonatomic,retain) UIColor *currentPageIndicatorTintColor;
 
 
D.实现步骤
1. 创建一个UIScrollView,设置位置、尺寸
 
2.用代码加载多张图片
     CGFloat imageWidth = ;
CGFloat imageHeight = ;
CGFloat imageY = ; for (int i=; i<; i++) {
CGFloat imageX = i * imageWidth;
UIImageView *currentImageView = [[UIImageView alloc] initWithImage:[UIImage imageNamed:[NSString stringWithFormat:@"img_%02d", i+]]];
currentImageView.frame = CGRectMake(imageX, imageY, imageWidth, imageHeight); [self.scrollView addSubview:currentImageView];
}
 
3.设置contentSize
     // 设置可以拖曳的范围,只允许横向拖曳,而且范围是所有的图片宽度总和
self.scrollView.contentSize = CGSizeMake( * imageWidth, );
 
4.开启 pageEnable = YES
     每次拖曳至少滑动1个UIScrollView宽度单位,设置UIScrollView的宽度为图片的宽度之后,刚好翻过一页。
     // 开启翻页模式,每次拖曳都会滑动一个UIScrollView宽度单位
self.scrollView.pagingEnabled = YES;
 
没有开启之前,切换两幅图片的时候终止拖曳,会停留在那一刻的显示状态
 
开启之后效果就像书本翻页一样
 
 
5.加入pageControl
pageControl要放在UIScrollView外,而且要比UIScrollView更前,才能正常显示
 
 
6.使用代码设置pageControl
pageControl属性:
     // 总页数
@property(nonatomic) NSInteger numberOfPages; // default is 0
// 当前页码
@property(nonatomic) NSInteger currentPage;
// 只有一页的时候隐藏页码
@property(nonatomic) BOOL hidesForSinglePage; // hide the the indicator if there is only one page. default is NO
// 其他页码指示颜色
@property(nonatomic,retain) UIColor *pageIndicatorTintColor;
// 当前页码指示颜色
@property(nonatomic,retain) UIColor *currentPageIndicatorTintColor;
 
(1)要手动设置pageControl,它才能正常工作
     // 设置pageControl
self.pageControl.numberOfPages = ;
self.pageControl.pageIndicatorTintColor = [UIColor blackColor]; //设置delegate
self.scrollView.delegate = self;
 
(2)控制器遵守UIScrollViewDelegate协议,在 scrollViewDidScroll中动态设置当前页码
 /** 当scrollView滚动的时候调用 */
- (void)scrollViewDidScroll:(UIScrollView *)scrollView {
CGFloat scrollWidth = scrollView.frame.size.width; // 当一副图片拖曳超过一半的时候就重新计算页码
int page = (scrollView.contentOffset.x + scrollWidth * 0.5) / scrollWidth; self.pageControl.currentPage = page;
}
 
 
 
7.使用定时器NSTimer自动换页
(1)添加定时器
     // 创建定时器
NSTimer *timer = [NSTimer scheduledTimerWithTimeInterval: target:self selector:@selector(nextImage) userInfo:nil repeats:YES];
 
(2)创建定时器调用的方法
 - (void) nextImage {
// 1.增加pageControl的页码,这里不能直接操作currentPage,因为这样会和scrollViewDidScroll的页码计算冲突,应该是滚动画面,触发scrollViewDidScroll进行页码转换
int pageNo = ;
if (self.pageControl.currentPage == (IMAGE_COUNT - )) {
pageNo = ;
}
else {
pageNo = self.pageControl.currentPage + ;
} // 2.计算scrollView的滑动位置
CGFloat offsetX = pageNo * self.scrollView.frame.size.width;
CGPoint offset = CGPointMake(offsetX, ); // 移动一页,带动画效果
[self.scrollView setContentOffset:offset animated:YES];
}
 
(3)定时器的弱点,在单线程运行时,得不到线程资源的时候,定时器定制运行,事件累积,得到资源之后才一起运行,这里有两种情况:
 
a.手动拖曳阻止了定时器
     解决:销毁定时器,确保资源之后再创建一个
 // 开始手动拖曳的时候,销毁定时器
- (void)scrollViewWillBeginDragging:(UIScrollView *)scrollView {
[self.timer invalidate]; // 调用了invalidate之后再不可用了
self.timer = nil;
} // 结束手动拖曳,重新定义定时器
- (void)scrollViewDidEndDragging:(UIScrollView *)scrollView willDecelerate:(BOOL)decelerate {
[self addTimer];
} // 添加定时器
- (void) addTimer {
self.timer = [NSTimer scheduledTimerWithTimeInterval: target:self selector:@selector(nextImage) userInfo:nil repeats:YES];
}
 
b.外部可刷新的控件抢占了所有线程资源
如下图中,添加了一个TextView,当拖曳其滚动条时,占用了所有线程刷新资源,定时器就被阻断了
 
解决:争取主线程资源来刷新(分享资源)
 // 添加定时器
- (void) addTimer {
self.timer = [NSTimer scheduledTimerWithTimeInterval: target:self selector:@selector(nextImage) userInfo:nil repeats:YES]; // 获得主线程资源,防止另外的如可滚动控件的资源全占用
[[NSRunLoop currentRunLoop] addTimer:self.timer forMode:NSRunLoopCommonModes];
}
 
 
E.滚动页的优化
1.只使用3个ImageView加载图片,动态加载图片
2.无限滚动
 
 
F.主要代码:
 //
// ViewController.m
// ScrollViewPage
//
// Created by hellovoidworld on 14/11/28.
// Copyright (c) 2014年 hellovoidworld. All rights reserved.
// #import "ViewController.h" #define IMAGE_COUNT 5 @interface ViewController () <UIScrollViewDelegate>
@property (weak, nonatomic) IBOutlet UIScrollView *scrollView; // 滚动控件
@property (weak, nonatomic) IBOutlet UIPageControl *pageControl; // 页码控件 @property(nonatomic, strong) NSTimer *timer; // 定时器 @end @implementation ViewController - (void)viewDidLoad {
[super viewDidLoad];
// Do any additional setup after loading the view, typically from a nib. CGFloat imageWidth = ;
CGFloat imageHeight = ;
CGFloat imageY = ; for (int i=; i<IMAGE_COUNT; i++) {
CGFloat imageX = i * imageWidth;
UIImageView *currentImageView = [[UIImageView alloc] initWithImage:[UIImage imageNamed:[NSString stringWithFormat:@"img_%02d", i+]]];
currentImageView.frame = CGRectMake(imageX, imageY, imageWidth, imageHeight); [self.scrollView addSubview:currentImageView];
} // 设置可以拖曳的范围,只允许横向拖曳,而且范围是所有的图片宽度总和
self.scrollView.contentSize = CGSizeMake(IMAGE_COUNT * imageWidth, ); // 开启翻页模式,每次拖曳都会滑动一个UIScrollView宽度单位
self.scrollView.pagingEnabled = YES; // 设置pageControl
self.pageControl.numberOfPages = ;
self.pageControl.pageIndicatorTintColor = [UIColor blackColor];
self.pageControl.currentPageIndicatorTintColor = [UIColor redColor]; // 设置delegate
self.scrollView.delegate = self; // 创建定时器
[self addTimer];
} - (void)didReceiveMemoryWarning {
[super didReceiveMemoryWarning];
// Dispose of any resources that can be recreated.
} /** 当scrollView滚动的时候调用 */
- (void)scrollViewDidScroll:(UIScrollView *)scrollView {
CGFloat scrollWidth = scrollView.frame.size.width; // 当一副图片拖曳超过一半的时候就重新计算页码
int page = (scrollView.contentOffset.x + scrollWidth * 0.5) / scrollWidth; self.pageControl.currentPage = page;
} - (void) nextImage {
// 1.增加pageControl的页码,这里不能直接操作currentPage,因为这样会和scrollViewDidScroll的页码计算冲突,应该是滚动画面,触发scrollViewDidScroll进行页码转换
int pageNo = ;
if (self.pageControl.currentPage == (IMAGE_COUNT - )) {
pageNo = ;
}
else {
pageNo = self.pageControl.currentPage + ;
} // 2.计算scrollView的滑动位置
CGFloat offsetX = pageNo * self.scrollView.frame.size.width;
CGPoint offset = CGPointMake(offsetX, ); // 移动一页,带动画效果
[self.scrollView setContentOffset:offset animated:YES];
} // 开始手动拖曳的时候,销毁定时器
- (void)scrollViewWillBeginDragging:(UIScrollView *)scrollView {
[self.timer invalidate]; // 调用了invalidate之后再不可用了
self.timer = nil;
} // 结束手动拖曳,重新定义定时器
- (void)scrollViewDidEndDragging:(UIScrollView *)scrollView willDecelerate:(BOOL)decelerate {
[self addTimer];
} // 添加定时器
- (void) addTimer {
self.timer = [NSTimer scheduledTimerWithTimeInterval: target:self selector:@selector(nextImage) userInfo:nil repeats:YES]; // 获得主线程资源,防止另外的如可滚动控件的资源全占用
[[NSRunLoop currentRunLoop] addTimer:self.timer forMode:NSRunLoopCommonModes];
} @end
 

[iOS基础控件 - 5.4] 广告分页代码(UIScrollView制作)的更多相关文章

  1. [iOS基础控件 - 5.5] 代理设计模式 (基于”APP列表"练习)

    A.概述      在"[iOS基础控件 - 4.4] APP列表 进一步封装,初见MVC模式”上进一步改进,给“下载”按钮加上效果.功能      1.按钮点击后,显示为“已下载”,并且不 ...

  2. [iOS基础控件 - 6.6.1] 展示团购数据代码

      1.主控制器: // // ViewController.m // GroupPurchase // // Created by hellovoidworld on 14/12/3. // Cop ...

  3. iOS 基础控件(下)

    上篇介绍了UIButton.UILabel.UIImageView和UITextField,这篇就简短一点介绍UIScrollView和UIAlertView. UIScrollView 顾名思义也知 ...

  4. [iOS基础控件 - 7.0] UIWebView

    A.基本使用 1.概念 iOS内置的浏览器控件 Safari浏览器就是通过UIWebView实现的   2.用途:制作简易浏览器 (1)基本请求 创建请求 加载请求 (2)代理监听webView加载, ...

  5. [iOS基础控件 - 6.11.3] 私人通讯录Demo 控制器的数据传递、存储

    A.需求 1.搭建一个"私人通讯录"Demo 2.模拟登陆界面 账号 密码 记住密码开关 自动登陆开关 登陆按钮 3.退出注销 4.增删改查 5.恢复数据(取消修改)   这个代码 ...

  6. [iOS基础控件 - 6.10.2] PickerView 自定义row内容 国家选择Demo

    A.需求 1.自定义一个UIView和xib,包含国家名和国旗显示 2.学习row的重用   B.实现步骤 1.准备plist文件和国旗图片     2.创建模型 // // Flag.h // Co ...

  7. [iOS基础控件 - 6.9] 聊天界面Demo

    A.需求 做出一个类似于QQ.微信的聊天界面 1.每个cell包含发送时间.发送人(头像).发送信息 2.使用对方头像放在左边,我方头像在右边 3.对方信息使用白色背景对话框,我方信息使用蓝色背景对话 ...

  8. [iOS基础控件 - 6.7] 微博展示 使用代码自定义TableCell(动态尺寸)

    A.需求 1.类似于微博内容的展示 2.头像 3.名字 4.会员标志 5.内容 6.分割线 7.配图(可选,可有可无)   code source: https://github.com/hellov ...

  9. [iOS基础控件 - 6.6] 展示团购数据 自定义TableViewCell

    A.需求 1.头部广告 2.自定义cell:含有图片.名称.购买数量.价格 3.使用xib设计自定义cell,自定义cell继承自UITableViewCell 4.尾部“加载更多按钮”,以及其被点击 ...

随机推荐

  1. 创业公司Playcafe关门大吉 创始人总结10大失败教训

    导读:互联网电视游戏网站PlayCafe的创始人马克·高登森(Mark Goldenson)日前撰文,总结了自己创业失败的十个教训.以下为文章主要内容: 一年半前,我与公司联合创始人戴维·奈格(Dev ...

  2. Android:使用ViewPager实现左右滑动切换图片(图上有点点)

    在以下实例的基础上加上点点 Android:使用ViewPager实现左右滑动切换图片 (简单版) 效果预览: 因为要把点点放图片上,所以修改布局为相对布局: <?xml version=&qu ...

  3. 如何理解IoC/DI

    IoC:Inversion of Control,控制反转DI:Dependency Injection,依赖注入 要理解上面两个概念,就必须搞清楚如下的问题: 参与者都有谁?依赖:谁依赖于谁?为什么 ...

  4. python学习笔记四--元组

    一.元组: 1. 不可变更的列表 2. 从语法上,她们是编写在小括号里,不是方括号里,列表是编写在方括号里的 3. 圆括号也同时用于表达式,如果想说明这是一个元组,不是表达式,可以在value后,关闭 ...

  5. Jquery attr()方法 属性赋值和属性获取

    jquery中用attr()方法来获取和设置元素属性,attr是attribute(属性)的缩写,在jQuery DOM操作中会经常用到attr(),attr()有4个表达式. 1. attr(属性名 ...

  6. AIDL与stub

     Stub翻译成中文是存根的意思,注意Stub对象是在被调用端进程,也就是服务端进程,至此,服务端aidl服务端得编码完成了.  stub是为了方便client,service交互而生成出来的代码.A ...

  7. WinCE设置多国语言支持

    最近项目中需要支持中(简繁)日韩英多种语言,在网上找了很多解决办法,最后发现还是MSDN最好. [c-sharp] view plaincopy [HKEY_LOCAL_MACHINE/SYSTEM/ ...

  8. 告诉你一个真实的OpenStack:都谁在用,用来干什么?

    告诉你一个真实的OpenStack:都谁在用,用来干什么? OpenStack基金会近日发布的双年调查报告显示,开源云计算软件OpenStack正在进入主流企业市场,但该项目依然面临较难部署和管理的老 ...

  9. php 生成类的对象 $a=new test();

    程序 <?php class test { ... } $a=new test(); 1.BNF 范式 start: variable '=' expr ';' expr: new_expr ; ...

  10. 【待填坑】bzoj上WC的题解

    之前在bzoj上做了几道WC的题目,现在整理一下 bzoj2115 去膜拜莫队的<高斯消元解xor方程组> bzoj2597 LCT维护MST bzoj1758 分数规划+树分治+单调队列 ...