在屏幕之间创建导航时遇到问题
Having issue to create navigation between screen
我有一个启动画面,几秒钟后转到介绍页面,从介绍页面,我有一个 link 用于登录和注册。我尝试从介绍页面 to/from 登录设置导航,但遇到错误消息:
undefined 不是一个对象(计算'_this.props.navigation.navigate')。
我试图查看有关 react-navigation 的文档,但解释不清楚,因为它们混淆了 App.js 中的所有屏幕。
App.js
import React, {Component} from 'react';
import { StyleSheet, StatusBar, Text, View} from 'react-native';
import { createStackNavigator, createAppContainer } from 'react-navigation';
import Intro from './screen/Intro';
import Login from './components/Login';
const RootStack = createStackNavigator(
{
IntroScreen: Intro,
LoginScreen: Login,
},
{
initialRouteName: 'IntroScreen',
}
);
const AppNavigator = createAppContainer(RootStack);
export default class App extends Component {
render() {
return (
<View style={styles.container}>
<StatusBar
barStyle="light-content"
backgroundColor="#fefefe"
/>
<Intro/>
</View>
);
}
}
Intro.js
该页面跟随初始屏幕显示,我可以从该页面 select 登录或注册。
import React, { Component } from 'react';
import {
Text,
Image,
View,
ImageBackground,
StyleSheet,
TouchableOpacity
}
from 'react-native';
import SplashScreen from 'react-native-splash-screen';
export default class Intro extends Component{
componentDidMount(){
SplashScreen.hide();
}
render(){
return(
<ImageBackground source={require('../images/signup-background.jpg')} style={{width: '100%', height: '100%'}}>
<View style={styles.container}>
<Image
source ={ require('../images/logo.png')}
/>
<Text style={styles.simpleText}>WELCOME</Text>
<Text style={styles.literal}>Thank you for your interest in the APG app. </Text>
<Text style={styles.literal}>How can we help you?</Text>
<TouchableOpacity
style= {styles.signinCont}
onPress={() => this.props.navigation.navigate('IntroScreen')}
>
<Text style= {styles.signinText}>
I am already an APG Patient
</Text>
</TouchableOpacity>
<TouchableOpacity style= {styles.signupCont}>
<Text style= {styles.signupText}>
I am not an APG Patient
</Text>
</TouchableOpacity>
</View>
</ImageBackground>
);
}
}
Login.js
在登录上,我有一个 link 按钮用于注册并忘记密码,以防用户没有帐户
import React, { Component } from 'react';
import {
Text,
TouchableOpacity,
Label,
View,
TextInput,
StyleSheet,
}
from 'react-native';
export default class Login extends Component {
render(){
return(
<View style={styles.container}>
<View>
<Text>Login</Text>
</View>
<Label>Email</Label>
<TextInput
style={Styles.textbox}
placeholder="Email"
value= {this.state.email}
/>
<Label>Password</Label>
<TextInput
style={Styles.textbox}
placeholder="Password"
value ={this.state.password}
secureTextEntry={true}
/>
<View>
<Text>Forgot password</Text>
</View>
<TouchableOpacity style={styles.signin}>
<Text style ={styles.signinText}>Sign In</Text>
</TouchableOpacity>
<View>
<Text>Not an APG Member? </Text>
<TouchableOpacity style={styles.signup}
onPress ={() => this.props.navigation.navigate('SignUp') }
>
<Text>Sign Up</Text>
</TouchableOpacity>
</View>
</View>
);
}
}
我希望能够从 Intro.js 和 login.js 中选择登录或注册,以便能够单击注册进行注册,然后从注册中选择可以点击登录。
解决方案
onPress={this.props.navigation.navigate('SignUp')}
不调用 this.props.navigation.navigate
函数。
如下更改您的 onPress
属性。
使用es6箭头函数制作匿名函数
<TouchableOpacity
style={styles.signup}
onPress={() => this.props.navigation.navigate('SignUp')}
>
或者您可以在 onPress
中引用您的函数。再次渲染时,它会提高性能。
navigate = () => {
this.props.navigation.navigate('SignUp')
}
return (
...
<TouchableOpacity
style={styles.signup}
onPress={this.navigate}
>
)
为什么
props
仅引用值,即使它是函数。因此,使 props
引用您预定义的 class 中的匿名函数或函数。
当你使用 not 箭头函数时不要忘记 bind(this)
。
navigate() {
this.props.navigation.navigate('SignUp')
}
...
onPress={this.navigate.bind(this)}
...
我有一个启动画面,几秒钟后转到介绍页面,从介绍页面,我有一个 link 用于登录和注册。我尝试从介绍页面 to/from 登录设置导航,但遇到错误消息: undefined 不是一个对象(计算'_this.props.navigation.navigate')。
我试图查看有关 react-navigation 的文档,但解释不清楚,因为它们混淆了 App.js 中的所有屏幕。
App.js
import React, {Component} from 'react';
import { StyleSheet, StatusBar, Text, View} from 'react-native';
import { createStackNavigator, createAppContainer } from 'react-navigation';
import Intro from './screen/Intro';
import Login from './components/Login';
const RootStack = createStackNavigator(
{
IntroScreen: Intro,
LoginScreen: Login,
},
{
initialRouteName: 'IntroScreen',
}
);
const AppNavigator = createAppContainer(RootStack);
export default class App extends Component {
render() {
return (
<View style={styles.container}>
<StatusBar
barStyle="light-content"
backgroundColor="#fefefe"
/>
<Intro/>
</View>
);
}
}
Intro.js 该页面跟随初始屏幕显示,我可以从该页面 select 登录或注册。
import React, { Component } from 'react';
import {
Text,
Image,
View,
ImageBackground,
StyleSheet,
TouchableOpacity
}
from 'react-native';
import SplashScreen from 'react-native-splash-screen';
export default class Intro extends Component{
componentDidMount(){
SplashScreen.hide();
}
render(){
return(
<ImageBackground source={require('../images/signup-background.jpg')} style={{width: '100%', height: '100%'}}>
<View style={styles.container}>
<Image
source ={ require('../images/logo.png')}
/>
<Text style={styles.simpleText}>WELCOME</Text>
<Text style={styles.literal}>Thank you for your interest in the APG app. </Text>
<Text style={styles.literal}>How can we help you?</Text>
<TouchableOpacity
style= {styles.signinCont}
onPress={() => this.props.navigation.navigate('IntroScreen')}
>
<Text style= {styles.signinText}>
I am already an APG Patient
</Text>
</TouchableOpacity>
<TouchableOpacity style= {styles.signupCont}>
<Text style= {styles.signupText}>
I am not an APG Patient
</Text>
</TouchableOpacity>
</View>
</ImageBackground>
);
}
}
Login.js 在登录上,我有一个 link 按钮用于注册并忘记密码,以防用户没有帐户
import React, { Component } from 'react';
import {
Text,
TouchableOpacity,
Label,
View,
TextInput,
StyleSheet,
}
from 'react-native';
export default class Login extends Component {
render(){
return(
<View style={styles.container}>
<View>
<Text>Login</Text>
</View>
<Label>Email</Label>
<TextInput
style={Styles.textbox}
placeholder="Email"
value= {this.state.email}
/>
<Label>Password</Label>
<TextInput
style={Styles.textbox}
placeholder="Password"
value ={this.state.password}
secureTextEntry={true}
/>
<View>
<Text>Forgot password</Text>
</View>
<TouchableOpacity style={styles.signin}>
<Text style ={styles.signinText}>Sign In</Text>
</TouchableOpacity>
<View>
<Text>Not an APG Member? </Text>
<TouchableOpacity style={styles.signup}
onPress ={() => this.props.navigation.navigate('SignUp') }
>
<Text>Sign Up</Text>
</TouchableOpacity>
</View>
</View>
);
}
}
我希望能够从 Intro.js 和 login.js 中选择登录或注册,以便能够单击注册进行注册,然后从注册中选择可以点击登录。
解决方案
onPress={this.props.navigation.navigate('SignUp')}
不调用 this.props.navigation.navigate
函数。
如下更改您的 onPress
属性。
使用es6箭头函数制作匿名函数
<TouchableOpacity
style={styles.signup}
onPress={() => this.props.navigation.navigate('SignUp')}
>
或者您可以在 onPress
中引用您的函数。再次渲染时,它会提高性能。
navigate = () => {
this.props.navigation.navigate('SignUp')
}
return (
...
<TouchableOpacity
style={styles.signup}
onPress={this.navigate}
>
)
为什么
props
仅引用值,即使它是函数。因此,使 props
引用您预定义的 class 中的匿名函数或函数。
当你使用 not 箭头函数时不要忘记 bind(this)
。
navigate() {
this.props.navigation.navigate('SignUp')
}
...
onPress={this.navigate.bind(this)}
...