0

我正在尝试将 React Navigation 6.x 包含到带有 Redux 的 React Native 项目中,因此需要能够从外部组件访问导航器。

我正在遵循本指南(在没有导航道具的情况下进行导航)并且具有与示例中基本相同的代码,在功能上运行良好:

import { createNavigationContainerRef } from '@react-navigation/native';

export const navigationRef = createNavigationContainerRef()

export function navigate(name, params) {
  if (navigationRef.isReady()) {
    navigationRef.navigate(name, params);
  }
}

但是我也在使用 Typescript。

React Navigation 还有一个关于集成 Typescript 的指南(使用 TypeScript 进行类型检查),它展示了如何键入导航 ref 本身,它也可以正常工作:

export const navigationRef = createNavigationContainerRef<RootStackParamList>();

虽然没有键入navigate函数的示例,但我无法得到任何工作。

我认为解决方案是复制navigationRef.navigate()方法的类型(在此处定义)并将其简单地应用于包装函数:

// navigationRef.navigate() typing...
//
// navigate<RouteName extends keyof ParamList>(
//   ...args: undefined extends ParamList[RouteName]
//     ? [screen: RouteName] | [screen: RouteName, params: ParamList[RouteName]]
//     : [screen: RouteName, params: ParamList[RouteName]]
// ): void;


type ParamList = RootStackParamList;
type Navigate = <RouteName extends keyof ParamList>(
  ...args: undefined extends ParamList[RouteName]
    ? [screen: RouteName] | [screen: RouteName, params: ParamList[RouteName]]
    : [screen: RouteName, params: ParamList[RouteName]]
) => void;

export const navigate: Navigate = (name, params) => {
  if (navigationRef.isReady()) {
    navigationRef.navigate(name, params);
  }
}

// or...

export const navigate: typeof navigationRef.navigate = (name, params) => {
  if (navigationRef.isReady()) {
    navigationRef.navigate(name, params);
  }
}

不幸的是,这给出了以下错误:

Argument of type '[(undefined extends RootStackParamList[RouteName] ? [screen: RouteName] | [screen: RouteName, params: RootStackParamList[RouteName]] : [screen: ...])[0], (undefined extends RootStackParamList[RouteName] ? [screen: ...] | [screen: ...] : [screen: ...])[1]]' is not assignable to parameter of type 'undefined extends RootStackParamList[(undefined extends RootStackParamList[RouteName] ? [screen: RouteName] | [screen: RouteName, params: RootStackParamList[RouteName]] : [screen: ...])[0]] ? [screen: ...] | [screen: ...] : [screen: ...]'.ts(2345)
4

1 回答 1

0

您可以重复使用的类型navigationRef.navigate

export const navigate: typeof navigationRef.navigate = (name, params) => {
  if (navigationRef.isReady()) {
    navigationRef.navigate(name, params);
  }
}
于 2022-02-11T15:36:05.327 回答