0

WARN Require cycle: src\Navigation\StackNavigation.js -> src\Navigation\TabsNavigation.js -> src\Navigation\StackNavigation.jsRequire cycles are allowed, but can result in uninitialized values. Consider refactoring to remove the need for a cycle.

I'm starting on react native and nesting navigators is quite a challenge to me. When the dashboard is displayed, the above warning is displayed.

When I try to navigate to ProductsStack, this error is displayed.
ERROR Warning: Cannot update a component (BottomTabNavigator) while rendering a different component (ProductsStack). To locate the bad setState() call inside ProductsStack, follow the stack trace as described in https://reactjs.org/link/setstate-in-render

Below is my code: **StackNavigation.js **

`import React from 'react'
import { createStackNavigator } from "@react-navigation/stack";
import Brands from '../Screens/Brands'
import Products2 from '../Screens/Products2'
import Warehouses from '../Screens/Warehouses'
import AdminProfile from '../Screens/AdminProfile'
import Products from '../Screens/Products'
import Purchases from '../Screens/Purchases'
import Sales from '../Screens/Sales'
import Expenses from '../Screens/Expenses'
import Accounting from '../Screens/Accounting'
import TabsNavigation from './TabsNavigation';
import More from '../Screens/More';
import Login from '../auth/Login'
import { getFocusedRouteNameFromRoute } from '@react-navigation/native';
import Categories2 from '../Screens/Categories2';


const Stack=createStackNavigator()
const tabHiddenRoutes = ["Categories","Brands","Products2","Warehouses","AdminProfile","Products","Purchases","Sales","Expenses","Accounting"];


const MainStack = () => {
  return (
    <Stack.Navigator 
    screenOptions={{headerShown:false}} initialRouteName='Dashboard2'>
    <Stack.Screen name='Dashboard2' component={TabsNavigation}/>
      </Stack.Navigator>
  )
}

const ProductsStack = ({navigation,route}) => {
if(tabHiddenRoutes.includes(getFocusedRouteNameFromRoute(route))){
  navigation.setOptions({tabBarStyle: {display: 'none'}});
 } else {
 navigation.setOptions({tabBarStyle: {display: 'flex'}});
}
    return (
      <Stack.Navigator>
      <Stack.Screen name='Products3' component={Products} options={{headerShown:false}} />
      {/* <Stack.Screen name='Categories' component={Categories} /> */}
      <Stack.Screen name='Categories' component={Categories2} />
      <Stack.Screen name='Brands' component={Brands} />
      <Stack.Screen name='Products2' component={Products2}  options={{title:'Products'}}/>
      <Stack.Screen name='Warehouses' component={Warehouses} />
  
      </Stack.Navigator>
    )
  }
  const MoreStack = ({navigation,route}) => {
    if(tabHiddenRoutes.includes(getFocusedRouteNameFromRoute(route))){
      navigation.setOptions({tabBarStyle: {display: 'none'}});
     } else {
     navigation.setOptions({tabBarStyle: {display: 'flex'}});
    }
    return (
      <Stack.Navigator>
      <Stack.Screen name='More2' component={More} options={{headerShown:false}}/>
      <Stack.Screen name='AdminProfile' component={AdminProfile} />
      <Stack.Screen name='Products' component={Products} />
      <Stack.Screen name='Purchases' component={Purchases} />
      <Stack.Screen name='Sales' component={Sales} />
      <Stack.Screen name='Expenses' component={Expenses} />
      <Stack.Screen name='Accounting' component={Accounting} />
  
      </Stack.Navigator>
    )
  }


export {MainStack,ProductsStack,MoreStack}`

**TabsNavigation.js **

import { View, Text } from 'react-native'
import React from 'react'
import { createBottomTabNavigator } from '@react-navigation/bottom-tabs';
import Dashboard from '../Screens/Dashboard';
import POS from '../Screens/POS';
import Reports from '../Screens/Reports'
import Ionicons from 'react-native-vector-icons/Ionicons'
import Icon from 'react-native-vector-icons/MaterialCommunityIcons';  ;
import { Platform, TouchableOpacity } from 'react-native';
import { MoreStack, ProductsStack } from './StackNavigation';
import { useNavigation } from '@react-navigation/native'


const Tabs = createBottomTabNavigator();
const TabsNavigation = () => {
  const navigation=useNavigation()
  
  return (
    <Tabs.Navigator screenOptions={{headerShown:'false',
    tabBarStyle:{backgroundColor:'white',minHeight:60,fontSize:16,paddingBottom:10
    },
    tabBarInactiveTintColor:'grey',
    tabBarActiveTintColor:"#38BDF8"}}>
    <Tabs.Screen name='Dashboard' component={Dashboard} options={
      {headerShown:false,
        tabBarIcon:({color,size})=>(
         <Icon name='home' color={color} size={30} />
          
        )
      }
    }/>
    <Tabs.Screen name='Products' component={ProductsStack} options={{
      headerShown:false,
        tabBarIcon:({color,size})=>(
         <Icon name='microsoft-xbox-controller-view' color={color} size={30} />
          
        )
      }
    }/>
    <Tabs.Screen name='POS' component={POS} options={{
      tabBarStyle:{display:'none'},
          headerLeft: () => (
            <TouchableOpacity onPress={() => {navigation.goBack()}}>
                <Ionicons name='arrow-back-outline' size={25} color={'black'} style={{marginLeft:10}}/>
              </TouchableOpacity>
              
            
          ),
        tabBarLabel: () => null,
        tabBarIcon:({color,size})=>{
          return(
            <View style={{
              top:Platform.OS=="ios" ? -10:-20,
              width:Platform.OS=="ios"?50:60,
              height:Platform.OS=="ios"?50:60,
              borderRadius:Platform.OS=="ios"?25:20,
              backgroundColor:"#38BDF8",
              alignItems:'center',
              justifyContent:'center',
              padding:5
              
            }}>
              <Icon name='point-of-sale' size={50} color={"white"}  />
            </View>
          )
        }
        
      }
    }/>
    <Tabs. Screen name='Reports' component={Reports} options={
      {
        tabBarIcon:({color,size})=>(
         <Icon name='chart-areaspline' color={color} size={30} />
          
        )
      }
    }/>
      <Tabs.Screen name='More' component={MoreStack} options={{
      headerShown:false,
        tabBarIcon:({color,size})=>(
         <Icon name='view-grid-plus' color={color} size={30} />
          
        )
      }
    }/>
  </Tabs.Navigator>
  )
}


export default TabsNavigation

I've removed the unused imports but still has the warning

1 Answer 1

0

I fixed the require cycle error by writing my navigation in one file

    import { View,Platform, TouchableOpacity } from 'react-native'
import React, { useEffect } from 'react'
import { createBottomTabNavigator } from '@react-navigation/bottom-tabs';
import { useNavigation } from '@react-navigation/native'
import { createStackNavigator } from "@react-navigation/stack";
import { getFocusedRouteNameFromRoute } from '@react-navigation/native';
import Dashboard from '../Screens/Dashboard';
import POS from '../Screens/POS';
import Reports from '../Screens/Reports'
import Ionicons from 'react-native-vector-icons/Ionicons'
import Icon from 'react-native-vector-icons/MaterialCommunityIcons';  ;
import More from '../Screens/More';
import Brands from '../Screens/Brands'
import Products2 from '../Screens/Products2'
import Warehouses from '../Screens/Warehouses'
import AdminProfile from '../Screens/AdminProfile'
import Products from '../Screens/Products'
import Purchases from '../Screens/Purchases'
import Sales from '../Screens/Sales'
import Expenses from '../Screens/Expenses'
import Accounting from '../Screens/Accounting'
import Categories2 from '../Screens/Categories2';
import Login from '../auth/Login'
// import SignUp from '../auth/SignUp'


const Tabs = createBottomTabNavigator();
const Stack=createStackNavigator()
const tabHiddenRoutes = ["Categories","Brands","Products2","Warehouses","AdminProfile","Products","Purchases","Sales","Expenses","Accounting"];
const MainStack = () => {
    return (
      <Stack.Navigator 
      screenOptions={{headerShown:false}} initialRouteName='Login'>
      <Stack.Screen name='Login' component={Login}/>
      {/* <Stack.Screen name='SignUp' component={SignUp}/> */}
      <Stack.Screen name='Dashboard2' component={TabsNavigation}/>
        </Stack.Navigator>
    )
  }
  
  const ProductsStack = ({navigation,route}) => {
    useEffect(()=>{
      if(tabHiddenRoutes.includes(getFocusedRouteNameFromRoute(route))){
        navigation.setOptions({tabBarStyle: {display: 'none'}});
       } else {
       navigation.setOptions({tabBarStyle: {display: 'flex'}});
      }
    },[navigation,route])
  
      return (
        <Stack.Navigator>
        <Stack.Screen name='Products3' component={Products} options={{headerShown:false}} />
        <Stack.Screen name='Categories' component={Categories2} />
        <Stack.Screen name='Brands' component={Brands} />
        <Stack.Screen name='Products2' component={Products2}  options={{title:'Products'}}/>
        <Stack.Screen name='Warehouses' component={Warehouses} />
    
        </Stack.Navigator>
      )
    }
    const MoreStack = ({navigation,route}) => {
      useEffect(()=>{
        if(tabHiddenRoutes.includes(getFocusedRouteNameFromRoute(route))){
          navigation.setOptions({tabBarStyle: {display: 'none'}});
         } else {
         navigation.setOptions({tabBarStyle: {display: 'flex'}});
        }
      },[navigation,route])
      return (
        <Stack.Navigator>
        <Stack.Screen name='More2' component={More} options={{headerShown:false}}/>
        <Stack.Screen name='AdminProfile' component={AdminProfile} />
        <Stack.Screen name='Products' component={Products} />
        <Stack.Screen name='Purchases' component={Purchases} />
        <Stack.Screen name='Sales' component={Sales} />
        <Stack.Screen name='Expenses' component={Expenses} />
        <Stack.Screen name='Accounting' component={Accounting} />
    
        </Stack.Navigator>
      )
    }
const TabsNavigation = () => {
  const navigation=useNavigation()
  
  return (
    <Tabs.Navigator screenOptions={{headerShown:'false',
    tabBarStyle:{backgroundColor:'white',minHeight:60,fontSize:16,paddingBottom:10
    },
    tabBarInactiveTintColor:'grey',
    tabBarActiveTintColor:"#38BDF8"}}>
    <Tabs.Screen name='Dashboard' component={Dashboard} options={
      {headerShown:false,
        tabBarIcon:({color,size})=>(
         <Icon name='home' color={color} size={30} />
          
        )
      }
    }/>
    <Tabs.Screen name='Products' component={ProductsStack} options={{
      headerShown:false,
        tabBarIcon:({color,size})=>(
         <Icon name='microsoft-xbox-controller-view' color={color} size={30} />
          
        )
      }
    }/>
    <Tabs.Screen name='POS' component={POS} options={{
      tabBarStyle:{display:'none'},
          headerLeft: () => (
            <TouchableOpacity onPress={() => {navigation.goBack()}}>
                <Ionicons name='arrow-back-outline' size={25} color={'black'} style={{marginLeft:10}}/>
              </TouchableOpacity>
              
            
          ),
        tabBarLabel: () => null,
        tabBarIcon:({color,size})=>{
          return(
            <View style={{
              top:Platform.OS=="ios" ? -10:-20,
              width:Platform.OS=="ios"?50:60,
              height:Platform.OS=="ios"?50:60,
              borderRadius:Platform.OS=="ios"?25:20,
              backgroundColor:"#38BDF8",
              alignItems:'center',
              justifyContent:'center',
              padding:5
              
            }}>
              <Icon name='point-of-sale' size={50} color={"white"}  />
            </View>
          )
        }
        
      }
    }/>
    <Tabs.Screen name='Reports' component={Reports} options={
      {
        tabBarIcon:({color,size})=>(
         <Icon name='chart-areaspline' color={color} size={30} />
          
        )
      }
    }/>
      <Tabs.Screen name='More' component={MoreStack} options={{
      headerShown:false,
        tabBarIcon:({color,size})=>(
         <Icon name='view-grid-plus' color={color} size={30} />
          
        )
      }
    }/>
  </Tabs.Navigator>
  )
}

  
  
  export {MainStack}

I also utilized the useEffect in ProductStack to get rid of the second warning

ERROR Warning: Cannot update a component (BottomTabNavigator)  
  while rendering a different component (ProductsStack).  
  To locate the bad setState() call inside ProductsStack,  
  follow the stack trace as described in https://reactjs.org/link/setstate- in-render
Sign up to request clarification or add additional context in comments.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question