{"id":122,"date":"2025-09-26T14:49:53","date_gmt":"2025-09-26T14:49:53","guid":{"rendered":"https:\/\/blog.vyomscode.com\/?p=122"},"modified":"2025-09-26T15:01:25","modified_gmt":"2025-09-26T15:01:25","slug":"creating-top-navigation-tabs-in-expo-router-with-react-navigation","status":"publish","type":"post","link":"https:\/\/blog.vyomscode.com\/index.php\/2025\/09\/26\/creating-top-navigation-tabs-in-expo-router-with-react-navigation\/","title":{"rendered":"Creating Top Navigation Tabs in Expo Router with React Navigation"},"content":{"rendered":"\n<p>When building apps, navigation plays a huge role in the overall user experience. If your app involves bookings, tasks, or other segmented data, <strong>top navigation tabs<\/strong> (sliders) can help users switch between views effortlessly.<\/p>\n\n\n\n<p>In this blog, we\u2019ll walk through how to implement top navigation tabs in an Expo Router project using <strong>React Navigation\u2019s Material Top Tabs<\/strong>. By the end, you\u2019ll have a working setup where users can toggle between <strong>Active<\/strong> and <strong>History<\/strong> bookings.<\/p>\n\n\n\n<hr class=\"wp-block-separator has-alpha-channel-opacity is-style-wide\"\/>\n\n\n\n<h4 class=\"wp-block-heading\">Step 1 \u2013 Install the Required Package<\/h4>\n\n\n\n<p>First, install the <code>@react-navigation\/material-top-tabs<\/code> package:<\/p>\n\n\n\n<p><strong><em>npm i @react-navigation\/material-top-tabs<\/em><\/strong><\/p>\n\n\n\n<h4 class=\"wp-block-heading\">Step 2 \u2013 Set Up the Folder Structure<\/h4>\n\n\n\n<p>Assume your project is structured like this:<\/p>\n\n\n\n<p><strong>src\/app\/(user)\/<br>\u251c\u2500\u2500 _layout.tsx<br>\u251c\u2500\u2500 index.tsx<br>\u2514\u2500\u2500 bookings.tsx<\/strong><\/p>\n\n\n\n<p>We want to create top tabs inside <code>bookings.tsx<\/code>. For that, let\u2019s make a new folder <code>book<\/code> inside <code>(user)<\/code> and create the following files:<\/p>\n\n\n\n<p><strong>src\/app\/(user)\/book\/_layout.tsx<br>src\/app\/(user)\/book\/index.tsx<br>src\/app\/(user)\/book\/history.tsx<\/strong><\/p>\n\n\n\n<h4 class=\"wp-block-heading\">Step 3 \u2013 Redirect the Old Bookings Page<\/h4>\n\n\n\n<p>Since we moved bookings into the <code>book<\/code> folder, we\u2019ll redirect the old <code>bookings.tsx<\/code> to point to the new setup.<\/p>\n\n\n\n<p>Update <strong><code>src\/app\/(user)\/bookings.tsx<\/code><\/strong>:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code><strong><em>import { Redirect } from 'expo-router'; \n\nexport default function BtwoBIndex() {\n  return &lt;Redirect href={'home'} \/>;\n}\n<\/em><\/strong><\/code><\/pre>\n\n\n\n<h4 class=\"wp-block-heading\">Step 4 \u2013 Add the Top Tabs Layout<\/h4>\n\n\n\n<p>Now, let\u2019s configure the top tabs inside <code>src\/app\/(user)\/book\/_layout.tsx<\/code>.<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code><strong><em>import { createMaterialTopTabNavigator } from '@react-navigation\/material-top-tabs';\nimport React from 'react'; \nimport { StyleSheet } from 'react-native';  \nimport NewBooking from '.\/index';\nimport CabDuty from '.\/cabDuty'; \nimport HotelDuty from '.\/hotelDuty'; \n\nconst Tab = createMaterialTopTabNavigator(); \n\nexport default function Specialroute() {\n  return ( \n    &lt;Tab.Navigator\n      screenOptions={{\n        tabBarScrollEnabled: true,\n        tabBarItemStyle: { width: 'auto' },\n        tabBarLabelStyle: { \n          textTransform: 'none',\n          flexShrink: 1 \n        }\n      }}\n      style={styles.tabContainer}\n    > \n      &lt;Tab.Screen name=\"index\" component={NewBooking} options={{ tabBarLabel: 'New Booking' }} \/>  \n      &lt;Tab.Screen name=\"cabDuty\" component={CabDuty} options={{ tabBarLabel: \"Cab Duty\" }} \/>   \n      &lt;Tab.Screen name=\"hotelDuty\" component={HotelDuty} options={{ tabBarLabel: \"Hotel Duty\" }} \/>   \n    &lt;\/Tab.Navigator> \n  );\n}\n\nconst styles = StyleSheet.create({\n  tabContainer: { \n    flex: 1, \n  },  \n});<\/em><\/strong><\/code><\/pre>\n\n\n\n<p>\ud83d\udc49 With this structure, you can add as many pages as you want to the top tabs. If they overflow, they\u2019ll automatically become <strong>scrollable horizontally<\/strong>.<\/p>\n\n\n\n<h4 class=\"wp-block-heading\">Step 5 \u2013 Build the Active &amp; History Screens<\/h4>\n\n\n\n<p>Inside the <code>book<\/code> folder, add content for the two tabs:<\/p>\n\n\n\n<p><strong><code>src\/app\/(user)\/book\/index.tsx<\/code> (Active Bookings):<\/strong><\/p>\n\n\n\n<pre class=\"wp-block-code\"><code><strong><em>import { StyleSheet } from 'react-native'; \nimport { Text, View } from '@\/src\/components\/Themed';\n\nexport default function ActiveBooking() {\n  return (\n    &lt;View style={styles.container}>\n      &lt;Text style={styles.title}>Active&lt;\/Text> \n    &lt;\/View>\n  );\n}\n\nconst styles = StyleSheet.create({\n  container: {\n    flex: 1,\n    alignItems: 'center',\n    justifyContent: 'center',\n  },\n  title: {\n    fontSize: 20,\n    fontWeight: 'bold',\n  }, \n});<\/em><\/strong><\/code><\/pre>\n\n\n\n<p><code>src\/app\/(user)\/book\/history.tsx<\/code> (History Bookings):<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code><strong><em>import { StyleSheet } from 'react-native'; \r\nimport { Text, View } from '@\/src\/components\/Themed';\r\n\r\nexport default function HistoryBooking() {\r\n  return (\r\n    &lt;View style={styles.container}>\r\n      &lt;Text style={styles.title}>History&lt;\/Text> \r\n    &lt;\/View>\r\n  );\r\n}\r\n\r\nconst styles = StyleSheet.create({\r\n  container: {\r\n    flex: 1,\r\n    alignItems: 'center',\r\n    justifyContent: 'center',\r\n  },\r\n  title: {\r\n    fontSize: 20,\r\n    fontWeight: 'bold',\r\n  }, \r\n});\r\n<\/em><\/strong><\/code><\/pre>\n\n\n\n<h4 class=\"wp-block-heading\">Step 6 \u2013 Improve the Bottom Tabs<\/h4>\n\n\n\n<p>Finally, let\u2019s update the main <strong><code>src\/app\/(user)\/_layout.tsx<\/code><\/strong> to add a clean bottom tab navigation experience.<\/p>\n\n\n\n<p>Inside the <code>TabLayout()<\/code> return, modify like this:<\/p>\n\n\n\n<p><strong><em>return (<br>&lt;Tabs&gt;<br>   {\/* Hide old Bookings tab *\/}<br>   {\/* New Bookings tab *\/}<br>   &lt;Tabs.Screen<br>      name=&#8221;book&#8221;<br>      options={{<br>         title: &#8216;Bookings&#8217;,<br>         tabBarIcon: ({ color }) =&gt; &lt;TabBarIcon name=&#8221;book&#8221; color={color} \/&gt;, <br>       }}<br>    \/&gt;<br>&lt;\/Tabs&gt;<br>);<\/em><\/strong><\/p>\n\n\n\n<h4 class=\"wp-block-heading\">Final Thoughts<\/h4>\n\n\n\n<p>With this setup:<\/p>\n\n\n\n<ul>\n<li>Users can switch between <strong>Active<\/strong> and <strong>History<\/strong> bookings via <strong>top tabs<\/strong>.<\/li>\n\n\n\n<li>You can easily add more tabs (Cab Duty, Hotel Duty, etc.) without changing much code.<\/li>\n\n\n\n<li>The bottom navigation stays clean, redirecting seamlessly to the new top tab system.<\/li>\n<\/ul>\n\n\n\n<p>This modular approach keeps your codebase organized while offering users an intuitive navigation experience.<\/p>\n\n\n\n<p><a href=\"https:\/\/tripti.vyomscode.com\/\" data-type=\"link\" data-id=\"https:\/\/tripti.vyomscode.com\/\">Tripti<\/a><\/p>\n","protected":false},"excerpt":{"rendered":"<p>When building apps, navigation plays a huge role in the overall user experience. If your app involves bookings, tasks, or other segmented data, top navigation tabs (sliders) can [&hellip;]<\/p>\n","protected":false},"author":1,"featured_media":0,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"footnotes":""},"categories":[1],"tags":[],"_links":{"self":[{"href":"https:\/\/blog.vyomscode.com\/index.php\/wp-json\/wp\/v2\/posts\/122"}],"collection":[{"href":"https:\/\/blog.vyomscode.com\/index.php\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/blog.vyomscode.com\/index.php\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/blog.vyomscode.com\/index.php\/wp-json\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/blog.vyomscode.com\/index.php\/wp-json\/wp\/v2\/comments?post=122"}],"version-history":[{"count":4,"href":"https:\/\/blog.vyomscode.com\/index.php\/wp-json\/wp\/v2\/posts\/122\/revisions"}],"predecessor-version":[{"id":128,"href":"https:\/\/blog.vyomscode.com\/index.php\/wp-json\/wp\/v2\/posts\/122\/revisions\/128"}],"wp:attachment":[{"href":"https:\/\/blog.vyomscode.com\/index.php\/wp-json\/wp\/v2\/media?parent=122"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/blog.vyomscode.com\/index.php\/wp-json\/wp\/v2\/categories?post=122"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/blog.vyomscode.com\/index.php\/wp-json\/wp\/v2\/tags?post=122"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}