TouchableOpacity
使事物变得可触摸,或者正如 React Native 所说:
用于使视图正确响应触摸的包装器。
但是在
ScrollView
或 ListView
中使用它会导致我们(或至少我)不希望这样时突出显示。
向下滚动充满元素的
ListView
涉及以下三个步骤:
触摸元素会立即产生突出显示动画。但在这种情况下,我们只想滚动。我们不想对该元素做任何事情,无论是突出显示还是打开详细视图等。
这种情况并不总是发生,但大多数时候发生在我的 Android 设备上。
处理这个问题的正确方法是什么?
滚动手势应取消
TouchableOpacity
触摸响应器,但如果您认为 TouchableOpacity
突出显示提前触发,您可以尝试调整 delayPressIn
属性。
您可以使用
delayPressIn={1000}
,这会延迟动画,直到您按下1秒。
delayPressIn
属性的 <TouchableOpacity>
延迟(以毫秒为单位),从触摸开始,在调用 onPressIn 之前。
使用示例:
<FlatList
horizontal
contentContainerStyle={{ paddingRight: 16 }} // this set the padding to last item
showsHorizontalScrollIndicator={false} // hide the scroller
data={results}
keyExtractor={(result) => result.data.id}
renderItem={({ item }) => {
return (
<TouchableOpacity
delayPressIn={1000} // delay animation for 1 second
onPress={() => navigation.navigate('ResultsShow')}
>
<ResultsDetail result={item.data} />
</TouchableOpacity>
);
}}
/>;
您可以在这里找到更多相关信息。
delayPressIn
没有达到预期的效果,因为如果用户点击速度足够快,则不会显示任何效果。
正确的解决方案是使用 Pressable,它可以正确避免当用户滚动时触发
onPress
,并添加不透明动画,如下所示:
const PressableWithAnimation = React.memo((props) => {
const animated = useRef(new Animated.Value(1)).current;
const handlePress = () => {
animated.setValue(0.4);
Animated.timing(animated, {
toValue: 1,
duration: 400,
useNativeDriver: true,
}).start()
if (props.onPress) props.onPress();
};
return (
<Pressable onPress={handlePress}>
<Animated.View style={[styles.button, { opacity: animated }]}>
{props.children}
</Animated.View>
</Pressable>
);
});
您可以在这里比较我尝试过的所有实现:https://snack.expo.dev/@pickleheadsian/button-tests-in-scrollview