Here is how I solved my problem:
Here is my initial state:
state = {
onEndReachedCalledDuringMomentum: true,
lastLoadCount: 0,
}
This is my FlatList
<FlatList
keyboardShouldPersistTaps="always"
style={...}
data={this.state.searchResults}
extraData={this.state}
bounces={false}
renderItem={({ item, index }) =>
<SearchResultView
uriSsource={item.image}
itemIndex={index}
name={item.name}
/>
}
showsVerticalScrollIndicator={false}
keyExtractor={this._keyExtractor}
numColumns={2}
onEndReached={() => this._loadMoreData()}
onEndReachedThreshold={0.01}
ListFooterComponent={this._renderSearchResultsFooter}
onMomentumScrollBegin={() => this._onMomentumScrollBegin()}
/>
Here are the functions I am calling:
// Key Extractor
_keyExtractor = (item, index) => item.id;
// Check if list has started scrolling
_onMomentumScrollBegin = () => this.setState({ onEndReachedCalledDuringMomentum: false });
// Load more data function
_loadMoreData = () => {
if (!this.state.onEndReachedCalledDuringMomentum) {
this.setState({ onEndReachedCalledDuringMomentum: true }, () => {
setTimeout(() => {
if (this.state.lastLoadCount >= 20 && this.state.notFinalLoad) {
this.setState({
page: this.state.page + 1,
}, () => {
// Then we fetch more data;
this._callTheAPIToFetchMoreData();
});
};
}, 1500);
});
};
};
// Show your spinner
_renderSearchResultsFooter = () => {
return (
(this.state.onEndReachedCalledDuringMomentum && this.state.lastLoadCount >= 20 && this.state.notFinalLoad) ?
<View style={{ marginBottom: 30, marginTop: -50, alignItems: 'center' }}>
<ActivityIndicator size="large" color="#e83628" />
</View> : null
)
}
Once I get data, inside of _callTheAPIToFetchMoreData()
, I update the state like this:
this.setState({
lastLoadCount: results.length,
onEndReachedCalledDuringMomentum: results.length >= 20 ? true : false,
notFinalLoad: results.length >= 20 ? true : false
}
Happy coding.