onEndReached导致列表视图上显示多个项目

时间:2018-04-20 07:41:07

标签: javascript reactjs react-native ecmascript-6 react-native-android

我最终在列表视图中复制了多个项目,因为出于某种原因,使用相同的参数调用了api' page = 1'多次,onEndReached在没有滚动的情况下自动触发。

我尝试过这样的事情:

 componentDidMount() {
        this.fetchCategories();
 }


fetchCategories() {
   this.setState({isLoading: true});
   categoryApi.getOne(this.state.page).then(response => {
       if (response.data) {
           this.setState({
               categories: this.state.categories.concat(response.data.data),
               isLoading: false,
           });
       } else {
           this.setState({isLoading: false});
           Alert.alert(
               'Something wrong happened!',
               'My Alert Msg',
               [],
               {cancelable: true}
           )
       }
   }); }

this.state = {
     isLoading: false,
     categories: [],
     page: 1,
};

showMore = () => {
    this.setState({page: this.state.page + 1});
    this.fetchCategories();
}; 



<FlatList
  data={this.state.categories}
  extraData={this.state}
  renderItem={(rowData) => <CategoryItem navigate={navigate} item={rowData}/>}
  onEndReached={this.showMore}
  keyExtractor={(item, index) => index}
 />

我尝试了什么: 将showMore更改为:

showMore = () => {
        // console.log("End reached.");
        this.setState(prevState =>({
            page: prevState + 1
        }), () => {
            this.fetchCategories();
        });
}; 

我仍然可以看到页面重复的项目= 1,api仍然被参数页面= 1多次调用!

任何人都知道如何避免这样的事情?

1 个答案:

答案 0 :(得分:1)

您必须将onEndReachedThresholdonEndReached结合使用,以防止发生奇怪的行为

正如docs

中所述
  

onEndReached:当滚动位置位于呈现内容的onEndReachedThreshold范围内时调用一次。

因此,您可以将值设置为onEndReachedThreshold={0.5}

当内容的结尾位于列表可见长度的一半之内时,

0.5将触发onEndReached

为了重复合并它们需要的项目,concat将两个数组组合在一起,有或没有唯一值。

因此,像往常一样,您可以使用es6 spread operator

实施例

let arr1 = [1, 2, 3];
let arr2 = [3, 5, 6];

let deDupeIt = (...arrs) => [ ...new Set( [].concat(...arrs) ) ];

let dedupedArrays = deDupeIt(arr1, arr2)
console.log(dedupedArrays)

在你的情况下,在某处定义函数并将其称为

this.setState({
               categories: deDupeIt(this.state.categories, response.data.data),
               isLoading: false,
           });

注意:

如果您正在使用代码段的第二部分 应使用prevState.page + 1而不是prevState + 1