我是 React Native 和 Typescript 的新手。我一直在用 Stack Navigation 和 Drawer Navigation 实现一个小项目。该项目一直运行良好,但现在我必须进行一些单元测试。我从一个非常简单的开始,但失败了:/
这是应用程序导航的代码:
导航器.tsx
import App from "../../App";
import React from 'react';
import { Image, StyleSheet, TouchableHighlight } from 'react-native';
import { createAppContainer, NavigationScreenProp, NavigationState, NavigationParams } from 'react-navigation';
import { createDrawerNavigator } from 'react-navigation-drawer';
import { createStackNavigator } from 'react-navigation-stack';
import LoginScreen from "./LoginScreen";
import RegisterScreen from "./RegisterScreen";
import MapScreen from "./MapScreen";
import BikesScreen from "./BikesScreen";
import TheftScreen from "./TheftScreen";
import RentBikeScreen from "./RentBikeScreen";
import RouteListScreen from "./RouteListScreen";
import CouponScreen from "./CouponScreen";
import strings from "../config/strings";
interface Props {
navigation: NavigationScreenProp<NavigationState,NavigationParams>;
}
interface State {}
export default class NavigatorContainer extends React.Component<Props, State> {
render() {
const DrawerStack =
createDrawerNavigator({
Map: MapScreen,
Bikes: BikesScreen,
Theft: TheftScreen,
RouteList: RouteListScreen,
Coupon: CouponScreen
})
DrawerStack.navigationOptions = ({ navigation }) => {
const { routeName } = navigation.state.routes[navigation.state.index];
const headerTitle =
routeName == "Map" ? strings.CONSULT_ROUTE :
routeName == "Bikes" ? strings.BIKES_TITLE :
routeName == "Theft" ? strings.THEFT_REPORT_TITLE :
routeName == "Register" ? strings.REGISTER_SCREEN_TITLE :
routeName == "RouteList" ? strings.ROUTE_LIST_TITLE :
routeName == "Coupon" ? strings.COUPON_TITLE : "";
return {
headerTitle,
headerLeft: ({ tintColor }: {tintColor: any}) => (
<TouchableHighlight onPress={() => navigation.toggleDrawer()}><Image
source={require('../assets/images/drawer.png')}
style={[styles.icon, { tintColor: tintColor }]}
/></TouchableHighlight>)
};
};
const AppNavigator = createStackNavigator(
{
Login: {
screen: LoginScreen,
navigationOptions: {
header: null
}
},
Register: {
screen: RegisterScreen
},
DrawerStack: DrawerStack
},
{
initialRouteName: 'Login',
}
);
const AppContainer = createAppContainer(AppNavigator);
return <AppContainer />;
}
}
const styles = StyleSheet.create({
icon: {
width: 24,
height: 24,
},
});
这是测试:
应用测试.tsx
/**
* @format
*/
import 'react-native';
import React from 'react';
import App from '../App';
import * as renderer from 'react-test-renderer';
jest.mock('react-native', () => {
return {
StyleSheet: {
create: () => {
}
},
Platform: {}
}
});
it('renders correctly', () => {
renderer.create(<App />);
});
使用“纱线测试”执行测试时,我得到以下信息:
src/screens/Navigator.tsx:50:38 - error TS7031: Binding element 'navigation' implicitly has an 'any' type
所以我用“导航:NavigationScreenProp”更改了“导航”:
DrawerStack.navigationOptions = (navigation : NavigationScreenProp<NavigationState,NavigationParams>) => {....
并且测试通过了!...但是现在当我尝试使用“this.props.navigation.navigate('Map')”进入 DrawerNavigator 的屏幕之一时,例如 MapScreen,我得到了错误:
TypeError: undefined is not an object (evaluating 'navigation.state.routes')
我看到问题出在这一行:
const { routeName } = navigation.state.routes[navigation.state.index];
但我不知道如何解决它,也不明白为什么它只适用于 '({ navigation })'
有任何想法吗?