支持多点触控行为,包括平移和滚动
import { useRef } from "react"; import { Dimensions, View } from "react-native"; import { Gesture, GestureDetector, ScrollView, } from "react-native-gesture-handler"; import Animated, { useAnimatedStyle, useSharedValue, withSpring, } from "react-native-reanimated"; import { Text } from "../restyled/Text";
const items = [ { id: "id_John", name: "John" }, { id: "id_Jane", name: "Jane" }, { id: "id_Jack", name: "Jack" }, { id: "id_Jill", name: "Jill" }, { id: "id_Joe", name: "Joe" }, { id: "id_Jim", name: "Jim" }, { id: "id_Joy", name: "Joy" }, ];
const listItemHeight = 75; const listItemWidth = Dimensions.get("window").width;
type Position = { x: number; y: number };
export function List() { return ( <ScrollView style={{ flex: 1, gap: 12 }}> {items.map((item, index) => ( ))} ); }
type ListItemProps = { id: string; };
function ListItem(props: ListItemProps) { const { id } = props;
const sharedSelectedItem = useSharedValue<string | null>(null); const sharedSelectedPosStart = useRef( useSharedValue({ x: 0, y: 0, }) ).current; const sharedSelectedPos = useRef( useSharedValue({ x: 0, y: 0, }) ).current;
const panGesture = Gesture.Pan() .activateAfterLongPress(250) .onStart((e) => { sharedSelectedItem.value = id; sharedSelectedPosStart.value = { x: e.absoluteX, y: e.absoluteY }; }) .onUpdate((e) => { sharedSelectedPos.value = { y: e.absoluteY - sharedSelectedPosStart.value.y, x: e.absoluteX - sharedSelectedPosStart.value.x, }; }) .onFinalize((e) => { sharedSelectedItem.value = null; sharedSelectedPos.value = { x: withSpring(0), y: withSpring(0), }; });
const animatedStyle = useAnimatedStyle(() => { const active = sharedSelectedItem.value === id; return { backgroundColor: active ? "blue" : "gray", opacity: active ? 1 : 0.5, transform: [ { translateX: sharedSelectedPos.value.x, }, { translateY: sharedSelectedPos.value.y, }, ], }; });
return ( <GestureDetector …
内容来源: software-mansion/react-native-gesture-handler