как получить доступ к navigation.toggleDrawer() из навигатора стека?

#react-native #react-navigation

Вопрос:

У меня есть осязаемый значок в заголовке стека, когда я выполняю console.log({ навигация}). Я понимаю это:

 Object {
  "navigation": Object {
    "accessibilityLabel": undefined,
    "allowFontScaling": undefined,
    "backImage": undefined,
    "canGoBack": false,
    "label": undefined,
    "labelStyle": Array [
      undefined,
      undefined,
    ],
    "labelVisible": undefined,
    "onLabelLayout": [Function handleLeftLabelLayout],
    "onPress": undefined,
    "pressColorAndroid": undefined,
    "screenLayout": Object {
      "height": 667.2941284179688,
      "width": 338.8235168457031,
    },
    "tintColor": "#F5EDED",
    "titleLayout": Object {
      "height": 29.647058486938477,
      "width": 250.8235321044922,
    },
    "truncatedLabel": undefined,
  },
}

 

Я включил свой навигационный код ниже, начиная с навигации по ящику.

 import React from "react";

import { createStackNavigator } from "@react-navigation/stack";
import { createDrawerNavigator } from "@react-navigation/drawer";
import { createMaterialBottomTabNavigator } from "@react-navigation/material-bottom-tabs";

import MaterialCommunityIcons from "react-native-vector-icons/MaterialCommunityIcons";

import HomeScreen from "../screens/HomeScreen";
import BodyPartsScreen from "../screens/BodyPartsScreen";
import PreMadeScreen from "../screens/PreMadeScreen";
import WorkoutDiaryScreen from "../screens/WorkoutDiaryScreen";
import StatsScreen from "../screens/StatsScreen";
import HistoryScreen from "../screens/HistoryScreen";
import ChestListScreen from "../screens/ChestListScreen";
import ExerciseSelectedScreen from "../screens/ExerciseSelectedScreen";
import StartWorkoutScreen from "../screens/StartWorkoutScreen";

import ContactSupportScreen from "../screens/ContactSupportScreen";
import FeatureRequestScreen from "../screens/FeatureRequestScreen";
import MeasurementsScreen from "../screens/MeasurementsScreen";
import MembershipScreen from "../screens/MembershipScreen";
import SettingsScreen from "../screens/SettingsScreen";
import DrawerContent from "../screens/DrawerContent";
import ProfileScreen from "../screens/ProfileScreen";



/////////////////////// Drawer //////////////////////////////////////////

const Drawer = createDrawerNavigator();

export const DrawerNavigator = (props, navigation) => {
  return (
    <Drawer.Navigator
      initialRouteName="Home"
      drawerContent={(props) => <DrawerContent {...props} />}
    >
      <Drawer.Screen
        name="Home"
        component={HomeScreen}
        options={{
          title: "Back",
          headerStyle: {
            backgroundColor: "#000000",
          },
        }}
      />

      <Drawer.Screen
        name="Membership"
        component={MembershipScreen}
        options={{
          title: "Membership",
          headerStyle: {
            backgroundColor: "#000000",
          },
        }}
      />
      <Drawer.Screen
        name="Profile"
        component={ProfileScreen}
        options={{
          title: "profile",
          headerStyle: {
            backgroundColor: "#000000",
          },
        }}
      />
      <Drawer.Screen
        name="Measurements"
        component={MeasurementsScreen}
        options={{
          title: "Measurements",
          headerStyle: {
            backgroundColor: "#000000",
          },
        }}
      />
      <Drawer.Screen
        name="Feature"
        component={FeatureRequestScreen}
        options={{
          title: "Feature Request",
          headerStyle: {
            backgroundColor: "#000000",
          },
        }}
      />
      <Drawer.Screen
        name="Contact"
        component={ContactSupportScreen}
        options={{
          title: "Contact",
          headerStyle: {
            backgroundColor: "#000000",
          },
        }}
      />
    </Drawer.Navigator>
  );
};
 

Навигация по вкладкам.

 ////////////////// Tabs /////////////////////////////

const Tab = createMaterialBottomTabNavigator();

export function TabNavigator({ navigation }) {
  return (
    <Tab.Navigator
      initialRouteName="Home"
      activeColor="#D72323"
      barStyle={{ backgroundColor: "#000000" }}
    >
      <Tab.Screen
        name="Home"
        component={DrawerNavigator}
        options={{
          tabBarIcon: ({ color }) => (
            <MaterialCommunityIcons name="home" color={color} size={26} />
          ),
        }}
      />
      <Tab.Screen
        name="Workout"
        component={StartWorkoutScreen}
        options={{
          tabBarIcon: ({ color }) => (
            <MaterialCommunityIcons
              name="weight-lifter"
              color={color}
              size={26}
            />
          ),
        }}
      />
      <Tab.Screen
        name="Settings"
        component={SettingsScreen}
        options={{
          tabBarIcon: ({ color }) => (
            <MaterialCommunityIcons
              name="cog-outline"
              color={color}
              size={26}
            />
          ),
        }}
      />
    </Tab.Navigator>
  );
}
 

Навигация по стеку.

 ////////////////////////// Stack /////////////////////////////////////

const Stack = createStackNavigator();

export function StackNavigator(props, navigation) {
  return (
    <Stack.Navigator
      initialRouteName="Home"
      screenOptions={{
        headerStyle: {
          backgroundColor: "#000000",
        },

        headerTintColor: "#F5EDED",
        headerTitleStyle: {
          fontWeight: "bold",
        },
      }}
    >
      <Stack.Screen
        name="HomeScreen"
        component={TabNavigator}
        options={({ navigation }) => ({
          headerLeft: () => (
            <MaterialCommunityIcons
              onPress={() => navigation.toggleDrawer()}
              name="forwardburger"
              color="#F5EDED"
              size={26}
            />
          ),
        })}
      />
      <Stack.Screen
        name="Drawer"
        component={DrawerContent}
        options={{
          title: "Drawer",
        }}
      />
      <Stack.Screen
        name="Body"
        component={BodyPartsScreen}
        options={{
          title: "Body Parts",
        }}
      />
      <Stack.Screen
        name="Diary"
        component={WorkoutDiaryScreen}
        options={{
          title: "Workout Diary",
        }}
      />
      <Stack.Screen
        name="PreMade"
        component={PreMadeScreen}
        options={{
          title: "Pre Made Workouts",
        }}
      />
      <Stack.Screen
        name="Stats"
        component={StatsScreen}
        options={{
          title: "Your Workout Stats",
        }}
      />
      <Stack.Screen
        name="History"
        component={HistoryScreen}
        options={{
          title: "Your Workout History",
        }}
      />
      <Stack.Screen
        name="Chest"
        component={ChestListScreen}
        options={{
          title: "Champion Chest",
        }}
      />

      <Stack.Screen
        name="ExerciseSelected"
        component={ExerciseSelectedScreen}
        options={{
          title: "Customise Your Exercise",
        }}
      />
    </Stack.Navigator>
  );
}

 

Мне нужно получить доступ к navigation.toggleDrawer() или navigation.openDrawer (), как это возможно? У меня есть значок, установленный в моем навигаторе, а не на экране, который я хочу использовать, но он появляется там.

Ответ №1:

На экране, где вы устанавливаете свой значок, сделайте это:

     const StackNav = () => {
      return (
        <Stack.Navigator>
          <Stack.Screen
            name="Screen Name"
            component={ScreenComponent}
            options={({navigation}) => ({
              headerLeft: () => (
                <TouchableOpacity onPress={() => navigation.toggleDrawer()}>
                  <Icon name="menu" />
                </TouchableOpacity>
              ),
            })}
          />
        ...
        </Stack.Navigator>
      );
    };
 

Обратите внимание, что ваш StackNav компонент должен быть прямым потомком вашего DrawerNavigator .

Редактировать

После анализа вашего кода я сделал рабочую закуску, которая демонстрирует, как правильно его использовать DrawerNavigator .

Обратите внимание, что я сделал некоторые предположения о том, чего вы пытаетесь достичь, но это обычный способ настройки навигации. Вот ссылка на демонстрационную версию: Закуска.

Комментарии:

1. Спасибо за ответ. Я продолжаю получать сообщение об ошибке в консоли . навигация.toggleDrawer-это не функция. (в «navigation.toggleDrawer ()» навигация.toggleDrawer » не определена) есть идеи, как с этим справиться?

2. @Ty87 Это означает, что вы не получаете navigation объект вашего DrawerNavigator , возможно, что-то не так с тем, как вы его используете. Не могли бы вы изменить свой вопрос и добавить код вашего DrawerNavigator и вашего StackNavigator ?

3. Спасибо. Я отредактировал вопрос, чтобы включить мой полный навигационный код.

4. @Ty87 Да, ваша настройка навигации довольно запутана. Я не уверен, чего именно вы пытаетесь достичь с помощью навигации по вашему приложению, но есть несколько явных ошибок. Вы DrawerNavigator должны быть родителем всех остальных навигаторов, так как вы, скорее всего, хотите, чтобы пользователь мог получить доступ к ящику из любой точки приложения.

5. @Ty87 В вашей текущей реализации не navigation.toggleDrawer() определен, потому что ваш DrawerNavigator файл вложен глубоко в один из ваших Stack.Screen , поэтому StackNavigator у вас нет возможности получить доступ к navigation реквизиту вашего ящика, поскольку props он передается от родителя к ребенку, поэтому ваш ящик должен быть вверху, если вы хотите, чтобы все дети имели доступ к его реквизиту. Я отредактирую свой ответ и включу простую закуску о том, как использовать a DrawerNavigator .