React Native中如何让长按事件冒泡以同时触发父子组件长按回调
React Native Pressable长按事件冒泡实现方案
React Native 的触摸事件系统中,
Pressable组件默认的onLongPress回调会阻止事件向上冒泡,因此默认无法触发父级组件的长按回调,不需要依赖第三方包的前提下有两种常用实现方案。
方案1:手动调用父级回调(层级较浅时推荐)
直接将父组件的长按逻辑通过ref或者props传递给子组件,子组件触发自身长按逻辑的同时手动调用父级回调即可,实现最简单性能最优:
import { useRef } from 'react'; import { Pressable, ScrollView, Text, StyleSheet } from 'react-native'; export default function App() { // 存储父级长按回调,也可以直接定义后通过props逐层传递 const parentLongPress = useRef(() => { console.log('triggered 2'); }).current; return ( <Pressable style={styles.press2} onLongPress={parentLongPress} > <Text>Look Down</Text> <ScrollView> <Pressable style={styles.press1} onLongPress={() => { // 触发子组件自身逻辑 console.log('triggered 1'); // 手动调用父级长按回调模拟冒泡 parentLongPress(); }} > <Text>click me</Text> </Pressable> </ScrollView> </Pressable> ); } const styles = StyleSheet.create({ press1: { padding: 20, backgroundColor: '#f5c2e7', }, press2: { padding: 30, backgroundColor: '#cba6f7', flex: 1, } });
方案2:自定义长按判定逻辑(层级较深时推荐)
RN原始的基础触摸事件onTouchStart/onTouchEnd/onTouchMove默认支持冒泡,你可以基于这几个事件自行实现长按判定,不需要依赖Pressable默认的onLongPress:
import { useState } from 'react'; import { Pressable, ScrollView, Text, StyleSheet } from 'react-native'; // 和RN官方长按阈值保持一致,可自行调整 const LONG_PRESS_THRESHOLD = 500; export default function App() { const [pressTimer, setPressTimer] = useState(null); const handleTouchStart = (callback) => { // 按下时启动计时 const timer = setTimeout(() => { callback?.(); }, LONG_PRESS_THRESHOLD); setPressTimer(timer); }; const clearPressTimer = () => { // 抬手/滑动时清空计时器,取消长按判定 if (pressTimer) { clearTimeout(pressTimer); setPressTimer(null); } }; return ( <Pressable style={styles.press2} onTouchStart={() => handleTouchStart(() => console.log('triggered 2'))} onTouchEnd={clearPressTimer} onTouchMove={clearPressTimer} > <Text>Look Down</Text> <ScrollView> <Pressable style={styles.press1} onTouchStart={() => handleTouchStart(() => console.log('triggered 1'))} onTouchEnd={clearPressTimer} onTouchMove={clearPressTimer} > <Text>click me</Text> </Pressable> </ScrollView> </Pressable> ); } // 样式同方案1可复用
如果需要更贴合官方长按行为,可在onTouchMove中添加触摸位移判定,移动距离超过10px时清空计时器取消长按即可。
内容的提问来源于stack exchange,提问作者user15573857
相关产品推荐
相关产品推荐

