在 React Native 中,ListView 组件是非常常用的一个组件。它用于展示大量的数据项,支持滚动、下拉刷新、上拉加载等功能,在 App 开发中的作用不可替代。本文将对 React Native ListView 进行总结和梳理,旨在帮助开发者更好地理解和使用这个组件。
基本用法
ListView 最基本的用法就是列表展示数据。我们可以通过设置数据源和渲染子组件来实现。例如下面这个例子展示了如何使用 ListView 显示一个简单的列表:
import React, { Component } from 'react'; import { AppRegistry, ListView, Text, View } from 'react-native'; export default class MyListView extends Component { constructor(props) { super(props); this.state = { dataSource: new ListView.DataSource({ rowHasChanged: (r1, r2) => r1 !== r2, }), }; } componentDidMount() { const data = [ { name: '张三', age: 18 }, { name: '李四', age: 20 }, { name: '王五', age: 22 }, ]; this.setState({ dataSource: this.state.dataSource.cloneWithRows(data), }); } render() { return ( <ListView dataSource={this.state.dataSource} renderRow={(rowData) => ( <View> <Text>{rowData.name}</Text> <Text>{rowData.age}</Text> </View> )} /> ); } } AppRegistry.registerComponent('MyListView', () => MyListView);
值得注意的是,在构造函数中我们设置了 dataSource,它是通过 ListView.DataSource 的一个实例来创建的。对于每一行的数据,我们需要判断它是否是相同的,这里通过 rowHasChanged 函数来实现。在 componentDidMount 生命周期方法中,我们将数据源设置为 ListView 的 dataSource 属性,并调用 cloneWithRows 方法将数据传入。
在 render 方法中,我们通过 renderRow 属性来指定每一行的渲染方式。这里我们使用了一个简单的 View 和 Text 来显示一条数据。
横向滚动
ListView 默认是纵向滚动的,如果我们需要横向滚动,可以设置 horizontal 属性为 true。例如:
<ListView horizontal={true} ... />
下拉刷新
当我们需要下拉刷新列表的时候,可以使用 RefreshControl 组件。RefreshControl 是一个内置的组件,具有下拉刷新的功能。例如:
import React, { Component } from 'react'; import { AppRegistry, ListView, Text, View, RefreshControl } from 'react-native'; export default class MyListView extends Component { constructor(props) { super(props); this.state = { dataSource: new ListView.DataSource({ rowHasChanged: (r1, r2) => r1 !== r2, }), refreshing: false, }; } componentDidMount() { const data = [ { name: '张三', age: 18 }, { name: '李四', age: 20 }, { name: '王五', age: 22 }, ]; this.setState({ dataSource: this.state.dataSource.cloneWithRows(data), }); } _onRefresh() { this.setState({ refreshing: true }); setTimeout(() => { const data = [ { name: '张三', age: 18 }, { name: '李四', age: 20 }, { name: '王五', age: 22 }, { name: '赵六', age: 24 }, { name: '钱七', age: 26 }, ]; this.setState({ dataSource: this.state.dataSource.cloneWithRows(data), refreshing: false, }); }, 2000); } render() { return ( <ListView dataSource={this.state.dataSource} renderRow={(rowData) => ( <View> <Text>{rowData.name}</Text> <Text>{rowData.age}</Text> </View> )} refreshControl={ <RefreshControl refreshing={this.state.refreshing} onRefresh={this._onRefresh.bind(this)} /> } /> ); } } AppRegistry.registerComponent('MyListView', () => MyListView);
在这个例子中,我们新增了一个 refreshing 状态,用于标记是否正在刷新数据。在 _onRefresh 方法中,我们将 refreshing 置为 true,模拟开始刷新数据;2 秒后,我们随机生成 5 条新的数据,并将 refreshing 置为 false,标记刷新结束。
在 ListView 的属性中,我们新增了一个 refreshControl,它可以用来指定 RefreshControl 的一些属性,如 refreshing 和 onRefresh 等。
上拉加载
和下拉刷新类似,当需要在 ListView 中添加上拉加载更多的功能时,我们可以使用 onEndReached 属性和 onEndReachedThreshold 等属性来实现。例如:
import React, { Component } from 'react'; import { AppRegistry, ListView, Text, View, RefreshControl } from 'react-native'; export default class MyListView extends Component { constructor(props) { super(props); this.state = { dataSource: new ListView.DataSource({ rowHasChanged: (r1, r2) => r1 !== r2, }), refreshing: false, hasMore: true, data: [ { name: '张三', age: 18 }, { name: '李四', age: 20 }, { name: '王五', age: 22 }, ], }; } _onRefresh() { this.setState({ refreshing: true }); setTimeout(() => { const data = [ { name: '张三', age: 18 }, { name: '李四', age: 20 }, { name: '王五', age: 22 }, ]; this.setState({ dataSource: this.state.dataSource.cloneWithRows(data), refreshing: false, hasMore: true, data: data, }); }, 2000); } _loadMore() { if (!this.state.hasMore) { return; } // 模拟异步获取数据 setTimeout(() => { const data = [ { name: '赵六', age: 24 }, { name: '钱七', age: 26 }, ]; const newData = this.state.data.concat(data); const hasMore = newData.length < 11 ? true : false; this.setState({ dataSource: this.state.dataSource.cloneWithRows(newData), hasMore: hasMore, data: newData, }); }, 2000); } renderFooter() { if (!this.state.hasMore) { return ( <View style={{ alignItems: 'center', paddingVertical: 10 }}> <Text style={{ color: '#ccc' }}>没有更多了~</Text> </View> ); } return null; } render() { return ( <ListView dataSource={this.state.dataSource} renderRow={(rowData) => ( <View> <Text>{rowData.name}</Text> <Text>{rowData.age}</Text> </View> )} refreshControl={ <RefreshControl refreshing={this.state.refreshing} onRefresh={this._onRefresh.bind(this)} /> } onEndReached={this._loadMore.bind(this)} onEndReachedThreshold={10} renderFooter={this.renderFooter.bind(this)} /> ); } } AppRegistry.registerComponent('MyListView', () => MyListView);
在这个例子中,我们新增了一个 hasMore 状态,用于标记是否还有更多数据可供加载。在 _loadMore 方法中,我们模拟异步获取数据,并将新数据通过 concat 方法和原始数据合并,再通过 cloneWithRows 方法更新 DataSource。如果新数据的长度小于 11,说明还有更多数据,否则已经加载完毕。
在 ListView 的属性中,我们新增了 onEndReached 和 onEndReachedThreshold 两个属性。当用户滚动到距离底部 10 的位置时,就会触发 _loadMore 方法。同时,我们通过 renderFooter 属性来指定底部的渲染方式,根据 hasMore 状态来判断是否需要显示“没有更多了~”的提示。
总结
React Native ListView 组件是 App 开发中常用的组件之一,有多种使用场景。本文对其常见的用法进行了详细的总结和梳理,包括基本用法、横向滚动、下拉刷新、上拉加载等。希望本文能够帮助开发者更好地了解和掌握 ListView 组件,提高工作效率。
来源:JavaScript中文网 ,转载请注明来源 本文地址:https://www.javascriptcn.com/post/65a8d9e6add4f0e0ff216004