下拉刷新和UITableView的section headerView冲突的原因分析与解决方案
UITableView:下拉刷新和上拉加载更多
【转载请注明出处】
本文将说明具有多个section的UITableView在使用下拉刷新机制时会遇到的问题及其解决方案。
工程地址在帖子最下方,只需要代码的直拉到底即可。
【目录】
1、现象分析;
2、解决方案;
3、工程地址。
1、现象分析
当前的大多数支持下拉刷新的库,都是通过修改UIScrollView的contentInset实现的。
(可参见我的这篇帖子:UITableView:下拉刷新和上拉加载更多)
使用这种方法带来的问题是,当UITableView具有多个section时,依照上述方式使用下拉刷新,在加载过程中上滑,会出现样式跑版:

为了分析出问题所在,首先在控制台打印出正常状态下UITableView的所有子View :

比较各行的frame.origin.y可以看出,UITableView的section headerView是和cell一起,按顺序放入基类UIScrollView的内容View中的。
再看加载中时的情况:

从Pull2RefreshView的frame可以看出,此时UITableView的contentInset已经被修改为(65, 0, 0, 0)。而section headerView和各个cell的frame.origin.y不受影响,和预期一致。
最后看看在加载中状态下上滑时的情况,将UITableView上滑至上方图中所示情境,即第一行的cell刚刚好越过section headerView:

可以看到,section headerView的frame.origin.y发生了变化,它和第二个cell一起被放在了第一个cell的下方,即:
section headerView.frame.origin.y == firstCell.frame.origin.y + cellHeight;
继续上滑,可以看到section headerView.frame.origin.y不断变化,但在界面显示上,始终位于距离UITableView.frame.origin.y为65(即修改后contengInset.top的值)的位置,直到下一个section headerView出现时,才随着cell向上移动,如图:
【注意:不论在任何情况下,第一个cell的frame.origin.y始终为section headerView的高度,在本例中为23,即使它已经处于section headerView的上方】
2、解决方案
由此,可以粗略得出以下结论:
A、 section headerView和cell之间并不是简单的顺序摆放的关系,它们之间可以发生重叠;
B、 section headerView在界面上的显示位置由UITableView.contentInset.top决定,直到被下一个section headerView替代。
如此,想要在滑动时修改section headerView的显示位置,令其和cell一起移动,只需要动态地修改UITableView.contentInset.top即可,如下:
1 - (void)scrollViewDidScroll:(UIScrollView *)scrollView
2 {
3 //added 2013.11.28 动态修改headerView的位置
4 if (headerRefreshing)
5 {
6 if (scrollView.contentOffset.y >= -scrollView.contentInset.top
7 && scrollView.contentOffset.y < )
8 {
9 //注意:修改scrollView.contentInset时,若使当前界面显示位置发生变化,会触发scrollViewDidScroll:,从而导致死循环。
//因此此处scrollView.contentInset.top必须为-scrollView.contentOffset.y
scrollView.contentInset = UIEdgeInsetsMake(-scrollView.contentOffset.y, , , );
}
else if (scrollView.contentOffset.y == )//到0说明headerView已经在tableView最上方,不需要再修改了
{
scrollView.contentInset = UIEdgeInsetsZero;
}
}
//other code here...
}
Added 2014.7.24:
对于不需要提交到AppStore的应用,还有一个更简单的办法,即覆盖UITableView的私有方法。
- (BOOL)allowsHeaderViewsToFloat
{
return NO;
} - (BOOL)allowsFooterViewsToFloat
{
return NO;
}
3、工程地址
使用iOS 6.1 SDK编译,使用ARC。
地址:https://github.com/cDigger/CDPullToRefreshDemo
【参考】
1、Section Headers in UITableView when inset of tableview is changed
2、Change Default Scrolling Behavior of UITableView Section Header
下拉刷新和UITableView的section headerView冲突的原因分析与解决方案的更多相关文章
- UITableView:下拉刷新和上拉加载更多
[转载请注明出处] 本文将说明让UIScrollView支持"下拉刷新"和"上拉加载更多"的实现机制,并实现一个可用的tableView子类,以下主要以&quo ...
- IOS学习笔记34—EGOTableViewPullRefresh实现下拉刷新
移动应用开发中有这么一种场景,就是在列表中显示的数据刷新,有点击刷新按钮刷新的,也有现在最流行的由Twitter首先推出的下拉刷新功能,在IOS中,使用下拉刷新更新UITableView中的数据也用的 ...
- listview下拉刷新和上拉加载更多的多种实现方案
listview经常结合下来刷新和上拉加载更多使用,本文总结了三种常用到的方案分别作出说明. 方案一:添加头布局和脚布局 android系统为listview提供了addfootview ...
- ListView装上拉电阻下拉刷新
主要用到了这个几个文件.MainActivity是界面的Activity,MyAdapter是ListView的自己定义适配,MyListView是自己定义带头部LIistView,假设仅仅须要上拉载 ...
- 【转载】Android中ListView下拉刷新的实现
在网上看到一个下拉刷新的例子,很的很棒,转载和更多的人分享学习 原文:http://blog.csdn.net/loongggdroid/article/details/9385535 ListVie ...
- Android中ListView下拉刷新的实现
ListView中的下拉刷新是非常常见的,也是经常使用的,看到有很多同学想要,那我就整理一下,供大家参考.那我就不解释,直接上代码了. 这里需要自己重写一下ListView,重写代码如下: packa ...
- ListView下拉刷新上拉加载更多实现
这篇文章将带大家了解listview下拉刷新和上拉加载更多的实现过程,先看效果(注:图片中listview中的阴影可以加上属性android:fadingEdge="none"去掉 ...
- UITableView与UISearchController搜索及上拉加载,下拉刷新
#import "ViewController.h" #import "TuanGouModel.h" #import "TuanGouTableVi ...
- IOS UITableView下拉刷新和上拉加载功能的实现
在IOS开发中UITableView是非常常用的一个功能,而在使用UITableView的时候我们经常要用到下拉刷新和上拉加载的功能,今天花时间实现了简单的UITableView的下拉刷新和上拉加载功 ...
随机推荐
- QXmlStreamReader/QXmlStreamWriter实现Qt下xml文件读写
版权声明:若无来源注明,Techie亮博客文章均为原创. 转载请以链接形式标明本文标题和地址: 本文标题:QXmlStreamReader/QXmlStreamWriter实现Qt下xml文件读写 ...
- 软工实践团队展示——WorldElite
软工实践团队展示--WorldElite 本次作业链接 团队成员 031602636许舒玲(组长) 031602237吴杰婷 031602634吴志鸿 081600107傅滨 031602220雷博浩 ...
- Win10 版本情况 201810
- PHP中与类和对象有关的几个系统函数
与类有关的系统函数: class_exists(“类名”), 判断一个类是否存在(是否定义过) interface_exists(“接口名”), 判断一个接口是否存在(是否定义过) get_class ...
- oracle 关于表数据delete 后如何恢复
今天在PL/SQL中操作不小心删掉了某个表的部分数据,这可吓坏了本猿:于是悄悄的打开电脑,赶紧找度娘帮忙.经过度娘的小爬虫帮助,几分钟就把数据恢复了. 那么表数据delete掉后怎么恢复呢? 用fla ...
- 第78天:jQuery事件总结(一)
jQuery事件总结(一) 现在就一点一点积累自己的知识体系,记录自己学到的和自己所理解的jQuery. JavaScript和HTML之间的交互式通过用户和浏览器操作页面时引发的事件机制来处理 ...
- 【刷题】BZOJ 4650 [Noi2016]优秀的拆分
Description 如果一个字符串可以被拆分为 AABBAABB 的形式,其中 AA 和 BB 是任意非空字符串,则我们称该字符串的这种拆分是优秀的.例如,对于字符串 aabaabaa,如果令 A ...
- 使用adb命令查看apk版本
adb devices (显示连接的设备) adb root (获取手机root权限) adb remount (重新挂载系统分区,使系统分区重新可写) adb shell (进入目标设备的L ...
- 解题:ZJOI 2006 游戏排名系统
题面 跟i207M学了学重载运算符后找前驱后继,然后就是练练无旋树堆 #include<map> #include<cstdio> #include<string> ...
- 使用log4net将日志文件输出为csv格式
我们在编写程序时,会在程序运行过程中记录一些日志.log4net作为一款经久耐用的日志组件,值得我们信赖.在中小型公司中,往往没有专业的日志服务器来处理应用程序产生的日志,而格式化不好的日志文件又为上 ...