I made this simple solution using scrollviews and touch position.
It has a very clean implementation with no heavy components or external modules.
You can also use this with <View>
components instead of scrollviews.
So first, we will be creating a hook: useSwipe.tsx
import { Dimensions } from 'react-native';
const windowWidth = Dimensions.get('window').width;
export function useSwipe(onSwipeLeft?: any, onSwipeRight?: any, rangeOffset = 4) {
let firstTouch = 0
// set user touch start position
function onTouchStart(e: any) {
firstTouch = e.nativeEvent.pageX
}
// when touch ends check for swipe directions
function onTouchEnd(e: any){
// get touch position and screen size
const positionX = e.nativeEvent.pageX
const range = windowWidth / rangeOffset
// check if position is growing positively and has reached specified range
if(positionX - firstTouch > range){
onSwipeRight && onSwipeRight()
}
// check if position is growing negatively and has reached specified range
else if(firstTouch - positionX > range){
onSwipeLeft && onSwipeLeft()
}
}
return {onTouchStart, onTouchEnd};
}
then, in your component… in my case im going to use: exampleComponent.tsx
- Import the previous
useSwipe
hook. - Add
onTouchStart
andonTouchEnd
events to your scrollView.
ExampleComponent
import * as React from 'react';
import { ScrollView } from 'react-native';
import { useSwipe } from '../hooks/useSwipe'
export function ExampleComponent(props: any) {
const { onTouchStart, onTouchEnd } = useSwipe(onSwipeLeft, onSwipeRight, 6)
function onSwipeLeft(){
console.log('SWIPE_LEFT')
}
function onSwipeRight(){
console.log('SWIPE_RIGHT')
}
return (
<ScrollView onTouchStart={onTouchStart} onTouchEnd={onTouchEnd}>
{props.children}
</ScrollView>
);
}
You can mess around with the offsetRange
property to handle precision.
And adapt the original code to be used with normal class components instead of hooks.