选项卡内的条件导航

Conditional navigation inside Tabs

我想根据状态显示屏幕。 因此,当我单击左下角的选项卡时,if 有一个有效用户,我想被重定向到 UserProfile-screen,else 重定向到 LoginScreen。 反应本机导航让我感到困惑,我只是看不出有什么问题。 所以在 LoginRoutes.tsx 中,我只是尝试使用 true / false 来改变这种行为 提前致谢。

我目前拥有的:

BottomTabBar.tsx:

export const BottomTabNavigator = () => {
  const colorScheme = useColorScheme();
  return (
    <Tab.Navigator
      screenOptions={{
        tabBarShowLabel: true,
        tabBarStyle: {
          backgroundColor: "#292929",
          borderTopWidth:0
        },
        tabBarInactiveTintColor: "#919191",
        tabBarInactiveBackgroundColor: "#292929",
        tabBarActiveTintColor: Colors[colorScheme].text,
        headerShown: false,
      }}
    >
     <Tab.Screen
        name="LoginRoutes"
        component={LoginRoutes}
        options={{ title: "Login", headerShown: false}}
      />

      <Tab.Screen
        name="SettingsTabScreen"
        component={SettingsTabScreen}
        options={{ headerShown: false,title:"test" }}
      />
    </Tab.Navigator>
  );
};

LoginRoutes.tsx

import * as React from "react";
import { ActivityIndicator, View, Text } from "react-native";
import AsyncStorage from "@react-native-async-storage/async-storage";
import { createStackNavigator } from "@react-navigation/stack";
import NavigationContainer from "./UserProfileStack";
import LoginScreen from "../Screens/LoginScreen";
import UserProfile from "../components/UserProfile";
import Colors from "../constants/Colors";
import { UserProfileInfo } from "../constants/Types";

function LoginRoutes({ navigation }: { navigation: any }) {
  const [loading, setLoading] = React.useState(true);
  const [user, setUser] = React.useState(null);

  const Stack = createStackNavigator();

  React.useEffect(() => {
    // check if the user is logged in or not
    AsyncStorage.getItem("user")
      .then((userString) => {
        if (userString) {
          console.log("-----------EXISTING------------");
          console.log(JSON.parse(userString).id);
          setUser(JSON.parse(userString));
        } else {
          console.log("not logged in, showing LoginPage");
        }
        setLoading(false);
      })
      .catch((err) => {
        console.log(err);
        setLoading(false);
      });
  }, []);

  if (loading) {
    return (
      <View
        style={{
          height: "100%",
          justifyContent: "center",
          backgroundColor: Colors.dark.background,
        }}
      >
        <ActivityIndicator
          size="large"
          style={{ backgroundColor: Colors.dark.background }}
        />
        <Text
          style={{
            color: Colors.dark.text,
            marginTop: 10,
            alignSelf: "center",
          }}
        >
          retrieving userdata...
        </Text>
      </View>
    );
  }
  return (
    <NavigationContainer>
      <Stack.Navigator>
        {true ? (
          <Stack.Screen name="LoginScreen" component={LoginScreen} />
        ) : (
          <Stack.Screen name="UserProfile" component={UserProfile} />
        )}
      </Stack.Navigator>
    </NavigationContainer>
  );
}

export default LoginRoutes;

stackNavigator:

import { createStackNavigator } from "react-navigation-stack";
import { createAppContainer } from "react-navigation";


import LoginScreen from "../Screens/LoginScreen";
import UserProfile from "../components/UserProfile";
import { UserProfileInfo } from "../constants/Types";
import { StackNavigationProp } from '@react-navigation/stack';
export type UserProfileStackParams = {
    LoginScreen: undefined, 
    UserProfile: { profileInfo: UserProfileInfo };
  };

const screens = {
  LoginScreen: {
    screen: LoginScreen,
    navigationOptions: {headerShown: false,gestureEnabled:false},
  },
  UserProfile: {
    screen: UserProfile,
    navigationOptions: {headerShown: false,gestureEnabled:false},
  },
};

// home stack navigator screens
const UserProfileStack = createStackNavigator(screens);

export default createAppContainer(UserProfileStack);

UserProfile.tsx


type Props = {
  navigation: StackNavigationProp<UserProfileStackParams, "UserProfile">
  loggedInUser: {}
};


const DATA = [
  {
    // contains valid data
  },
];
  export const UserProfile: React.FC<Props> = ({ navigation}) => {
  const [steamID, setSteamID] = React.useState({ id: null, watchLists: null });
  const [profileInfo, setProfileInfo] = React.useState<UserProfileInfo>(null);
  const [loading, setLoading] = React.useState(true);

  React.useEffect(() => {
    // check if the user is logged in or not
    AsyncStorage.getItem("user")
      .then((userString) => {
        if (userString) {
          console.log("logged in.");
          setSteamID(JSON.parse(userString));
          fetchUserProfile(steamID.id).then((response) => {
            setProfileInfo(response);
          });
        } else {
          console.log("not logged in, showing LoginPage");
        }
        setLoading(false);
      })
      .catch((err) => {
        console.log(err);
        setLoading(false);
      });
  }, []);

  return (
    <>
              <Button
                title="btn"
                onPress={() => {
                  navigation.navigate("LoginScreen")
                }}
              ></Button>

export default UserProfile;

BottomTabNavigator 中,您可以检查用户是否已登录。您可以像在 UserProfile.tsx 文件中获取用户一样获取用户。


export const BottomTabNavigator = () => {
  const [user, setUser] = React.useState(null);

  React.useEffect(() => {
    // check for user
  }, []);
  
  return (
    <Tab.Navigator
      screenOptions={{ ... }}
    >
     <Tab.Screen
        name="LoginRoutes"
        component={user ? UserScreen : LoginScreen}
      />
    </Tab.Navigator>
  );
};

或者,您可以考虑通过 Context Provider 获取用户,这样您就不必在每次要查看用户是否登录时都检查存储。

在此处阅读更多相关信息:

How To Manage User State with React Context

React Context