HomeGuidesReferenceLearn
ArchiveExpo SnackDiscord and ForumsNewsletter

Drawer

Learn how to use the Drawer layout in Expo Router.


To use drawer navigator you'll need to install some extra dependencies.

Installation

Terminal
npx expo install @react-navigation/drawer react-native-gesture-handler react-native-reanimated

No additional configuration is required for SDK 50 and above. Reanimated Babel plugin is automatically configured in babel-expo-preset when you install the library.

Update your babel.config.js to include the Reanimated babel plugin:

babel.config.js
module.exports = {
  presets: [
      %%placeholder-start%%... %%placeholder-end%%
    ],
    plugins: [
      %%placeholder-start%%... %%placeholder-end%%
      'react-native-reanimated/plugin',
    ],
};

After you add the Babel plugin, restart your development server and clear the bundler cache using the command:

Terminal
npx expo start --clear

If you load other Babel plugins, the Reanimated plugin has to be the last item in the plugins array.

Usage

Now you can use the Drawer layout to create a drawer navigator. You'll need to wrap the <Drawer /> in a <GestureHandlerRootView> to enable gestures. It is required as of Expo Router v3 and greater. You only need one <GestureHandlerRootView> in your component tree. Any nested routes are not required to be wrapped individually.

app/_layout.js
import { GestureHandlerRootView } from 'react-native-gesture-handler';
import { Drawer } from 'expo-router/drawer';

export default function Layout() {
  return (
    <GestureHandlerRootView style={{ flex: 1 }}>
      <Drawer />
    </GestureHandlerRootView>
  );
}

To edit the drawer navigation menu labels, titles and screen options specific screens are required as follows:

app/_layout.js
import { GestureHandlerRootView } from 'react-native-gesture-handler';
import { Drawer } from 'expo-router/drawer';

export default function Layout() {
  return (
    <GestureHandlerRootView style={{ flex: 1 }}>
      <Drawer>
        <Drawer.Screen
          name="index" // This is the name of the page and must match the url from root
          options={{
            drawerLabel: 'Home',
            title: 'overview',
          }}
        />
        <Drawer.Screen
          name="user/[id]" // This is the name of the page and must match the url from root
          options={{
            drawerLabel: 'User',
            title: 'overview',
          }}
        />
      </Drawer>
    </GestureHandlerRootView>
  );
}

Note: Be careful when using react-native-gesture-handler on the web. It can increase the JavaScript bundle size significantly. Learn more about using platform-specific modules.

Now you can use the Drawer layout to create a drawer navigator.

app/_layout.js
import { Drawer } from 'expo-router/drawer';

export default function Layout() {
  return <Drawer />;
}

To edit the drawer navigation menu labels, titles and screen options specific screens are required as follows:

app/_layout.js
import { Drawer } from 'expo-router/drawer';

export default function Layout() {
  return (
    <Drawer>
      <Drawer.Screen
        name="index" // This is the name of the page and must match the url from root
        options={{
          drawerLabel: 'Home',
          title: 'overview',
        }}
      />
      <Drawer.Screen
        name="user/[id]" // This is the name of the page and must match the url from root
        options={{
          drawerLabel: 'User',
          title: 'overview',
        }}
      />
    </Drawer>
  );
}