我有一个FlatList
renderHeaderComponent() {
return(
<View style={{ flexDirection: 'row', marginTop: 10, borderBottomColor: '#CED0CE', borderWidth: 1, borderColor: 'transparent' }}>
<Icon name='search' size={30} style={{ marginLeft: 10, marginRight: 10 }}/>
<TextInput
style={{height: 40, flex: 1}}
onChangeText={(text) => this.onChangeText(text)}
placeholder='Type text for search'
clearButtonMode='while-editing'
value={this.state.searchText}
/>
</View>
);
};
在标题中有TextInput。我使用TextInput作为搜索栏。
onChangeText(text) {
const filteredRestaurants = _.filter(this.props.list, (restaurantObject) => {
const restaurant = restaurantObject.restaurant;
const result = restaurant.name.trim().toLowerCase().includes(text.trim().toLowerCase());
return result;
})
this.setState({
searchText: text,
restaurants: filteredRestaurants
});
}
在onChangeMethod我过滤我的数据。
{{1}}
问题如下。当我在TextInput中键入一个符号时,焦点会立即从TextInput丢失?键入时如何将焦点保持在TextInput中?
答案 0 :(得分:2)
您需要使用auto-bound
方法,因为ListHeaderComponent
的类型为ReactClass
,您当前的方法基本上会重新创建并重新绑定其render
每次数据更新,这不是你想要的。 this comment
无论如何,对于你的例子,你应该
解决你的问题 1)将ListHeaderComponent
道具改为
ListHeaderComponent={this.renderListHeader}
2)现在您要将renderHeaderComponent
方法更改为auto-bound method
,并且通过这样做,每次更改数据时都不会实例化新的渲染(或者将文本输入到`TextInput中)
renderListHeader = () => (
<View style={{ flexDirection: 'row', marginTop: 10, borderBottomColor: '#CED0CE', borderWidth: 1, borderColor: 'transparent' }}>
<Icon name='search' size={30} style={{ marginLeft: 10, marginRight: 10 }}/>
<TextInput
style={{height: 40, flex: 1}}
onChangeText={(text) => this.onChangeText(text)}
placeholder='Type text for search'
clearButtonMode='while-editing'
value={this.state.searchText}
/>
</View>
)
答案 1 :(得分:2)
我遇到了这个问题,为了解决这个问题,我将 renderListHeader 包装在 React.useMemo 钩子中,并将状态钩子作为一个项目传递给依赖数组。
renderListHeader = useMemo(() => (
<View style={{ flexDirection: 'row', marginTop: 10, borderBottomColor: '#CED0CE', borderWidth: 1, borderColor: 'transparent' }}>
<Icon name='search' size={30} style={{ marginLeft: 10, marginRight: 10 }}/>
<TextInput
style={{height: 40, flex: 1}}
onChangeText={(text) => this.onChangeText(text)}
placeholder='Type text for search'
clearButtonMode='while-editing'
value={this.state.searchText}
/>
</View>
), [this.onChangeText])
答案 2 :(得分:1)
从本地版本0.61.5开始,这仍然是SectionList的问题。 auto-bound
方法不起作用,因为当数据变为空数组时,ListHeaderComponent重新呈现。
我使用了以下解决方法:
Animated.View
Animated.event
将Y转换为Animated.View
代码示例
const animatedScrollYValue = useRef(new Animated.Value(0)).current;
...
<View>
<Animated.View style={{
position: 'absolute',
top: 142,
left: 30,
right: 30,
zIndex: 1,
transform: [{ translateY: Animated.multiply(animatedScrollYValue, new Animated.Value(-1)) }] }}>
// Your text input
</Animated.View>
<Animated.SectionList
scrollEventThrottle={1}
onScroll={Animated.event([{ nativeEvent: { contentOffset: { y: animatedScrollYValue } } }], { useNativeDriver: true })}
keyExtractor={(item) => item.id}
ListHeaderComponent={// Whatever you want but make you include space for the absolute TextInput}
sections={data}
renderItem={renderItem}
renderSectionHeader={renderHeader}
/>
</View>