Milan Nesovic
Milan Nesovic

Reputation: 33

React Native Bottom tab bar jump on every load

i have the exact same problem like on issue:

React Native header / bottom tabbar jumping on first app load

On every load the bottom bar jumps up and down for unknown reason. I wrapped the root app in SafeAreaProvider, i wrapped my screens in SafeAreaView and still the same thing happens.

Here is my code:

Root App:

const App = () => {
  return (
    <SafeAreaProvider>
      <StatusBar backgroundColor="#01497C" />
      <NavigationContainer>
        <Stack.Navigator
          initialRouteName="AuthLoadingScreen"
          screenOptions={{headerShown: false}}>
          <Stack.Screen
            name="AuthLoadingScreen"
            component={AuthLoadingScreen}
          />
          <Stack.Screen name="Home" component={Tabs} />
          <Stack.Screen name="QuizScreen" component={QuizScreen} />
          <Stack.Screen name="QuizReviewScreen" component={QuizReviewScreen} />
          <Stack.Screen name="QuizEndScreen" component={QuizEndScreen} />
        </Stack.Navigator>
      </NavigationContainer>
    </SafeAreaProvider>
  );
};

Tabs:

const Tabs = () => {
  const TabBarCustom = ({children, onPress}) => {
    return (
      <TouchableOpacity
        style={{top: -10, justifyContent: 'center', alignItems: 'center'}}
        onPress={onPress}
        activeOpacity={1}>
        <LinearGradient
          style={{
            width: 70,
            height: 70,
            borderRadius: 35,
            shadowColor: '#000',
            shadowOffset: {
              width: 0,
              height: 4,
            },
            shadowOpacity: 0.3,
            shadowRadius: 4.65,

            elevation: 8,
          }}
          colors={['#01497C', '#89C2D9']}>
          {children}
        </LinearGradient>
      </TouchableOpacity>
    );
  };

  return (
    <Tab.Navigator
      tabBarOptions={{
        showLabel: false,
        style: {
          height: 60,
        },
      }}>
      <Tab.Screen
        name="Quizzes"
        component={QuizzesScreen}
        options={{
          tabBarIcon: ({focused}) => (
            <View style={{alignItems: 'center', justifyContent: 'center'}}>
              <Ionicon
                name="apps-outline"
                color={focused ? '#89C2D9' : '#2A6F97'}
                size={30}
              />
              <Text
                style={{color: focused ? '#89C2D9' : '#2A6F97', fontSize: 13}}>
                Quizzes
              </Text>
            </View>
          ),
        }}
      />
      <Tab.Screen
        name="Flashcards"
        component={FlashCardsScreen}
        options={{
          tabBarIcon: ({focused}) => (
            <View style={{alignItems: 'center', justifyContent: 'center'}}>
              <Ionicon
                name="copy-outline"
                color={focused ? '#89C2D9' : '#2A6F97'}
                size={30}
              />
              <Text
                style={{color: focused ? '#89C2D9' : '#2A6F97', fontSize: 13}}>
                Flashcards
              </Text>
            </View>
          ),
        }}
      />
      <Tab.Screen
        name="Import"
        component={QuizzesScreen}
        options={{
          tabBarIcon: ({focused}) => (
            <View style={{alignItems: 'center', justifyContent: 'center'}}>
              <Icon
                name="plus"
                color={focused ? '#A9D6E5' : 'white'}
                size={42}
              />
            </View>
          ),
          tabBarButton: props => <TabBarCustom {...props} />,
        }}
      />
      <Tab.Screen
        name="Account"
        component={QuizzesScreen}
        options={{
          tabBarIcon: ({focused}) => (
            <View style={{alignItems: 'center', justifyContent: 'center'}}>
              <Ionicon
                name="person-outline"
                color={focused ? '#89C2D9' : '#2A6F97'}
                size={30}
              />
              <Text
                style={{color: focused ? '#89C2D9' : '#2A6F97', fontSize: 13}}>
                Account
              </Text>
            </View>
          ),
        }}
      />
      <Tab.Screen
        name="About"
        component={QuizzesScreen}
        options={{
          tabBarIcon: ({focused}) => (
            <View style={{alignItems: 'center', justifyContent: 'center'}}>
              <Ionicon
                name="search"
                color={focused ? '#89C2D9' : '#2A6F97'}
                size={30}
              />
              <Text
                style={{color: focused ? '#89C2D9' : '#2A6F97', fontSize: 13}}>
                Search
              </Text>
            </View>
          ),
        }}
      />
    </Tab.Navigator>
  );
};

The issue happens every time tabs get loaded.

Upvotes: 3

Views: 2181

Answers (2)

matheus miranda
matheus miranda

Reputation: 1

I use MaterialCommunityIcons for tab icons so, I sove this issue with

useLayoutEffect(() => {
  async function loadIcons() {
    setIsLoading(true);
    await MaterialCommunityIcons.loadFont();
    setIsLoading(false);
  }
  loadIcons();
}, []);

if (isLoading) {
  return <></>;
}

Why useLayouEffect? The signature is identical to useEffect, but it fires synchronously after all DOM mutations. Use this to read layout from the DOM and synchronously re-render. Updates scheduled inside useLayoutEffect will be flushed synchronously, before the browser has a chance to paint. read more

Upvotes: 0

Dildar Khan
Dildar Khan

Reputation: 121

I had the same issue, in my case I was using Custom StatusBar in different screens with different props. The issue was I wasn't using translucent prop in all screen StatusBar. Using translucent in all screen StatusBar fixed the problem. Give me a thumbs up if it solve your problem.

Upvotes: 3

Related Questions