Search code examples
react-nativereact-navigationreact-navigation-stack

Is there a way to hide a tab item when using createBottomTabNavigator and createStackNavigator and at the same time navigationOptions working?


I have three screens, i want to use the te tab bar only for the firsts two screens. In those two screens i put a button that navigate to the third screen. my first aproach was tis code:

import React from "react";
import { Platform } from "react-native";
import {
  createStackNavigator,
  createBottomTabNavigator,
  StackViewTransitionConfigs
} from "react-navigation";

import TabBarIcon from "../components/TabBarIcon";
import HomeScreen from "../screens/HomeScreen";
import LinksScreen from "../screens/LinksScreen";
import SettingsScreen from "../screens/SettingsScreen";

const Tabs = createBottomTabNavigator({
  Home: {
    screen: HomeScreen,
    navigationOptions: ({ navigation }) => ({
      tabBarLabel: "Home",
      title: "Tahiry",
      tabBarIcon: ({ focused }) => (
        <TabBarIcon
          focused={focused}
          name={
            Platform.OS === "ios"
              ? `ios-information-circle${focused ? "" : "-outline"}`
              : "md-information-circle"
          }
        />
      )
    })
  },
  Links: {
    screen: LinksScreen,
    navigationOptions: ({ navigation }) => ({
      tabBarLabel: "Links",
      tabBarIcon: ({ focused }) => (
        <TabBarIcon
          focused={focused}
          name={Platform.OS === "ios" ? "ios-link" : "md-link"}
        />
      )
    })
  }
});

export default createStackNavigator({
  tabs: Tabs,
  Settings: SettingsScreen
});

It is working but the "navigationOptions" are not working, so if i set a title to the header ( that is always displayed even if i set "header:null"), it doesn't appear. I tried another approach with the next code but i can no manage to hide the third tab item:

import React from 'react';
import { Platform } from 'react-native';
import { createStackNavigator, createBottomTabNavigator } from 'react-navigation';

import TabBarIcon from '../components/TabBarIcon';
import HomeScreen from '../screens/HomeScreen';
import LinksScreen from '../screens/LinksScreen';
import SettingsScreen from '../screens/SettingsScreen';

const HomeStack = createStackNavigator({
  Home: HomeScreen,
});

HomeStack.navigationOptions = {
  tabBarLabel: 'Home',
  tabBarIcon: ({ focused }) => (
    <TabBarIcon
      focused={focused}
      name={
        Platform.OS === 'ios'
          ? `ios-information-circle${focused ? '' : '-outline'}`
          : 'md-information-circle'
      }
    />
  ),
};

const LinksStack = createStackNavigator({
  Links: LinksScreen,
});

LinksStack.navigationOptions = {
  tabBarLabel: 'Links',
  tabBarIcon: ({ focused }) => (
    <TabBarIcon
      focused={focused}
      name={Platform.OS === 'ios' ? 'ios-link' : 'md-link'}
    />
  ),
};

const SettingsStack = createStackNavigator({
  Settings: SettingsScreen,
});

SettingsStack.navigationOptions = {
  tabBarLabel: 'Settings',
  tabBarIcon: ({ focused }) => (
    <TabBarIcon
      focused={focused}
      name={Platform.OS === 'ios' ? 'ios-options' : 'md-options'}
    />
  ),
};

export default createBottomTabNavigator({
  HomeStack,
  LinksStack,
  SettingsStack,
});

Any advice is welcome.


Solution

  • I finally manage to make it working. The solution is from the second approach. First you have to declare you sceens in the stacks like this:

    const HomeStack = createStackNavigator({
      Home: HomeScreen,
      Details1: DetailsScreen
    });
    

    Afterwards you have to import the tabBarIcon separately, i think its is necessary because the createStackNavigator has no TabBarIcon method

    import TabBarIcon from "../components/TabBarIcon";
    
    

    You have now navigations and icons working, you can add as many screens as you want in the stacks. and you only create tabs for the stacks.

    Here is the complete example:

    import React from "react";
    import {
      Platform,
      StatusBar,
      StyleSheet,
      View,
      Button,
      Text
    } from "react-native";
    import {
      createBottomTabNavigator,
      createStackNavigator,
      createAppContainer
    } from "react-navigation";
    import TabBarIcon from "../components/TabBarIcon";
    
    class DetailsScreen extends React.Component {
      render() {
        return (
          <View style={{ flex: 1, justifyContent: "center", alignItems: "center" }}>
            <Text>Details1!</Text>
          </View>
        );
      }
    }
    
    class DetailsScreen2 extends React.Component {
      render() {
        return (
          <View style={{ flex: 1, justifyContent: "center", alignItems: "center" }}>
            <Text>Details2!</Text>
          </View>
        );
      }
    }
    
    class HomeScreen extends React.Component {
      render() {
        return (
          <View style={{ flex: 1, justifyContent: "center", alignItems: "center" }}>
            <Text>Home!</Text>
            <Button
              title="Go to Details1"
              onPress={() => this.props.navigation.navigate("Details1")}
            />
          </View>
        );
      }
    }
    
    class SettingsScreen extends React.Component {
      render() {
        return (
          <View style={{ flex: 1, justifyContent: "center", alignItems: "center" }}>
            <Text>Settings!</Text>
            <Button
              title="Go to Details2"
              onPress={() => this.props.navigation.navigate("Details2")}
            />
          </View>
        );
      }
    }
    
    const HomeStack = createStackNavigator({
      Home: HomeScreen,
      Details1: DetailsScreen
    });
    HomeStack.navigationOptions = {
      tabBarLabel: "Home",
      tabBarIcon: ({ focused }) => (
        <TabBarIcon
          focused={focused}
          name={
            Platform.OS === "ios"
              ? `ios-information-circle${focused ? "" : "-outline"}`
              : "md-information-circle"
          }
        />
      )
    };
    
    const SettingsStack = createStackNavigator({
      Settings: SettingsScreen,
      Details2: DetailsScreen2
    });
    
    SettingsStack.navigationOptions = {
      tabBarLabel: "Maison",
      tabBarIcon: ({ focused }) => (
        <TabBarIcon
          focused={focused}
          name={
            Platform.OS === "ios"
              ? `ios-information-circle${focused ? "" : "-outline"}`
              : "md-information-circle"
          }
        />
      )
    };
    
    export default createAppContainer(
      createBottomTabNavigator(
        {
          Home: HomeStack,
          Settings: SettingsStack
        },
        {
          /* Other configuration remains unchanged */
        }
      )
    );
    
    

    and this is the content of tabBaricon.js

    import React from 'react';
    import { Icon } from 'expo';
    
    import Colors from '../constants/Colors';
    
    export default class TabBarIcon extends React.Component {
      render() {
        return (
          <Icon.Ionicons
            name={this.props.name}
            size={26}
            style={{ marginBottom: -3 }}
            color={this.props.focused ? Colors.tabIconSelected : Colors.tabIconDefault}
          />
        );
      }
    }