常用代理方法:

- (void)scrollViewDidScroll:(UIScrollView *)scrollView

只有  [self.scrolView setContentOffset:CGPointMake(0, 100) animated:true]; animated 为true 才会调用

- (void)scrollViewDidEndScrollingAnimation:(UIScrollView *)scrollView

刚开始拖动的时候,dragging 为 YES,decelerating 为 NO;decelerate 过程中,dragging 和 decelerating 都为 YES;decelerate 未结束时开始下一次拖动,dragging 和 decelerating 依然都为 YES。所以无法简单通过 table view 的 dragging 和 decelerating 判断是在用户拖动还是减速过程。

- (void)scrollViewWillBeginDragging:(UIScrollView *)scrollView{
    

  self.isUserDragging = true;//标记用户开始拖动

}
- (void)scrollViewWillEndDragging:(UIScrollView *)scrollView withVelocity:(CGPoint)velocity targetContentOffset:(inout CGPoint *)targetContentOffset

如果decelerate为0 则下面的两个方法不会调用

- (void)scrollViewDidEndDragging:(UIScrollView *)scrollView willDecelerate:(BOOL)decelerate{

    self.isUserDragging = false;//停止拖动
}
scrollViewDidEndDragging 中的decelerate为false 则不会调用
- (void)scrollViewWillBeginDecelerating:(UIScrollView *)scrollView{
NSLog(@"--will decelerate ---");
}
- (void)scrollViewDidEndDecelerating:(UIScrollView *)scrollView{ NSLog(@"--end decelerate ---");
}

返回可以进行缩放的视图

- (UIView *)viewForZoomingInScrollView:(UIScrollView *)scrollView

分页功能:

1.self.scrolView.pagingEnabled

2.

如图,scrollview 只有一个子视图content view ,这样只需在content view 中布局需要展示的view 即可

self.scrolView.clipsToBounds = false //设置false 这样就能显示超出scrolview 边界部分的视图 但超出部分无法响应触摸事件,需另行处理

先定义每个item的size

#define DIMATER 80 //宽高

#define PADDING 20 //间距

设置scrollview的宽度

self.scrolWidth.constant = DIMATER+2*PADDING;

设置content view的宽度为scrollview的N倍即可

int total = 10;

self.contentWidth.constant = self.scrolWidth.constant *total;

- (void)scrollViewWillEndDragging:(UIScrollView *)scrollView withVelocity:(CGPoint)velocity targetContentOffset:(inout CGPoint *)targetContentOffset{

    CGFloat targetX = targetContentOffset->x;
int index = roundf(targetX/(PADDING*2+DIMATER));
//直接改变目标x坐标
targetContentOffset->x = index*(PADDING*2+DIMATER); }

视图的布局:

 for (UIView *view in self.conentView.subviews) {
[view removeFromSuperview];
}
for (int i = 0; i < total; i ++) {
CGFloat y = (self.scrolView.frame.size.height - DIMATER)/2;
CGFloat x = i * ( DIMATER+2*PADDING ) + PADDING;
UILabel *lab = [UILabel new];
lab.frame = CGRectMake(x, y, DIMATER, DIMATER);
lab.text = [NSString stringWithFormat:@"#%d",i];
lab.textColor = [UIColor blackColor];
lab.textAlignment = NSTextAlignmentCenter;
lab.backgroundColor = [UIColor greenColor];
lab.layer.cornerRadius = DIMATER/2;
lab.layer.masksToBounds = true;
[self.conentView addSubview:lab];
}

效果:

实现多控制器的重用:

思路:加载屏幕左中右三个控制器,这样技能实现重用控制器的目的,而且在滑动的时候由于左右的控制器已经加载,用户体验会更加好

@property (strong, nonatomic) NSMutableArray* visibleItemsArr; //当前可用

@property (strong, nonatomic) NSMutableArray* reuseItemsArr;//缓存控制器

直接上代码:

- (void)setPages{
int total = 10;//假设共有十个控制器
//scrollview的子视图content view管理各个控制器的view
self.contentViewWidthConstraint.constant = self.scrolView.frame.size.width*total;
[self.view setNeedsLayout];
[self.view layoutIfNeeded];
}
- (void)loadPages:(NSInteger)page{
//加载左中右三个控制器
NSMutableArray *waitToLoadsArr = [@[@(page-1),@(page),@(page+1)] mutableCopy];
NSMutableArray *waitEnqueArr = [NSMutableArray array];
for (ReuseItemController *itemCon in self.visibleItemsArr) {
if ([waitToLoadsArr containsObject:itemCon.pageIndex]) {//无需再次加载
[waitToLoadsArr removeObject:itemCon.pageIndex];
}
else{//不需要加载了 放入缓存 [waitEnqueArr addObject:itemCon];
}
}
//从可用中移除 放入缓存
for (ReuseItemController *itemCon in waitEnqueArr) {
[itemCon.view removeFromSuperview];
[self.visibleItemsArr removeObject:itemCon];
[self.reuseItemsArr addObject:itemCon];
}
for (NSNumber *page in waitToLoadsArr) {
[self addController:page.integerValue];
} } - (void)addController:(NSInteger)page{
if (page<0 || page>(10-1)) {
return;
}
ReuseItemController *itemCon = [self dequePage:page];
itemCon.pageIndex = @(page);
itemCon.view.frame = CGRectMake(page*self.scrolView.frame.size.width, 0, self.scrolView.frame.size.width, self.scrolView.frame.size.height);
[self.contentView addSubview:itemCon.view];
[itemCon reloadData];
[self.visibleItemsArr addObject:itemCon];
}
//从缓存池中取 ,没有就直接新建
- (ReuseItemController*)dequePage:(NSInteger)page{
ReuseItemController *itemCon = [self.reuseItemsArr firstObject];
static int instance = 0;//标记是第几个实例 本例中instance = 0 ,1 ,2共三个
if (itemCon) {
[self.reuseItemsArr removeObject:itemCon];//rmeove
}
else { itemCon = [ReuseItemController reuseItemController];
itemCon.instanceNum = @(instance);
instance++;
[itemCon willMoveToParentViewController:self];
//当前控制器作为子控制的容器
[self addChildViewController:itemCon];
[itemCon didMoveToParentViewController:self];
} return itemCon;
}
//
- (void)scrollViewDidScroll:(UIScrollView *)scrollView{
int index = roundf(scrollView.contentOffset.x/self.scrolView.frame.size.width);
[self loadPages:index]; }

ScrollView小记的更多相关文章

  1. [原]Paste.deploy 与 WSGI, keystone 小记

    Paste.deploy 与 WSGI, keystone 小记 名词解释: Paste.deploy 是一个WSGI工具包,用于更方便的管理WSGI应用, 可以通过配置文件,将WSGI应用加载起来. ...

  2. ScrollView嵌套ListView,GridView数据加载不全问题的解决

    我们大家都知道ListView,GridView加载数据项,如果数据项过多时,就会显示滚动条.ScrollView组件里面只能包含一个组件,当ScrollView里面嵌套listView,GridVi ...

  3. Android ScrollView监听滑动到顶部和底部的两种方式(你可能不知道的细节)

    Android ScrollView监听滑动到顶部和底部,虽然网上很多资料都有说,但是不全,而且有些细节没说清楚 使用场景: 1. 做一些复杂动画的时候,需要动态判断当前的ScrollView是否滚动 ...

  4. React-Native学习系列(二) Image和ScrollView

    接下来,我们接着(一)继续讲,今天我们学习的是Image组件和ScrollView组件. Image组件 Image:一个用于显示多种不同类型图片的React组件.那么要如何使用呢? 引入本地图片: ...

  5. iOS学习笔记——滚动视图(scrollView)

    滚动视图:在根视图中添加UIScrollViewDelegate协议,声明一些对象属性 @interface BoViewController : UIViewController<UIScro ...

  6. 实现下来ScrollView放大轮播图

    创建工程,创建一个UIScrollView属性,并遵循其协议: #define kWidth self.view.frame.size.width//屏幕宽 #define kHeight self. ...

  7. React Native之 ScrollView介绍和使用

    前言 学习本系列内容需要具备一定 HTML 开发基础,没有基础的朋友可以先转至 HTML快速入门(一) 学习 本人接触 React Native 时间并不是特别长,所以对其中的内容和性质了解可能会有所 ...

  8. ScrollView分栏视图分析

    代码精华部分如下: //1.添加scrollView /* 1). 添加一个scrollView; 2).创建关注.热门.附近三个控制器. 3). 存储它们的名字到数组中,遍历并放到本控制器里. 4) ...

  9. IOS实现自动循环滚动广告--ScrollView的优化和封装

    一.问题分析 在许多App中,我们都会见到循环滚动的视图,比如广告,其实想实现这个功能并不难,用ScrollView就可以轻松完成,但是在制作的过程中还存在几个小问题,如果能够正确的处理好这些小问题, ...

随机推荐

  1. Flutter设置图片为正方形

    AspectRatio( aspectRatio:/, child:Image.network("src") )

  2. MyBatis原理总结(前期准备)

    1.不同框架解决不用问题,框架封装了很多细节,开发者可以使用简单的方式实现功能. 2.三层架构: 1.表现层  2.业务层  3.持久层  都有相应的处理框架. 3.持久层的技术解决方案: JDBC技 ...

  3. 创建Dockerfile

    https://mp.weixin.qq.com/s?__biz=MzU0Mzk1OTU2Mg==&mid=2247483900&idx=1&sn=584962b8b6f24c ...

  4. 单元测试-测试技术(Unit Test)

    1.1白盒测试和单元测试的区别的论述: 1) 单元测试和白盒测试是不同的,虽然单元测试和白盒测试都是关注功能,虽然他们都需要代码支持,但是级别不同, 白盒测试关注的是类中一个方法的功能是更小的单位,但 ...

  5. json 反序列化成键值对

    通过JsonConvert.DeserializeObject<Dictionary<string, object>>(string value)方法反序列化为字典数据,在通过 ...

  6. 【网络开发】winsock组播

    https://my.oschina.net/lopo/blog/260685 //客户端 #include <winsock2.h> #include <stdio.h> # ...

  7. Python 绘图库Matplotlib入门教程

    0 简单介绍 Matplotlib是一个Python语言的2D绘图库,它支持各种平台,并且功能强大,能够轻易绘制出各种专业的图像. 1 安装 pip install matplotlib 2 入门代码 ...

  8. Java中关于时间日期格式保存到mysql的问题

    首先在设置数据库的时间日期字段的时候要先确定好采用何种类型,DATETIME. TIMESTAMP.DATE.TIME.YEAR. 其中datetime.time用的比较多,对应java中生成的poj ...

  9. (零)linux 学习 -- 从 shell 开始

    The Linux Command Line 读书笔记 - 部分内容来自 http://billie66.github.io/TLCL/book/chap02.html 文章目录 前言 什么是 she ...

  10. (十七)springMvc 对表单提交的日期以及JSON中的日期的参数绑定

    文章目录 前言 `Ajax`提交表单数据 `Ajax`提交`JSON` 格式数据 解决输出JSON乱码的问题 控制JSON输出日期格式 小记 前言 springMVC 提供强大的参数绑定功能,使得我们 ...