react-nativereact-navigationtabnavigatorreact-native-tabnavigator

Multiple headers in react native tabnavigation


I've just started getting a grip of react navigation and I followed a great tutorial on medium about Integrating the different navigation types. All works fine except I've gotten multiple headers. I'm trying to write headerShown: false somewhere but I'm quite unsure where to write it since my screenOption is taking in a route.

Sending some pics of my expo and my code.

Would really appreciate some help!

import React from "react";
import { Button, View, Text } from "react-native";
import { createBottomTabNavigator } from "@react-navigation/bottom-tabs";
import { NavigationContainer } from "@react-navigation/native";
import { createDrawerNavigator } from "@react-navigation/drawer";
import { createNativeStackNavigator } from "@react-navigation/native-stack";
import { Ionicons } from "@expo/vector-icons";

const Tab = createBottomTabNavigator();

function HomeScreen() {
  return (
    <Tab.Navigator
      screenOptions={({ route }) => ({
        tabBarIcon: ({ focused, color, size }) => {
          let iconName;
          if (route.name === "TabA") {
            iconName = focused
              ? "ios-information-circle"
              : "ios-information-circle-outline";
          } else if (route.name === "TabB") {
            iconName = focused ? "ios-list-box" : "ios-list";
          }
          return <Ionicons name={iconName} size={size} color={color} />;
        },
      })}
      tabBarOptions={{
        activeTintColor: "tomato",
        inactiveTintColor: "gray",
      }}
    >
      <Tab.Screen name="TabA" component={TabAScreen} />
      <Tab.Screen name="TabB" component={TabBScreen} />
    </Tab.Navigator>
  );
}

const Stack = createNativeStackNavigator();

function TabAScreen() {
  return (
    <Stack.Navigator>
      <Stack.Screen name="TabA Home" component={TabADetailsScreen} />
      <Stack.Screen name="TabA Details" component={Details} />
    </Stack.Navigator>
  );
}

function TabADetailsScreen({ navigation }) {
  return (
    <View style={{ flex: 1, justifyContent: "center", alignItems: "center" }}>
      <Text>Welcome to TabA page!</Text>

      <Button
        onPress={() => navigation.navigate("TabA Details")}
        title="Go to TabA Details"
      />
    </View>
  );
}

function Details() {
  return (
    <View style={{ flex: 1, justifyContent: "center", alignItems: "center" }}>
      <Text>TabA Details here!</Text>
    </View>
  );
}

function TabBScreen() {
  return (
    <View>
      <Text style={{ textAlign: "center", marginTop: 300 }}>
        Welcome to TabB page!
      </Text>
    </View>
  );
}

function NotificationScreen({ navigation }) {
  return (
    <View style={{ flex: 1, alignItems: "center", justifyContent: "center" }}>
      <Button onPress={() => navigation.goBack()} title="Go back home" />
    </View>
  );
}

const Drawer = createDrawerNavigator();

export default function App() {
  return (
    <NavigationContainer>
      <Drawer.Navigator initialRouteName="Home">
        <Drawer.Screen name="Home" component={HomeScreen} />
        <Drawer.Screen name="Notifications" component={NotificationScreen} />
      </Drawer.Navigator>
    </NavigationContainer>
  );
}

enter image description hereenter image description here

I have tried writing headerShown false in the homeScreen function but I'm unsure of where to put it since it is taking in a route and every time I write headerShown false it seems to create other problems with the route part.


Solution

  • While it is possible to pass a function to screenOptions, the function still returns the same object where headerShown can be defined like this:

    <Tab.Navigator
      screenOptions={({ route }) => ({
        headerShown: false,
        tabBarIcon: ({ focused, color, size }) => {
    ...
        },
      })}
    ...
    >
      <Tab.Screen name="TabA" component={TabAScreen} />
      <Tab.Screen name="TabB" component={TabBScreen} />
    </Tab.Navigator>
    

    For other navigators with an object like this:

    <X.Navigator screenOptions={{headerShown: false}}>
    ...
    </X.Navigator>