我正在使用 react-native-reanimated v 1.9 和 react-native-gesture-handler 在屏幕上拖动一个元素,我需要能够在用户按下“UNDO”按钮后将元素重置到以前的位置.
初始化一些动画值后:
this.X = new Value();
this.Y = new Value();
const offsetX = new Value();
const offsetY = new Value();
.... this.handlePan函数从这里获取平移事件:
<PanGestureHandler
ref={this.panRef}
enabled={this.panGestureHandlerEnabler}
onGestureEvent={this.handlePan}
onHandlerStateChange={this.handlePan}>
<Animated.View>
.......
</Animated.View>
</PanGestureHandler>
从 this.handlePan 事件映射到x和y,然后我可以使用 react-native-reanimated call()方法在任何平移运动结束时提取一些动画值,并使其可用于函数recordNewState():
this.handlePan = event([
{
nativeEvent: ({
translationX: x,
translationY: y,
absoluteY: Y,
absoluteX: X,
state,
}) =>
block([
set(this.X, add(x, offsetX)),
set(this.Y, add(y, offsetY)),
cond(eq(state, State.END), [
set(offsetX, add(offsetX, x)),
set(offsetY, add(offsetY, y)),
call([this.X, this.Y], (finalXY) => {
recordNewState({
action: 'XY',
value: {X: x, Y: y},
});
}),
]),
]),
},
{useNativeDriver: true},
]);
函数recordNewState()基本上构建了一个动画值数组,可用于undo()函数:
this.undo = () => {
if (lastRecordedState.length > 1) {
const undoAction =
lastRecordedState[lastRecordedState.length - 1];
switch (undoAction.action) {
case 'XY':
block([
offsetX.setValue(sub(offsetX, undoAction.value.X)),
offsetY.setValue(sub(offsetY, undoAction.value.Y)),
]);
break;
default:
break;
}
}
};
在这里,我检查最新的动画值 (undoAction.action),在 switch 语句中,如果它是 XY,我翻译项目减去最新的动画值。和
block([
offsetX.setValue(sub(offsetX, undoAction.value.X)),
offsetY.setValue(sub(offsetY, undoAction.value.Y)),
]);
该项目不会移回先前的位置,并且 call() 方法再次被调用,将另一个动画值添加到数组中。