用打字稿反应导航getparam

时间:2020-07-30 20:56:39

标签: typescript react-native expo react-navigation react-navigation-stack

我正在开发一个应用程序,该应用程序从FlatList导航到自定义组件,并且需要访问传递给该组件的数据。 FlatList组件当前如下所示:

import React from 'react';
import { View, Text, StyleSheet, FlatList, TouchableOpacity } from 'react-native';
import Order from '../../components/Order/Order';
import {
    NavigationParams,
    NavigationScreenProp,
    NavigationState,
} from 'react-navigation';
  
export interface IProps {
    navigation: NavigationScreenProp<NavigationState, NavigationParams>;
}

const OrdersOverview : React.FC<IProps> = props => {
    const { navigation } = props;
    return(
        <View>
            <FlatList
                keyExtractor={(item) => item.order_id}
                data={orders}
                renderItem={({ item }) => (
                    <TouchableOpacity onPress= {() => {
                        navigation.navigate('OrderDetails', item);
                    }}>
                        <Order
                            orderNumber={item.order_id}
                            orderDate={item.orderDate}
                            dueDate={item.dueDate}
                            invoiceAmount={item.invoiceAmount}
                            status={item.state}
                            customer={item.customer}
                        />
                    </TouchableOpacity>
                )}
            />
        </View>
    );
}

我正在尝试将单击的项目传递到详细信息屏幕。但是,我无法访问这些项目,也不知道为什么它不起作用。我正在尝试访问以下项目:

import React, { useState } from 'react';
import { View, Text, StyleSheet } from 'react-native';
import {
    NavigationParams,
    NavigationScreenProp,
    NavigationState,
} from 'react-navigation';
  
export interface IProps {
    navigation: NavigationScreenProp<NavigationState, NavigationParams>;
}

const OrderDetails : React.FC<IProps> = (props) => {

    const { navigation } = props;
    const [categoryName, setCategoryName] = useState('information');

    return(
        <View>
            <Text>{ navigation.getParam('orderDate') }</Text>
        </View>
    );
}

1 个答案:

答案 0 :(得分:0)

输入参数

可以在新版 React Navigation 中获得完整的打字稿支持。您现在使用 props.navigation.getParam() 而不是 props.route.params

您希望传递特定于您的应用及其参数要求的类型,而不是使用通用类型 NavigationState 作为您的 NavigationScreenProp 上的泛型。

我确定你已经有一个 Order 对象的类型,但我需要一个来玩:

interface OrderItem {
  order_id: number;
  orderDate: string;
  dueDate: string;
  invoiceAmount: number;
  state: string;
  customer: number;
}

现在我们说 OrderDetails 屏幕必须始终接收这些道具。

type RootStackParamList = {
  OrdersList: undefined;
  OrderDetails: OrderItem;
}

警告

请注意,不建议像您一样传递整个订单对象。您应该只传递 order_id 并通过某种全局状态访问订单本身。文档中有关于它的 long section,这只是其中的一部分:

<块引用>

了解参数中应该包含什么样的数据很重要。参数就像屏幕的选项。它们应该只包含用于配置屏幕中显示内容的信息。避免传递将显示在屏幕本身上的完整数据(例如传递用户 ID 而不是用户对象)。还要避免传递被多个屏幕使用的数据,这些数据应该在一个全局存储中。

<块引用>

例如,假设您有个人资料屏幕。当导航到它时,您可能会想在参数中传递用户对象。这看起来很方便,并且让您无需任何额外工作即可使用 route.params.user 访问用户对象。

<块引用>

然而,这是一种反模式。诸如用户对象之类的数据应该在您的全局存储中而不是导航状态中。否则,您会在多个地方复制相同的数据。这可能会导致错误,例如即使用户对象在导航后发生更改,配置文件屏幕也会显示过时的数据。

访问参数

但我想回答你的打字稿问题,所以我假设你可以从参数中访问 orderDate,即使你不应该。

您可以从堆栈或标签导航器中为堆栈屏幕道具导入一个类型,其中包括 routenavigation。我们将泛型设置为我们的参数映射 RootStackParamList 和当前路由名称 'OrderDetails'

import { StackScreenProps } from "@react-navigation/stack";

type OrderDetailsProps = StackScreenProps<RootStackParamList, 'OrderDetails'>

或者您可以只定义具有 route 类型的 RouteProp 属性,它采用相同的泛型。

import { RouteProp } from "@react-navigation/native";

type OrderDetailsProps = {
  route: RouteProp<RootStackParamList, 'OrderDetails'>;
}

无论哪种方式,我们都获得了对 route.params 属性的完整 Typescript 支持。

const OrderDetails : React.FC<OrderDetailsProps> = ({route}) => {
    return(
        <View>
            <Text>Order Placed on { route.params.orderDate }</Text>
        </View>
    );
}