不借助第三方插件利用ScrollView自身delegate实现下拉刷新和上拉加载

下拉刷新功能基本上在所有的app中都会被用到,而且这个功能已经被apple集成进去了,不过必须得是在tableViewController中才有,是一个叫做UIRefreshControl的控件,想看效果可以看手机QQ上面联系人列表下拉后的刷新。这里不多介绍。

本篇blog主要介绍如何在scrollview中实现下拉刷新的效果。因为有些时候我们可能更多地希望直接在scrollview中展现,而不是一定要局限于tableviewcontroller。

当然网上有很多下拉刷新和上拉加载的第三方控件,但是我这个人还是喜欢用系统原生API自己来做,一方面更能把原理吃透,另一方面方便自己定义。

好了,废话不多说了,直接上代码:

准备工作:

// 设置下拉刷新的process和label
    self.indicatorView = [[UIActivityIndicatorView alloc]initWithFrame:CGRectMake(self.frame.size.width/2 - 50, -25, 20, 20)];
    [self.indicatorView setColor:[UIColor blackColor]];
    self.pullRefreshLabel = [[UILabel alloc]initWithFrame:CGRectMake(self.frame.size.width/2 -20, -30, 90, 30)];
    self.pullRefreshLabel.font = [UIFont fontWithName:@"heiti SC" size:14];
    [self.pullRefreshLabel setText:@"下拉刷新"];
    [self.scroll_view addSubview:self.indicatorView];
    [self.scroll_view addSubview:self.pullRefreshLabel];
    [self.scroll_view bringSubviewToFront:self.indicatorView];
    [self.scroll_view bringSubviewToFront:self.pullRefreshLabel];

这里的准备工作其实就是在scrollview里面先加入一个activityIndicator和一个label

下拉刷新

// 下拉刷新
- (void)scrollViewWillBeginDecelerating:(UIScrollView *)scrollView{
    if (scrollView.contentOffset.y < -50 ) {
        [UIView animateWithDuration:1.0 animations:^{
            //  frame发生偏移,距离顶部50的距离(可自行设定)
            [scrollView setContentInset:UIEdgeInsetsMake(30, 0, 0, 0)];
            [self.indicatorView startAnimating];
        } completion:^(BOOL finished) {
            // 发起网络请求
            ...
            [self.indicatorView stopAnimating];
            [self.pullRefreshLabel setText:@"下拉刷新"];
            [scrollView setContentInset:UIEdgeInsetsMake(0, 0, 0, 0)];
            // 将当前页面置为1
            currentPage = 1;
        }];
    }
}

- (void)scrollViewDidScroll:(UIScrollView *)scrollView{
    // 保持indecator的位置一直在顶端
    if( scrollView.contentOffset.y < -50){
        [self.pullRefreshLabel setText:@"松开刷新"];
        self.indicatorView.frame = CGRectMake(self.frame.size.width/2-50, scrollView.contentOffset.y+20 ,30, 30);
        self.pullRefreshLabel.frame = CGRectMake(self.frame.size.width/2-20, scrollView.contentOffset.y+20, 100, 30);
    }else{
        self.indicatorView.frame = CGRectMake(self.frame.size.width/2-50, -30 ,30, 30);
        self.pullRefreshLabel.frame = CGRectMake(self.frame.size.width/2-20, -30, 100, 30);
    }
}

注意两个代理不要用错了。一个是WillBeginDecelerating ,一个是didScroll

willBeginDecelerating就是我们往下拉scrollview然后松手的时候,这个代理方法会去检测当前scrollview的contentoffset,然后根据下拉的程度决定是否进行刷新操作。这里我定义的阈值是50

然后为了使提示刷新的label和activityIndicator保持在一个固定的高度,就是不随着scrollview的往下拉而一直往下走,在didScroll代理里面计算了一下它们的位置。

上拉加载:

/ 上拉继续获取
- (void)scrollViewDidEndDragging:(UIScrollView *)scrollView willDecelerate:(BOOL)decelerate{
    /*
     *  关键-->
     *  scrollView一开始并不存在偏移量,但是会设定contentSize的大小,所以contentSize.height永远都会比contentOffset.y高一个手机屏幕的
     *  高度;上拉加载的效果就是每次滑动到底部时,再往上拉的时候请求更多,那个时候产生的偏移量,就能让contentOffset.y + 手机屏幕尺寸高大于这
     *  个滚动视图的contentSize.height
     */
    if (scrollView.contentOffset.y + scrollView.frame.size.height >= scrollView.contentSize.height+50) {
//        [UIView commitAnimations];
        [UIView animateWithDuration:1.0 animations:^{
            //  frame发生的偏移量,距离底部往上提高50(可自行设定)
            scrollView.contentInset = UIEdgeInsetsMake(0, 0, 50, 0);
        } completion:^(BOOL finished) {
            scrollView.contentInset = UIEdgeInsetsMake(0, 0, 0, 0);
            // 发送网络请求
            currentPage ++;
            ...
        }];
    }
}
时间: 2024-10-04 03:17:25

不借助第三方插件利用ScrollView自身delegate实现下拉刷新和上拉加载的相关文章

Android下拉刷新库,利用viewdraghelper实现,集成了下拉刷新,底部加载更多,数据初始加载显示loading等功能

项目Github地址:https://github.com/sddyljsx/pulltorefresh Android下拉刷新库,利用viewdraghelper实现. 集成了下拉刷新,底部加载更多,以及刚进入加载数据的loadview.包括了listview与gridview的改写. 效果1: 效果2: 效果3: 效果4: 效果5: 使用说明: imageList=(ListView)findViewById(R.id.image_list); imageAdapter=new ImageA

Android实现下拉刷新和上拉加载更多的RecyclerView和ScrollView

PullRefreshRecyclerView.java /** * 类说明:下拉刷新上拉加载更多的RecyclerView * Author: gaobaiq * Date: 2016/5/9 18:09 */ public class PullRefreshRecyclerView extends PullRefreshView { /** * 内置的RecyclerView: */ private RecyclerView mRecyclerView; /** * 可见的最后一个item

下拉刷新和上拉加载更多(第三方框架MJRefresh)

1 #import "RootViewController.h" 2 #import "MJRefresh.h" 3 @interface RootViewController ()<UITableViewDataSource,UITableViewDelegate,MJRefreshBaseViewDelegate> 4 { 5 UITableView *_tableView ; 6 NSMutableArray *datas; 7 MJRefresh

Android ScrollView和ListView联用,且ListView可以下拉刷新和上拉加载

ScrollView嵌套listView且ListView可以实现上拉加载. 由于代码太长,在此只提供实现思路: 先不说上拉加载的事,咱们先回想一下,ScrollView和LsitView联用,时的解决方案.1.禁用ListView的上下滑动,2.计算ListView每一项的高度,3.自定义ListView.列出后发现每一种方案基本上都是把ListView的滑动禁用掉了,如果把ListView的上下滑动禁用掉了何来上拉加载和下拉刷新之说,由此我们得出结论,如果想实现ScrollView和List

react native Expo完全基于ScrollView实现的下拉刷新和上拉触底加载

我直接封装成了一个组件 props参数为 static propTypes = { style:PropTypes.object, // 样式 refreshing:PropTypes.bool.isRequired,//是否开始下拉刷新动画 refreshBegin: PropTypes.func,// 开始下拉刷新回调 scrollEnd: PropTypes.func,// 触底回调 }; 使用示例 import React from 'react'; import { View, } f

vue10行代码实现上拉翻页加载更多数据,纯手写js实现下拉刷新上拉翻页不引用任何第三方插件

vue10行代码实现上拉翻页加载更多数据,纯手写js实现下拉刷新上拉翻页不引用任何第三方插件/库 一提到移动端的下拉刷新上拉翻页,你可能就会想到iScroll插件,没错iScroll是一个高性能,资源占用少,无依赖,多平台的javascript滚动插件.iScroll不仅仅是 滚动.它可以处理任何需要与用户进行移动交互的元素.在你的项目中包含仅仅4kb大小的iScroll,你的项目便拥有了滚动,缩放,平移,无限滚动,视差滚动,旋转功能.iScroll的强大毋庸置疑,本人也非常欢迎大家使用iScr

使用live delegate on来解决js对后加载的html失效的问题

今天要写一个前端的东西.每多学一点知识,就可以少写几行代码.几十行代码.几个文件量的代码--这是真的.一直对前端的研究都是停留在遇到问题百度谷歌答案的做法.今天遇到这样一个问题:已经写好的js代码,对ajax加载的html失效了. 用好几组关键字都没有找到答案,最后这组帮我找到了解答的办法: javascript not work on ajax content 很幸运,我来到了:http://stackoverflow.com/questions/10161938/jquery-functio

eclipse(有ADT插件)启动,出现Android SDK Content Loader 0%,加载不了问题的解决

系统:Win8.1-32位 软件:ADT-Bundle  23.0 我碰到的问题是每次开启都无法加载,不管是重启系统还是其他情况. 找到两种解决方法: 1.删掉workspace下的.metadata\.plugins\org.eclipse.core.resources\.projects文件夹,重启eclipse. 2.删掉C:\Users\用户名\.android文件夹下的所有内容,重启eclipse. 第一种方法我测试后还是没有解决,按照第二种方法做之后就顺利解决了.希望大家尽快解决问题

android 常用第三方插件收藏

1.android-vertical-slide-view: 仿照淘宝和聚美优品,在商品详情页,向上拖动时,可以加载下一页.使用ViewDragHelper,滑动比较流畅. 2.Android-MaterialRefreshLayout :这是一个下拉刷新控件,它比SwipeRefreshLayout更漂亮和强大 3.TwinklingRefreshLayout(推荐使用):支持下拉刷新和上拉加载的RefreshLayout,自带越界回弹效果,支持RecyclerView,AbsListView