反应本地登录和登录导航-正确的方式建议 [英] React native login and loggedin navigation - correct way advise
本文介绍了反应本地登录和登录导航-正确的方式建议的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!
问题描述
请找人告诉我登录和登录导航系统的正确方式。我现在所做的就是使用共享状态的Use-Better包来使用共享状态,并显示正确的导航。但我不确定这是不是正确的做法。请有人指出正确的方向和正确的方式来实现同样的目标。以下是我的代码。
import React, { useEffect } from "react";
import { useLoggedInUserState } from "./core/state";
import { useBetween } from "use-between";
import { getLoggedInUser } from "./core/utils";
//navigation
import LoginNav from "./nav/LoginNav";
import LoggedInNav from "./nav/LoggedInNav";
export default function App() {
//shared states
const { loggedInUser, setLoggedInUser } = useBetween(useLoggedInUserState);
//check storage and store user in state
useEffect(async () => {
const objUser = await getLoggedInUser();
setLoggedInUser(objUser);
}, []);
//render
return loggedInUser ? <LoggedInNav loggedInUser={loggedInUser} /> : <LoginNav />;
}
//login nav
已登录导航
import React, { memo } from "react";
import { createDrawerNavigator } from "@react-navigation/drawer";
import { NavigationContainer, CommonActions, useNavigation } from "@react-navigation/native";
import { Appbar, BottomNavigation, Menu, useTheme, Button } from "react-native-paper";
import { Text, Image, View, TouchableOpacity } from "react-native";
import { AboutScreen, TermsScreen, CartScreen, PaymentScreen, NotificationTestScreen, VehicleEditScreen } from "../screens";
import Sidebar from "../components/Sidebar";
import BottomNav from "./BottomNav";
const Drawer = createDrawerNavigator();
//LoggedIn Navigation
const LoggedInNav = (propsLoggedIn) => {
const { colors, background } = useTheme();
//const [visible, setVisible] = React.useState(false); //used by appbar
//const openMenu = () => setVisible(true); //used by appbar
//const closeMenu = () => setVisible(false); //used by appbar
const cartCount = 40; //will be from state
return (
<NavigationContainer>
<Drawer.Navigator
screenOptions={(propsNavigator) => ({
headerShown: true,
headerLeft: () => (
<View
style={{
flex: 1,
alignItems: "center",
justifyContent: "center",
flexDirection: "row",
}}
>
<TouchableOpacity onPress={() => propsNavigator.navigation.openDrawer()}>
<Image
source={require("../assets/images/menu.png")}
style={{
tintColor: "#fff",
width: 28,
height: 28,
position: "relative",
marginLeft: 8,
}}
/>
</TouchableOpacity>
<TouchableOpacity onPress={() => propsNavigator.navigation.navigate("Dashboard")}>
<Image
source={require("../assets/images/home.png")}
style={{
tintColor: "#fff",
width: 28,
height: 28,
position: "relative",
marginLeft: 8,
}}
/>
</TouchableOpacity>
</View>
),
headerRight: () => (
<View
style={{
flex: 1,
alignItems: "center",
justifyContent: "center",
flexDirection: "row",
}}
>
<TouchableOpacity
onPress={() => {
propsNavigator.navigation.navigate("NotificationTest");
}}
>
<Image
source={require("../assets/images/bell.png")}
style={{
tintColor: "#fff",
width: 32,
height: 32,
position: "relative",
marginRight: 4,
}}
/>
</TouchableOpacity>
<TouchableOpacity
onPress={() => {
propsNavigator.navigation.navigate("Cart");
}}
>
<Image
source={require("../assets/images/cart.png")}
style={{
tintColor: "#fff",
width: 32,
height: 32,
position: "relative",
marginRight: 16,
}}
/>
</TouchableOpacity>
{cartCount > 0 ? (
<View
style={{
position: "absolute",
backgroundColor: "red",
width: 16,
height: 16,
borderRadius: 15 / 2,
right: 10,
top: +8,
alignItems: "center",
justifyContent: "center",
}}
>
<Text
style={{
alignItems: "center",
justifyContent: "center",
color: "#FFFFFF",
fontSize: 8,
}}
>
{cartCount}
</Text>
</View>
) : null}
</View>
),
headerStyle: {
backgroundColor: colors.primary,
},
headerTintColor: "#fff",
headerTitleStyle: {
fontWeight: "bold",
},
/* header using react native paper
header: ({ navigation, back, route }) => (
<Appbar.Header>
{back ? <Appbar.BackAction onPress={navigation.goBack} /> : null}
<Appbar.Content title={route.params.title ? route.params.title : "Between Detailing"} />
{!back ? (
<Menu visible={visible} onDismiss={closeMenu} anchor={<Appbar.Action icon="menu" color="white" onPress={openMenu} />}>
<Menu.Item
onPress={() => {
navigation.navigate("Dashboard");
}}
title="Dashboard"
/>
<Menu.Item
onPress={() => {
navigation.navigate("About");
}}
title="About"
/>
<Menu.Item
onPress={() => {
navigation.navigate("Terms");
}}
title="Terms"
//disabled
/>
</Menu>
) : null}
</Appbar.Header>
),header using react native paper */
})}
drawerContent={(drawerContentProps) => <Sidebar loggedInUser={propsLoggedIn.loggedInUser} {...drawerContentProps} />}
>
<Drawer.Screen name="Dashboard" component={BottomNav} initialParams={{ title: "Dashboard" }} />
<Drawer.Screen name="About" component={AboutScreen} initialParams={{ title: "About" }} />
<Drawer.Screen name="Terms" component={TermsScreen} initialParams={{ title: "Terms" }} />
<Drawer.Screen name="VehicleEdit" component={VehicleEditScreen} initialParams={{ title: "Edit Vehicle" }} />
<Drawer.Screen name="Cart" component={CartScreen} initialParams={{ title: "Cart" }} options={{ drawerItemStyle: { display: "none" } }} />
<Drawer.Screen name="Payment" component={PaymentScreen} initialParams={{ title: "Payment" }} options={{ drawerItemStyle: { display: "none" } }} />
<Drawer.Screen name="NotificationTest" component={NotificationTestScreen} initialParams={{ title: "NotificationTest" }} options={{ drawerItemStyle: { display: "none" } }} />
</Drawer.Navigator>
</NavigationContainer>
);
};
export default memo(LoggedInNav);
谢谢您指向那个链接,我想我的方向差不多是对的。根据这篇文章,我对我的代码做了一些修改,它工作得很好。
我唯一关心的是我在LoginNav和LoggedInNav中都有2个导航容器1,如下所示。对这种情况有什么看法,这样做对吗?
//登录导航
const LoginNav = () => {
return (
<NavigationContainer>
<Stack.Navigator
screenOptions={{
headerShown: false,
}}
initialRouteName="Home"
>
<Stack.Screen name="Home" component={HomeScreen} />
<Stack.Screen name="Login" component={LoginScreen} />
<Stack.Screen name="Register" component={RegisterScreen} />
<Stack.Screen name="ForgotPassword" component={ForgotPasswordScreen} />
<Stack.Screen name="Dashboard" component={DashboardScreen} />
</Stack.Navigator>
</NavigationContainer>
);
};
//登录导航
//LoggedIn Navigation
const LoggedInNav = (propsLoggedIn) => {
const { colors, background } = useTheme();
//const [visible, setVisible] = React.useState(false); //used by appbar
//const openMenu = () => setVisible(true); //used by appbar
//const closeMenu = () => setVisible(false); //used by appbar
const cartCount = 40; //will be from state
return (
<NavigationContainer>
<Drawer.Navigator
drawerContent={(drawerContentProps) => <Sidebar loggedInUser={propsLoggedIn.loggedInUser} {...drawerContentProps} />}
>
<Drawer.Screen name="Dashboard" component={BottomNav} initialParams={{ title: "Dashboard" }} />
<Drawer.Screen name="About" component={AboutScreen} initialParams={{ title: "About" }} />
<Drawer.Screen name="Terms" component={TermsScreen} initialParams={{ title: "Terms" }} />
<Drawer.Screen name="VehicleEdit" component={VehicleEditScreen} initialParams={{ title: "Edit Vehicle" }} />
<Drawer.Screen name="Cart" component={CartScreen} initialParams={{ title: "Cart" }} options={{ drawerItemStyle: { display: "none" } }} />
<Drawer.Screen name="Payment" component={PaymentScreen} initialParams={{ title: "Payment" }} options={{ drawerItemStyle: { display: "none" } }} />
<Drawer.Screen name="NotificationTest" component={NotificationTestScreen} initialParams={{ title: "NotificationTest" }} options={{ drawerItemStyle: { display: "none" } }} />
</Drawer.Navigator>
</NavigationContainer>
);
};
//导航
import LoginNav from "./nav/LoginNav";
import LoggedInNav from "./nav/LoggedInNav";
export default function App() {
//shared states
const { loggedInUser, setLoggedInUser } = useBetween(useLoggedInUserState);
//common states
const [loading, setLoading] = useState(false);
//check storage and store user in state
useEffect(async () => {
setLoading(true);
const objUser = await getLoggedInUser();
setLoggedInUser(objUser);
setLoading(false);
}, []);
//render
if (!loading) {
return loggedInUser ? <LoggedInNav loggedInUser={loggedInUser} /> : <LoginNav />;
} else {
return (
<View>
<Text>Loading...</Text>
</View>
);
}
}
推荐答案
推荐的最佳做法是只有一个NavigationContainer
。我认为所有导航状态都有一个真实来源很重要。
尝试如下重构代码:
export default function App() {
//shared states
const { loggedInUser, setLoggedInUser } = useBetween(useLoggedInUserState);
//common states
const [loading, setLoading] = useState(false);
//check storage and store user in state
useEffect(async () => {
setLoading(true);
const objUser = await getLoggedInUser();
setLoggedInUser(objUser);
setLoading(false);
}, []);
//render
return !loading ? (
<NavigationContainer>
{loggedInUser ? (
<Drawer.Navigator
drawerContent={(drawerContentProps) => (
<Sidebar
loggedInUser={propsLoggedIn.loggedInUser}
{...drawerContentProps}
/>
)}
>
<Drawer.Screen
name="Dashboard"
component={BottomNav}
initialParams={{ title: "Dashboard" }}
/>
<Drawer.Screen
name="About"
component={AboutScreen}
initialParams={{ title: "About" }}
/>
<Drawer.Screen
name="Terms"
component={TermsScreen}
initialParams={{ title: "Terms" }}
/>
<Drawer.Screen
name="VehicleEdit"
component={VehicleEditScreen}
initialParams={{ title: "Edit Vehicle" }}
/>
<Drawer.Screen
name="Cart"
component={CartScreen}
initialParams={{ title: "Cart" }}
options={{ drawerItemStyle: { display: "none" } }}
/>
<Drawer.Screen
name="Payment"
component={PaymentScreen}
initialParams={{ title: "Payment" }}
options={{ drawerItemStyle: { display: "none" } }}
/>
<Drawer.Screen
name="NotificationTest"
component={NotificationTestScreen}
initialParams={{ title: "NotificationTest" }}
options={{ drawerItemStyle: { display: "none" } }}
/>
</Drawer.Navigator>
) : (
<Stack.Navigator
screenOptions={{
headerShown: false,
}}
initialRouteName="Home"
>
<Stack.Screen name="Home" component={HomeScreen} />
<Stack.Screen name="Login" component={LoginScreen} />
<Stack.Screen name="Register" component={RegisterScreen} />
<Stack.Screen
name="ForgotPassword"
component={ForgotPasswordScreen}
/>
<Stack.Screen name="Dashboard" component={DashboardScreen} />
</Stack.Navigator>
)}
</NavigationContainer>
) : (
<View>
<Text>Loading...</Text>
</View>
);
}
这篇关于反应本地登录和登录导航-正确的方式建议的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!
查看全文