代码之家  ›  专栏  ›  技术社区  ›  gigapico00

反应本机导航。navigate()仅在onPress函数中有效

  •  -1
  • gigapico00  · 技术社区  · 2 年前

    在我的应用程序中,

    onPress={() => navigation.navigate('<ScreenName>')} 
    

    完美无瑕,但如果我尝试在一个函数中更改屏幕,例如当我点击一个按钮时调用该函数

    const signup = (mobileNumber, {navigation}) => {
    Object.keys(mobileNumber).forEach((key) => {
        console.log(mobileNumber[key]);
    });
    
    if (mobileNumber.mobileNumber == null) {
        Alert.alert("Oops!", "Please insert your mobile number.");
        return;
    }
    
    let dataToSend = {mobile_number: mobileNumber.mobileNumber};
    let formBody = [];
    for (let key in dataToSend) {
        let encodedKey = encodeURIComponent(key);
        let encodedValue = encodeURIComponent(dataToSend[key]);
        formBody.push(encodedKey + '=' + encodedValue);
    }
    formBody = formBody.join('&');
    
    fetch('https://mywebsite.com/api/v1/createAccount.php', {
        method: 'POST',
        body: formBody,
        headers: {
        //Header Defination
        'Content-Type':
        'application/x-www-form-urlencoded;charset=UTF-8',
        },
    })
    .then((response) => response.json())
    .then((responseJson) => {
    console.log(responseJson);
    // If server response message same as Data Matched
    if (responseJson.status === 'success') {
        //Alert.alert("Excellent!", "Please go on");
        navigation.navigate('<ScreenName>');
    } else {
        console.log('Please check your mobileNumber');
    }
    })
    .catch((error) => {
    //Hide Loader
    console.error(error);
    });
    }
    
    
    function JoinScreen({ navigation }) {
    const [mobileNumber, setMobileNumber] = useState(null);
    const [isLoading, setLoading] = useState(true);
    
    const [data, newData] = useState(null);
    
    useEffect(() => {
        fetch("https://mywebsite.com/api/v1/createAccount.php")
            .then((response) => response.text())
            .then((response) => newData(response));
    }, []);
    
    return (
        <>
            <StatusBar hidden />
            <SafeAreaView style={{ flex: 1, alignItems: 'center', backgroundColor: '#262423' }}>
    
                <TextInput
                    style={styles.input}
                    placeholder="Your mobile number"
                    placeholderTextColor="#fff"
                    autoCapitalize="none"
                    autoCorrect={false}
                    onChangeText={(val) => setMobileNumber(val)}
                    keyboardType="phone-pad"
                />
    
                <TouchableOpacity onPress={() => signup({ mobileNumber })}>
                    <Text style={{ textAlign: "center", paddingTop: 20, color: "#babf26", fontSize: 20 }} >Create account</Text>
                </TouchableOpacity>
            </SafeAreaView>
        </>
    );
    

    }

    应用程序返回“ TypeError:undefined不是对象(正在计算“_ref6.navigation”) "

    如果有帮助,如果在“注册”功能中,我没有将“导航”括在花括号中,我会得到“ undefined不是对象(正在评估“navigation.navigate”) "

    2 回复  |  直到 2 年前
        1
  •  1
  •   David Scholz    2 年前

    你不能通过考试 navigation 反对 signup 作用声明

    const signup = (mobileNumber, {navigation})
    

    无效。大括号用于分解传递给函数的对象的属性。原因是什么 JoinScreen({ navigation }) 工作(很可能)是因为 JoinScreen 定义为导航器内的屏幕。因此,导航框架会将一个对象传递给导航器中定义为屏幕的所有屏幕,该对象的一部分是 航行 对象,可以使用大括号对其进行分解。

    对于 报名 事实并非如此,因为这只是一个函数。但是,你可以直接从 联合屏蔽 如下。

    function JoinScreen({ navigation }) {
     ...
      <TouchableOpacity onPress={() => signup(mobileNumber, navigation)}>
                    <Text style={{ textAlign: "center", paddingTop: 20, color: "#babf26", fontSize: 20 }} >Create account</Text>
                </TouchableOpacity>
    }
    

    然后,你的注册功能。

    const signup = (mobileNumber, navigation) => {
    
    ...
    
    }
    
        2
  •  1
  •   Ian Hudicourt    2 年前

    注册函数应该位于屏幕组件内部,或者应该将导航对象作为参数传递。