В отличие от ListView, мы можем обновить this.state.datasource. Есть ли какой-либо метод или пример для обновления FlatList или повторного рендеринга?
Моя цель - обновить текстовое значение, когда пользователь нажимает кнопку ...
renderEntries({ item, index }) {
return(
<TouchableHighlight onPress={()=> this.setState({value: this.state.data[index].value+1})>
<Text>{this.state.data[index].value}</Text>
</TouchableHighlight>
)
}
<FlatList
ref={(ref) => { this.list = ref; }}
keyExtractor={(item) => item.entry.entryId}
data={this.state.data}
renderItem={this.renderEntries.bind(this)}
horizontal={false} />
reactjs
react-native
react-native-flatlist
Shalonteoh
источник
источник
PureComponent
означает, что он не будет повторно визуализироваться, если реквизиты остаются мелкими - равными. Убедитесь, что все, от чегоrenderItem
зависит ваша функция, передается как опора, которая не===
после обновлений, иначе ваш пользовательский интерфейс может не обновляться при изменениях. Это включает в себя состояниеdata
опоры и родительского компонента ". Вы следуете этому совету?extraData
иshouldItemUpdate
, я не мог получить список для повторной визуализации. В итоге я очистил состояние, дождался его рендеринга и затем обновил состояние.this.setState({ data: null }, () => { this.setState({ data: actualData }) });
Ответы:
Используйте
extraData
свойство в своем компоненте FlatList.Как указано в документации:
источник
data={this.props.searchBookResults}
иextraData={this.state}
ниextraData={this.props}
у меня, ни у меня не работает. Иdata={this.props.searchBookResults}
тоже не работает. Что делать ?... data={this.props.searchBookResults} extraData={this.state.refresh} onPress={()={this.setState({ refresh: !refresh})}
extraData
extraData
опору, изменяются, когда дочерний элемент [ы] должен повторно отображаться. Например, если элементы списка могут быть активными / неактивными, убедитесь, что эта переменная статуса, независимо от того, является ли частьthis.state
объекта илиthis.props
объект тем, что должно быть внутриextraData
. Это может быть курсор или массив активных элементов и т. Д.shouldComponentUpdate()
, как только я обновил это или полностью закомментировал, все работало так же, как описано в документации.Для быстрого и простого решения Попробуйте:
установить дополнительные данные в логическое значение.
extraData = {this.state.refresh}
Переключите значение логического состояния, когда вы хотите повторно отрисовать / обновить список
this.setState({ refresh: !this.state.refresh })
источник
this.data.refresh()
. Вместо этого мы устанавливаем логическое значение и меняем его. Само логическое значение не имеет смысла, так какой смысл в нем существовать? ... (Нет смысла, кроме как правильно обновлять данные?)this.state.users
не работает, хотя я менял флаг у некоторых пользователей.О, это просто, просто используйте
extraData
Вы видите, как дополнительные данные работают за кулисами: FlatList или VirtualisedList просто проверяют , изменился ли этот объект с помощью обычного
onComponentWillReceiveProps
метода.Итак, все, что вам нужно сделать, это убедиться, что вы добавили что-то, что меняет файл
extraData
.Вот что я делаю:
Я использую immutable.js, поэтому все, что я делаю, это передаю Map (неизменяемый объект), содержащий все, что я хочу посмотреть.
<FlatList data={this.state.calendarMonths} extraData={Map({ foo: this.props.foo, bar: this.props.bar })} renderItem={({ item })=>(( <CustomComponentRow item={item} foo={this.props.foo} bar={this.props.bar} /> ))} />
Таким образом, при изменении
this.props.foo
илиthis.props.bar
изменении нашCustomComponentRow
будет обновляться, потому что неизменяемый объект будет отличаться от предыдущего.источник
extraData
! спасибо за ссылку наVirtualisedList
код!Хорошо, я только что узнал, что если мы хотим, чтобы FlatList знал об изменении данных за пределами свойства данных, нам нужно установить его на extraData, поэтому я делаю это сейчас так:
<FlatList data={...} extraData={this.state} .../>
обратитесь к: https://facebook.github.io/react-native/docs/flatlist#extradata
источник
Если у вас будет Button, вы можете обновить данные с помощью setState внутри onPress. SetState затем повторно отобразит ваш FlatList.
источник
После долгих поисков и поиска настоящего ответа, наконец, я получил ответ, который я считаю лучшим:
<FlatList data={this.state.data} renderItem={this.renderItem} ListHeaderComponent={this.renderHeader} ListFooterComponent={this.renderFooter} ItemSeparatorComponent={this.renderSeparator} refreshing={this.state.refreshing} onRefresh={this.handleRefresh} onEndReached={this.handleLoadMore} onEndReachedThreshold={1} extraData={this.state.data} removeClippedSubviews={true} **keyExtractor={ (item, index) => index }** /> .....
Моя основная проблема заключалась в том, что (KeyExtractor) я не использовал его таким образом. не работает: keyExtractor = {(item) => item.ID} после того, как я перешел на это, он работал как шарм, надеюсь, это кому-то поможет.
источник
this.state.refreshing
и функциюhandleRefresh
?Я решил эту проблему, добавив.
extraData={this.state}
Пожалуйста, проверьте код ниже, чтобы получить более подробную информацию.render() { return ( <View style={styles.container}> <FlatList data={this.state.arr} extraData={this.state} renderItem={({ item }) => <Text style={styles.item}>{item}</Text>} /> </View> ); }
источник
Просто расширение предыдущих ответов здесь. Две части для обеспечения: убедитесь, что вы добавили extraData и что ваш keyExtractor уникален. Если ваш keyExtractor постоянный, повторная визуализация не будет запущена.
<FlatList data={this.state.AllArray} extraData={this.state.refresh} renderItem={({ item,index })=>this.renderPhoto(item,index)} keyExtractor={item => item.id} > </FlatList>
источник
Я заменил
FlatList
на,SectionList
и он правильно обновляется при изменении состояния.<SectionList keyExtractor={(item) => item.entry.entryId} sections={section} renderItem={this.renderEntries.bind(this)} renderSectionHeader={() => null} />
Единственное, что нужно иметь в виду, это
section
наличие структуры diff:const section = [{ id: 0, data: this.state.data, }]
источник
Для меня трюк заключался в extraData и еще раз углублении в компонент элемента
state = { uniqueValue: 0 } <FlatList keyExtractor={(item, index) => item + index} data={this.props.photos} renderItem={this.renderItem} ItemSeparatorComponent={this.renderSeparator} /> renderItem = (item) => { if(item.item.selected) { return ( <Button onPress={this.itemPressed.bind(this, item)}>Selected</Button> ); } return ( <Button onPress={this.itemPressed.bind(this, item)}>Not selected</Button>); } itemPressed (item) { this.props.photos.map((img, i) => { if(i === item.index) { if(img['selected') { delete img.selected; } else { img['selected'] = true; } this.setState({ uniqueValue: this.state.uniqueValue +1 }); } } }
источник
Поместите переменные, которые будут изменены при вашем взаимодействии, в
extraData
Вы можете быть творческими.
Например, если вы имеете дело с изменяющимся списком с флажками на них.
<FlatList data={this.state.data.items} extraData={this.state.data.items.length * (this.state.data.done.length + 1) } renderItem={({item}) => <View>
источник
Если мы хотим, чтобы FlatList знал, что данные меняют свойство и состояние , мы можем создать объект, ссылающийся как на свойство, так и на состояние, и обновить плоский список.
const hasPropOrStateChange = { propKeyToWatch: this.props, ...this.state}; <FlatList data={...} extraData={this.hasPropOrStateChange} .../>
Документы: https://facebook.github.io/react-native/docs/flatlist#extradata
источник
В react-native-flatlist это свойство, называемое extraData. добавьте строку ниже в свой плоский список.
<FlatList data={data } style={FlatListstyles} extraData={this.state} renderItem={this._renderItem} />
источник
В этом примере, чтобы принудительно выполнить повторный рендеринг, просто измените переменную
machine
const [selected, setSelected] = useState(machine) useEffect(() => { setSelected(machine) }, [machine])
источник
Просто используйте:
onRefresh={true}
внутри вашего
flatList
компонента.источник
refreshing
опоруExtraData Flatlist не работал у меня, и я использовал опору от redux. Это звучало похоже на вопросы из комментариев в ответе ED209. Я закончил тем, что вручную вызвал setState, когда получил опору.
componentWillReceiveProps(nextProps: StateProps) { if (this.props.yourProp != null && nextProps.yourProp) { this.setState({ yourState: processProp(nextProps.yourProp) }); } } <FlatList data={this.state.yourState} extraData={this.state.yourState} />
Для тех из вас, кто использует> React 17, используйте getDerivedStateFromProps
источник