react native基于FlatList下拉刷新上拉加载实现代码示例


Posted in Javascript onSeptember 30, 2018

react native 的上拉加载一直困扰着自己,一直用的第三方组件,但是可维护性不高,而且也不太好用,最近工作没那么忙,就研究下了官方的FlatList,做出来的成果,比第三方组件流畅度高好多,而且也很好用

官方介绍:https://reactnative.cn/docs/flatlist/

下面是效果图:

react native基于FlatList下拉刷新上拉加载实现代码示例

ios效果图

react native基于FlatList下拉刷新上拉加载实现代码示例

android效果图

总体思路就是:就是计算屏幕高度,然后减去导航的头部,根据列表高度计算出每页的个数,然后向上取整。这样做的目的是:防止不满屏状态下的,onEndReached函数的主动触发。

方法实现:

//满屏页面判断
 fullScreenJusting(ItemHeight) {
  const screnHeight = screnInfo.size.height;   //屏幕高度
  //计算列表个数
  const listNum = (screnHeight - 40) / ItemHeight;
  return Math.ceil(listNum);
 }

下拉刷新用的是 RefreshControl

官网地址:https://reactnative.cn/docs/refreshcontrol/#progressbackgroundcolor

具体代码:

import React, { Component } from 'react';
import {
 View,
 Text,
 Image,
 StyleSheet,
 FlatList,
 RefreshControl,
 ActivityIndicator,
} from 'react-native';
import { SafeAreaView } from 'react-navigation';
import screnInfo from '../utils/View';
import BaseStyle from '../constants/Style';
import { QUESTION_LIST } from '../constants/Api';
import { form_req } from '../utils/Request';

export default class TestScreen extends Component {
 constructor(props) {
  super(props);
  this.state = {
   data: [
   ],
   refreshing: false,
   fresh: true,
   animating: true,
   nomore: false,
   pageSize: 0,
   pageNumber: 1,
  };
 }
 componentDidMount() { //初始化的时候要判断长度 控制上拉加载

  const ListNums = this.fullScreenJusting(50);
  this.setState({
   pageSize: ListNums
  })
  this.onEndReachedCalled = false;
   this.getOrderList(ListNums, 1, true);

 }
 //满屏页面判断
 fullScreenJusting(ItemHeight) {
  const screnHeight = screnInfo.size.height;   //屏幕高度
  //计算列表个数
  const listNum = (screnHeight - 40) / ItemHeight;
  return Math.ceil(listNum);
 }

 getOrderList(ListNums, pageNumber, fresh) {
  let nomore;
  form_req(QUESTION_LIST, {
   page: pageNumber,
   perpage: ListNums,
  }).then(res => {
   if (res.code == 200) {
    const item = res.data;
    if (item.length < ListNums) {
     nomore = true
    } else {
     nomore = false
    }
    if (fresh) {
     this.setState({
      data: item,
      nomore: nomore
     })
     
    } else {
     this.setState({
      data: this.state.data.concat(item),
      nomore: nomore,
     })
    }
    // this.onEndReachedCalledDuringMomentum = true;

   } else {

   }
  });
 }

 renderItem = item => {
  return (
   <View style={styles.item} key={item.id}>
    <Text>{item.name}</Text>
   </View>
  );
 };
 //列表线
 ItemSeparatorComponent = () => {
  return <View style={styles.baseLine} />;
 };
 //头部
 ListHeaderComponent = () => { };
 //尾部
 ListFooterComponent = () => {
  return (
   <View style={styles.bottomfoot}>
    {
     this.state.data.length != 0 ?
      this.state.nomore ? (
       <Text style={styles.footText}>- 我是有底线的 -</Text>
      ) : (
        <View style={styles.activeLoad}>
         <ActivityIndicator size="small" animating={this.state.animating} />
         <Text style={[styles.footText, styles.ml]}>加载更多...</Text>
        </View>
       )
      :
      null
    }

   </View>
  );
 };
 //为空时
 ListEmptyComponent() {
  return (
   <View style={styles.noListView}>
    {/* <Image
     style={styles.noListImage}
     source={require('../images/status/order_no_record.png')}
    /> */}
    <Text style={styles.NoListText}>暂无订单</Text>
   </View>
  );
 }
 _keyExtractor = (item,index) => item.id;

 _onEndReached = () => {
  if (!this.state.nomore && this.onEndReachedCalled ) {
   this.getOrderList(this.state.pageSize, ++this.state.pageNumber, false);
  }
  this.onEndReachedCalled=true;

 };
 _onRefresh() {
  this.setState({ nomore: false, pageNumber: 1 }, () => {
   this.getOrderList(this.state.pageSize, 1, true);
  })

 }

 render() {
  return (
   <SafeAreaView style={BaseStyle.flex}>
    <View style={styles.listConten}>
     <FlatList
      data={this.state.data}
      keyExtractor={this._keyExtractor}
      onEndReached={this._onEndReached}
      refreshing={true}
      renderItem={({ item }) => this.renderItem(item)}
      ItemSeparatorComponent={this.ItemSeparatorComponent}
      ListEmptyComponent={this.ListEmptyComponent}
      ListFooterComponent={this.ListFooterComponent}
      onEndReachedThreshold={0.1}
      refreshControl={
       <RefreshControl
        refreshing={this.state.refreshing}
        colors={['#ff0000', '#00ff00', '#0000ff']}
        progressBackgroundColor={"#ffffff"}
        onRefresh={() => {
         this._onRefresh();
        }}
       />
      }
     />
    </View>
   </SafeAreaView>
  );
 }
}

const styles = StyleSheet.create({
 listConten: {
  flex: 1,
  backgroundColor: '#ffffff',
 },
 item: {
  flexDirection: 'row',
  justifyContent: 'center',
  alignItems: "center",
  backgroundColor: '#ffffff',
  height: 50,
 },
 baseLine: {
  width: screnInfo.size.width,
  height: 1,
  backgroundColor: '#eeeeee',
 },
 noListView: {
  width: screnInfo.size.width,
  height: screnInfo.size.height - 140,
  justifyContent: 'center',
  alignItems: 'center',
 },
 NoListText: {
  marginTop: 15,
  fontSize: 18,
  color: '#999999',
 },
 noListImage: {
  width: 130,
  height: 140,
 },
 bottomfoot: {
  flexDirection: 'row',
  justifyContent: 'center',
  alignItems: 'center',
  padding: 10,
 },
 footText: {
  marginTop: 5,
  fontSize: 12,
  color: '#999999',
 },

 activeLoad: {
  flexDirection: 'row',
  justifyContent: 'center',
  alignItems: 'center',
 },
 ml: {
  marginLeft: 10,
 },
});

这里的坑就是:当初始化进来页面的时候 上拉会主动触发,所以这里加了一个开关 this.onEndReachedCalled = false; 初始化给一个false 当触发了 设为true,放在调取接口之后

react native基于FlatList下拉刷新上拉加载实现代码示例

代码都很简单易懂~ 有什么不懂的,或者有什么问题请留言,希望对大家的学习有所帮助,也希望大家多多支持三水点靠木。

Javascript 相关文章推荐
神奇的代码 通杀各种网站-可随意修改复制页面内容
Jul 17 Javascript
jquery 插件开发备注
Aug 27 Javascript
json对象转字符串如何实现
Dec 02 Javascript
javascript判断非数字的简单例子
Jul 18 Javascript
jQuery响应鼠标事件并隐藏与显示input默认值
Aug 24 Javascript
jQuery插件ajaxFileUpload实现异步上传文件效果
Apr 14 Javascript
jquery制作属于自己的select自定义样式
Nov 23 Javascript
js仿百度音乐全选操作
Jan 13 Javascript
详解 vue better-scroll滚动插件排坑
Feb 08 Javascript
傻瓜式解读koa中间件处理模块koa-compose的使用
Oct 30 Javascript
JavaScript基础之this和箭头函数详析
Sep 05 Javascript
JavaScript中遍历的十种方法总结
Dec 15 Javascript
关于AngularJS中ng-repeat不更新视图的解决方法
Sep 30 #Javascript
angular5 子组件监听父组件传入值的变化方法
Sep 30 #Javascript
小程序视频或音频自定义可拖拽进度条的示例代码
Sep 30 #Javascript
angularjs1.5 组件内用函数向外传值的实例
Sep 30 #Javascript
angular2 组件之间通过service互相传递的实例
Sep 30 #Javascript
详解如何webpack使用DllPlugin
Sep 30 #Javascript
浅谈angular2子组件的事件传递(任意组件事件传递)
Sep 30 #Javascript
You might like
PHP中error_reporting()函数的用法(修改PHP屏蔽错误)
2011/07/01 PHP
PHP实现仿Google分页效果的分页函数
2015/07/29 PHP
又拍云异步上传实例教程详解
2016/04/19 PHP
详细解读php的命名空间(一)
2018/02/21 PHP
php封装实现钉钉机器人报警接口的示例代码
2020/08/08 PHP
安装PHP扩展时解压官方 tgz 文件后没有configure文件无法进行配置编译的问题
2020/08/26 PHP
ASP.NET jQuery 实例1(在TextBox里面创建一个默认提示)
2012/01/13 Javascript
让页面上两个div中的滚动条(滑块)同步运动示例
2013/08/07 Javascript
js浮点数精确计算(加、减、乘、除)
2013/12/26 Javascript
js点击文本框后才加载验证码实例代码
2015/10/20 Javascript
js实现无缝滚动图(可控制当前滚动的方向)
2017/02/22 Javascript
d3.js入门教程之数据绑定详解
2017/04/28 Javascript
JS传播事件、取消事件默认行为、阻止事件传播详解
2017/08/14 Javascript
nodejs实现OAuth2.0授权服务认证
2017/12/27 NodeJs
vue的常用组件操作方法应用分析
2018/04/13 Javascript
webpack之引入图片的实现及问题
2018/10/08 Javascript
vue车牌号校验和银行校验实战
2019/01/23 Javascript
在Python中处理时间之clock()方法的使用
2015/05/22 Python
python中MethodType方法介绍与使用示例
2017/08/03 Python
致Python初学者 Anaconda入门使用指南完整版
2018/04/05 Python
pyside+pyqt实现鼠标右键菜单功能
2020/12/08 Python
Django项目中实现使用qq第三方登录功能
2019/08/13 Python
终于搞懂了Keras中multiloss的对应关系介绍
2020/06/22 Python
泰国演唱会订票网站:StubHub泰国
2018/02/26 全球购物
OSPF有什么优点?为什么OSPF比RIP收敛快?
2013/02/13 面试题
幼儿园家长会邀请函
2014/01/15 职场文书
员工薪酬福利制度
2014/01/17 职场文书
护士见习期自我鉴定
2014/02/08 职场文书
中药专业自荐信范文
2014/03/18 职场文书
数字化校园建设方案
2014/05/03 职场文书
教师专业自荐信
2014/05/31 职场文书
过程装备与控制工程专业求职信
2014/07/02 职场文书
售房协议书范本
2015/08/11 职场文书
Python学习之时间包使用教程详解
2022/03/21 Python
解决spring.thymeleaf.cache=false不起作用的问题
2022/06/10 Java/Android
使用pd.merge表连接出现多余行的问题解决
2022/06/16 Python