0

How to remove the bottom and top navigation on scrolling? Many apps like youtube hide their bottom and top navigation when a user is scrolling it can post feeds etc How can I do this with my code? for example, if a user is scrolling it hides the bottom and top navigation with smooth animation, and then posts cover the screen and when I stop it comes back bottom and top navigation can anyone help me to do that?

I created a small app on Expo Snack if you want to consider helping me feel free to check that out link https://snack.expo.dev/@syblus/stackoverflowquastion the web version if not good but the expo go version is good

Alan
  • 63
  • 5

2 Answers2

0

You could try use something like this and use headerIsShown state to apply a class that animates it in/out with transform: [{ translateY: headerIsShown ? 0 : - 60 }], If you want to animate it, you could use react native interpolation https://reactnative.dev/docs/animations#interpolation

<ScrollView
  onScroll={(event) => {
    const scrolling = event.nativeEvent.contentOffset.y;
    
    if (scrolling > 100) {
      setHeaderShown(true);
    } else {
      setHeaderShown(false);
    }
  }}
  style={{ flex: 1 }}
>
  {images.map(( { uri } ) => (
    <Image source={{ uri: item.download_url }} style={styles.image} />
  ))}
</ScrollView>
Malte Schulze-Boeing
  • 1,055
  • 10
  • 14
0

The top answer to this question: how to Show or hide Navbar when scroll use react.js? is a nice example of how this can be done. The below is a modified version of this where the scroll logic is placed into a custom hook. You then need to set the positioning of your top and bottom navs as position: fixed and change the location of them (top/bottom) depending on the show state.

// useShowHideElement.js
import { useEffect, useState } from 'react';

const useShowHideElement = () => {
  const [showElement, setShowElement] = useState(true);
  const [prevScrollPos, setPrevScrollPos] = useState(0);

  const controlElement = () => {
    if (typeof window !== 'undefined') {
      if (window.scrollY > prevScrollPos) {
        setShowElement(false);
      } else {
        setShowElement(true);
      }

      setPrevScrollPos(window.scrollY);
    }
  };

  useEffect(() => {
    if (typeof window !== 'undefined') {
      window.addEventListener('scroll', controlElement);

      return () => {
        window.removeEventListener('scroll', controlElement);
      };
    }
  }, [prevScrollPos]);

  return {
    show: showElement,
  };
};

export default useShowHideElement;

// bottomNav.js
import React from 'react';
import { StyleSheet, View } from 'react-native';
import FontAwesome from 'react-native-vector-icons/FontAwesome';
import Ionicons from 'react-native-vector-icons/Ionicons';
import useShowHideElement from './useShowHideElement';

const BottomNav = () => {
  const { show } = useShowHideElement();
  let page = 'home';

  return (
    <View style={{ ...styles.container, bottom: show ? 0 : '-100px' }}>
      {page === 'home' ? (
        <FontAwesome name='home' size={24} color='black' style={styles.activeIcon} />
      ) : (
        <FontAwesome name='home' size={24} color='black' style={styles.icons1} />
      )}
      {page === 'profile' ? (
        <FontAwesome name='user-circle' size={24} color='black' style={styles.activeIcon} />
      ) : (
        <FontAwesome name='user-circle' size={24} color='black' style={styles.icons1} />
      )}
    </View>
  );
};

export default BottomNav;

const styles = StyleSheet.create({
  container: {
    display: 'flex',
    flexDirection: 'row',
    justifyContent: 'space-evenly',
    backgroundColor: 'gray',
    borderTopLeftRadius: 20,
    borderTopRightRadius: 20,
    position: 'fixed',
    transition: '225ms',
    width: '100%',
    zIndex: 100,
    paddingVertical: 10,
    alignItems: 'center',
  },
  activeIcon: {
    backgroundColor: 'white',
    borderRadius: 50,
    fontSize: 30,
    padding: 10,
  },
  icons1: {
    color: 'white',
    fontSize: 30,
    marginRight: 20,
    marginLeft: 20,
  },
});
//topNav.js
import React, { useEffect, useState } from 'react';
import { StyleSheet, View, StatusBar, FlatList, Image } from 'react-native';
import Ionicons from 'react-native-vector-icons/Ionicons';
import Entypo from 'react-native-vector-icons/Entypo';
import useShowHideElement from './useShowHideElement';

const TopNav = () => {
  const { show } = useShowHideElement();
  let page = 'home';

  return (
    <View
      style={{
        flexDirection: 'row',
        alignItems: 'center',
        justifyContent: 'space-between',
        width: '100%',
        paddingVertical: 12,
        position: 'fixed',
        top: show ? 0 : '-100px',
        zIndex: 100,
        backgroundColor: 'gray',
        transition: '225ms',
      }}
    >
      <Entypo name='app-store' size={24} color='white' style={styles.icons1} />
      {page === 'home' && <Ionicons name='trophy' size={24} color='white' style={styles.icons11} />}
      {page === 'profile' && <Ionicons name='settings-sharp' size={24} color='black' style={styles.icons11} />}
    </View>
  );
};

export default TopNav;

const styles = StyleSheet.create({
  icons11: {
    color: 'white',
    fontSize: 30,
    marginRight: '3%',
  },
  icons1: {
    color: 'white',
    fontSize: 30,
    marginRight: 20,
    marginLeft: 20,
  },
});

Tomr93
  • 36
  • 3