Skip to main content
Version: 3.x

Gesture Detectors

Gesture Detector

The GestureDetector is a key component of react-native-gesture-handler. It supports gestures created either using the hooks API or the builder pattern. Additionally, it allows for the recognition of multiple gestures through gesture composition. GestureDetector interacts closely with Reanimated. For more details, refer to the Integration with Reanimated section.

When using hook API, you can also integrate it directly with the Animated API. More on that can be found in Integreation with Animated section.

danger

Nesting Gesture Detectors

Because GestureDetector supports both the hook API and the builder pattern, it is important to avoid nesting detectors that use different APIs, as this can result in undefined behavior.

Reusing Gestures

Using the same instance of a gesture across multiple Gesture Detectors may result in undefined behavior.

import { GestureDetector, useTapGesture } from 'react-native-gesture-handler';

export default function App() {
const tap = useTapGesture({
onDeactivate: () => {
console.log('Tap!');
},
});

return (
<GestureHandlerRootView>
<GestureDetector gesture={tap}>
<Animated.View />
</GestureDetector>
</GestureHandlerRootView>
);
}

Virtual Detectors

Since RNGH3, GestureDetector is a standalone host component. Depending on the view hierarchy, this can occasionally disrupt interactions between specific components. To resolve this, use InterceptingGestureDetector in combination with VirtualNativeDetector.

InterceptingGestureDetector

InterceptingGestureDetector functions similarly to a GestureDetector, but it can also act as a proxy for VirtualGestureDetector within its component subtree. Because it can be used solely to establish the context for virtual detectors, the gesture property is optional.

VirtualGestureDetector

VirtualGestureDetector is similar to the GestureDetector from RNGH2. Because it is not a host component, it does not interfere with the host view hierarchy. This allows you to attach gestures without disrupting functionality that depends on it.

Known use cases

Here are some of the most common use cases for virtual gesture detectors.

SVG

You can combine VirtualGestureDetector with react-native-svg to add gesture handling to individual SVG elements.


export default function App() {
const outerTap = useTapGesture({
onDeactivate: () => {
console.log('Box tapped!');
},
});
const innerTap = useTapGesture({
onDeactivate: () => {
console.log('Circle tapped!');
},
});

return (
<GestureHandlerRootView style={styles.container}>
<InterceptingGestureDetector gesture={outerTap}>
<View style={styles.box}>
<Svg height="250" width="250">
<VirtualGestureDetector gesture={innerTap}>
<Circle
cx="125"
cy="125"
r="125"
fill="#001A72"
onPress={() => {}}
/>
</VirtualGestureDetector>
</Svg>
</View>
</InterceptingGestureDetector>
</GestureHandlerRootView>
);

Text

You can use VirtualGestureDetector to add gesture handling to specific parts of a Text component.

} from 'react-native-gesture-handler';

export default function App() {
const outerTap = useTapGesture({
onDeactivate: () => {
console.log('Tapped on text!');
},
});

const nestedTap = useTapGesture({
onDeactivate: () => {
console.log('Tapped on nested part!');
},
});

return (
<GestureHandlerRootView style={styles.container}>
<InterceptingGestureDetector gesture={outerTap}>
<Text style={{ fontSize: 18, textAlign: 'center' }}>
Nested text
<VirtualGestureDetector gesture={nestedTap}>
<Text style={{ fontSize: 24, color: '#001A72' }}>
try tapping on this part.
</Text>
</VirtualGestureDetector>
This part is not special :c
</Text>
</InterceptingGestureDetector>
</GestureHandlerRootView>
);

Properties

gesture

gesture: SingleGesture | ComposedGesture;

A gesture object containing the configuration and callbacks. Can be any of the base gestures or any ComposedGesture.

userSelect (Web only)

userSelect: 'none' | 'auto' | 'text';

This parameter allows to specify which userSelect property should be applied to underlying view. Default value is set to "none".

touchAction (Web only)

userSelect: TouchAction;

This parameter allows to specify which touchAction property should be applied to underlying view. Supports all CSS touch-action values. Default value is set to "none".

enableContextMenu (Web only)

enableContextMenu: boolean;

Specifies whether context menu should be enabled after clicking on underlying view with right mouse button. Default value is set to false.