如何测试React Native Reanimated中useDerivedValue触发的goBack函数?
React Native Reanimated 2:useDerivedValue写法的测试用例编写
我有一个接收goBack函数作为参数的组件,用户点击按钮时会通过react-native-reanimated-2执行退场动画,动画结束后调用goBack函数。我用useDerivedValue监听isOpen值实现逻辑,代码如下:
useDerivedValue(() => { if (isOpen === 0) { runOnJS(toGoBack)(); } }, [isOpen]); const toCloseWiteAnim = () => { isOpen.value = withTiming(0); };
但我的测试用例只能通过withTiming回调调用goBack的版本,请问怎么针对useDerivedValue的写法编写测试用例,验证goBack函数被调用?
我的测试代码:
const element = await queryByTestId('test.x-icon'); expect(element).toBeTruthy(); fireEvent.press(element); expect(mockedGoBack).toBeCalled();
能通过测试的代码版本:
const toCloseWiteAnim = () => { isOpen.value = withTiming(0, {}, (isAnimFinished) => { if (isAnimFinished) { runOnJS(toGoBack)(); } }); };
解决方法
要测试useDerivedValue的写法,核心是让Reanimated的动画逻辑在测试环境中同步执行,同时触发useDerivedValue的更新检测,具体步骤如下:
- 替换Reanimated的测试实现
在测试文件顶部添加mock配置,让Reanimated以同步模式运行:
jest.mock('react-native-reanimated', () => { const Reanimated = require('react-native-reanimated/mock'); Reanimated.default.callbacks = true; return Reanimated; });
- 推进动画完成
点击按钮后,需要手动触发动画帧,让withTiming立即完成并更新isOpen的值,进而触发useDerivedValue的逻辑。可以使用Reanimated提供的advanceAnimation或jest的定时器:
// 引入advanceAnimation import { advanceAnimation } from 'react-native-reanimated'; // 测试逻辑 const element = await queryByTestId('test.x-icon'); expect(element).toBeTruthy(); fireEvent.press(element); // 推进动画,同步完成withTiming await advanceAnimation(); // 或者使用jest.runAllTimers() // jest.runAllTimers(); // 断言goBack被调用 expect(mockedGoBack).toBeCalled();
- 检查
useDerivedValue的判断逻辑
注意useDerivedValue中判断isOpen === 0是否准确——如果isOpen是Reanimated的SharedValue,正确的判断应该是isOpen.value === 0,这可能是导致逻辑不触发的潜在问题,需要确认代码中的写法是否正确。
内容的提问来源于stack exchange,提问作者Yoel
相关产品推荐
相关产品推荐

