我有一个评论列表,我想拖放这些评论并重新排序。这是列表的样子:https ://i.stack.imgur.com/sozkK.png
我的问题是我想在用户拖动评论时向用户显示项目所在的“预览”,因此每次将项目拖到列表中的另一个项目上时,我都会对列表进行重新排序,交换这两个但是然后当前正在拖动的项目更改为我正在拖动的项目。假设我有一个数组 ["a","b","c"],如果我拖动 A 并越过 B,我拖动的项目将转换为 B(因为 B 现在位于数组)。我想要的是简单地显示如果将要拖动的项目放在那里,列表的外观的预览
这是我的组件:
import React, { useState, useEffect, useRef, useMemo, View } from "react";
import { StyleSheet, Animated, PanResponder } from "react-native";
const Draggable = ({
index,
position,
movingDraggable,
onMovingDraggable,
releaseDraggable,
onReleaseDraggable,
swap,
renderChild
}) => {
const animatedView = useRef();
const [zIndex, setZIndex] = useState(0);
const [isMovedOver, setIsMovedOver] = useState(false);
useEffect(() => {
animatedView.current.measure((x, y, width, height, pageX, pageY) => {
if (
movingDraggable &&
movingDraggable.index != index &&
movingDraggable.pageX > pageX &&
movingDraggable.pageX < pageX + width &&
movingDraggable.pageY > pageY &&
movingDraggable.pageY < pageY + height
) {
setIsMovedOver(true);
swap(index, movingDraggable.index);
} else {
setIsMovedOver(false);
}
});
}, [movingDraggable]);
useEffect(() => {
animatedView.current.measure((x, y, width, height, pageX, pageY) => {
if (
releaseDraggable &&
releaseDraggable.index != index &&
releaseDraggable.pageX > pageX &&
releaseDraggable.pageX < pageX + width &&
releaseDraggable.pageY > pageY &&
releaseDraggable.pageY < pageY + height
) {
swap(index, releaseDraggable.index);
}
});
}, [releaseDraggable]);
const pan = useRef(new Animated.ValueXY());
const panResponder = useMemo(
() =>
PanResponder.create({
onStartShouldSetPanResponder: (evt, gestureState) => true,
onMoveShouldSetPanResponderCapture: (evt, gestureState) => true,
onPanResponderGrant: (evt, gestureState) => {
setZIndex(1);
pan.current.setOffset({
x: pan.current.x._value,
y: pan.current.y._value,
});
pan.current.setValue({ x: 0, y: 0 });
},
onPanResponderMove: Animated.event(
[null, { dx: pan.current.x, dy: pan.current.y }],
{
useNativeDriver: false,
listener: (evt) => {
const { pageX, pageY } = evt.nativeEvent;
onMovingDraggable({ index, pageX, pageY });
},
}
),
onPanResponderRelease: (evt, gestureState) => {
setZIndex(0);
const { pageX, pageY } = evt.nativeEvent;
onReleaseDraggable({ index, pageX, pageY });
setIsMovedOver(false);
Animated.spring(pan.current, {
toValue: {
x: 0 - pan.current.x._offset,
y: 0 - pan.current.y._offset,
},
useNativeDriver: false,
}).start(() => {
pan.current.setValue({ x: 0, y: 0 });
pan.current.setOffset({ x: 0, y: 0 });
});
},
}),
[]
);
const panStyle = { transform: pan.current.getTranslateTransform() };
return (
<Animated.View
{...panResponder.panHandlers}
ref={animatedView}
style={[panStyle, styles.shadow, position, { zIndex: zIndex }, /* zIndex ? { width: 0 } : null */ ]}
>
{renderChild(isMovedOver)}
</Animated.View>
)
};
const styles = StyleSheet.create({
shadow: {
shadowColor: "#000",
shadowOffset: {
width: 0,
height: 6,
},
shadowOpacity: 0.1,
shadowRadius: 10,
elevation: 10,
},
});
export default Draggable
父级中的功能:
const onMovingDraggable = (movingDraggable) => {
setMovingDraggable(movingDraggable);
};
const onReleaseDraggable = (releaseDraggable) => {
setMovingDraggable(null);
setReleaseDraggable(releaseDraggable);
};
const swap = (index1, index2) => {
var arr = [...characteristics];
arr.splice(index1 + 1, 0, arr[index2])
arr.splice(index2, 1)
setCharacteristics(arr);
};