Bottom Navigation is a navigation pattern where the section switching panel is located at the bottom of the screen. In Android it is implemented via BottomNavigationView (Material 3), in iOS — via UITabBarController or TabView in SwiftUI. Learn more about the Material Design specification in the Material Design 3 documentation.
Key Takeaways
Bottom Navigation is a navigation pattern where the main app sections are accessible via a panel at the bottom of the screen. This pattern has become a mobile design standard due to its one-handed usability. Unlike a side menu (Drawer), Bottom Navigation is always visible and does not require additional gestures to open.
Material Design 3 (2026) defines the Navigation Bar as a component with three states: default (icon + label), labeled (enlarged label, one active tab), and unlabeled (icons only). Google recommends Navigation Bar for apps with 3–5 equal sections. For 6+ sections — Navigation Drawer. In iOS SwiftUI, TabView automatically uses a bottom panel with system style.
A UX Movement study (2025) showed that Bottom Navigation improves task completion time by 27% compared to a side drawer, since the user sees all available sections without additional actions. Incorrect tap count decreases by 34% thanks to large touch targets (minimum 48x48 dp on Android, 44x44 pt on iOS).
BottomNavigationView in Android is a component from the Material 3 Library (com.google.android.material.navigation.NavigationBarView). It replaced the legacy BottomNavigationView from Material 2 and added support for Material You dynamic colors, animated active tab indicator, and built-in badges. The component is configured via XML menu and is fully compatible with Navigation Component.
// Activity with BottomNavigationView and NavHostFragment
class MainActivity : AppCompatActivity() {
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_main)
val navView = findViewById<NavigationBarView>(R.id.nav_view)
val navController = findNavController(R.id.nav_host_fragment)
// Automatic navigation synchronization
navView.setupWithNavController(navController)
// Badge setup
val badge = navView.getOrCreateBadge(R.id.navigation_messages)
badge.number = 8
badge.badgeGravity = BadgeDrawable.TOP_END
}
}
// XML menu for Bottom Navigation (res/menu/bottom_nav_menu.xml)
// <?xml version="1.0" encoding="utf-8"?>
// <menu xmlns:android="http://schemas.android.com/apk/res/android">
// <item android:id="@+id/navigation_home"
// android:icon="@drawable/ic_home"
// android:title="Home" />
// <item android:id="@+id/navigation_messages"
// android:icon="@drawable/ic_chat"
// android:title="Chats" />
// <item android:id="@+id/navigation_profile"
// android:icon="@drawable/ic_person"
// android:title="Profile" />
// </menu>Material 3 NavigationBarView supports three labelVisibilityMode modes: LABEL_VISIBILITY_AUTO (default — label is shown for the active tab), LABEL_VISIBILITY_LABELED (labels for all), LABEL_VISIBILITY_UNLABELED (icons only). The animated active tab indicator is configured via itemActiveIndicatorStyle with a custom ripple effect.
TabView is a built-in SwiftUI container for creating bottom navigation. Each tab is defined using the .tabItem modifier with an icon and text. TabView automatically creates a UITabBarController under the hood and supports all native panel features: badges, badge color, switching animation, and Dynamic Type adaptation.
import SwiftUI
struct ContentView: View {
var body: some View {
TabView {
HomeView()
.tabItem {
Label("Home", systemImage: "house.fill")
}
.badge(3)
SearchView()
.tabItem {
Label("Search", systemImage: "magnifyingglass")
}
NotificationsView()
.tabItem {
Label("Notifications", systemImage: "bell.fill")
}
.badge("12")
ProfileView()
.tabItem {
Label("Profile", systemImage: "person.circle.fill")
}
}
}
}TabView supports the .badge modifier (iOS 15+), which accepts Int (numeric badge) or String (text badge). Badge color can be changed via .badgeProminence(.increased) — makes the badge brighter. Tab switching animation is configured via .tabViewStyle(.automatic) or custom styles. For programmatic switching control, @State with selection is used.
Bottom Navigation is rarely used alone — each tab usually contains a stack navigator (NavigationView/NavigationStack in SwiftUI, NavHostFragment in Android). This combination gives the user both quick access to sections (Tab) and deep navigation within each section (Stack). This is the standard architecture for production apps.
struct AppTabView: View {
var body: some View {
TabView {
NavigationStack {
HomeView()
}
.tabItem {
Label("Home", systemImage: "house")
}
NavigationStack {
SearchView()
}
.tabItem {
Label("Search", systemImage: "magnifyingglass")
}
}
}
}
// Inside HomeView — stack navigation
struct HomeView: View {
var body: some View {
List(items) { item in
NavigationLink("\(item.title)", value: item)
}
.navigationDestination(for: Item.self) { item in
ItemDetailView(item: item)
}
}
}In Android, the same combination is implemented via NavHostFragment for each tab. Navigation Component automates back stack creation for each tab: when switching tabs, the stack state is preserved, and when returning — restored. This provides a seamless UX, like in Google system apps (Play Market, YouTube).
Material 3 (Material You) introduces a key change to Bottom Navigation — dynamic colors generated from the user's wallpaper. The system extracts dominant colors from the wallpaper and creates a palette of 5 key tones. NavigationBarView automatically applies these colors: the active tab receives the primary color, inactive tabs — onSurface variant.
The active tab indicator animation has become smooth: when switching, the indicator animates to the new tab with interpolation. The touch ripple effect uses the secondary color. Bottom Navigation in Material 3 also supports custom animations via itemActiveIndicatorStyle — the developer can set the shape (oval, rectangle), padding, and indicator color.
<!-- Active indicator style for NavigationBarView -->
<style name="Widget.MyApp.NavigationBarView.ActiveIndicator"
parent="Widget.Material3.NavigationBarView.ActiveIndicator">
<item name="android:height">32dp</item>
<item name="android:width">64dp</item>
<item name="android:marginHorizontal">8dp</item>
<item name="shapeAppearance">
@style/ShapeAppearance.Material3.Corner.Full
</item>
<item name="color">@color/primary_container</item>
</style>When designing Bottom Navigation, usability research should be considered. NN Group (2026): the bottom panel should be at least 56 dp high, touch targets — at least 48 dp. Label text — maximum 12 characters (Latin) or 8 characters (Cyrillic). The active tab should differ not only in color but also in icon state (filled vs outlined).
Material Design 3 recommends the following patterns: 4 tabs — optimal for easy scanning; a "+" icon in the center (FloatingActionButton) — for the primary action; badges — only for user action counters. Avoid: using Bottom Navigation with 2 tabs (use Tab Layout instead), dynamically changing tab order, hiding the panel on nested screens.
Frequently Asked Questions
Bottom Navigation — a panel at the bottom of the screen, always visible, for 3–5 equal sections. Navigation Drawer — a side menu invoked by gesture or button, for 6+ sections, settings, and secondary pages. Drawer hides content, Bottom Navigation does not.
4 tabs — optimal according to NN Group data. 3 — minimum to justify a bottom panel. 5 — maximum where all tabs remain distinguishable. 6+ requires switching to Navigation Drawer or a "More" item on iOS.
In Android Material 3, use getOrCreateBadge(itemId) on NavigationBarView. Configure the number via badge.number and position via badgeGravity (TOP_END, TOP_START). In iOS SwiftUI — the .badge(Int) modifier on .tabItem. In UIKit — tabBarItem.badgeValue = "N".
Yes. Material 3 NavigationBarView animates the active tab indicator movement. SwiftUI TabView uses the system iOS animation. For custom content animations, use matchedGeometryEffect (SwiftUI) or Transition (Jetpack Compose). The panel switching animation itself is system-based.
Yes, for mobile-first and PWA. Material Design 3 has a web Navigation Bar component. However, on desktop, it is better to use a side panel (Side Navigation) — horizontal space allows showing more items. Bottom Navigation on desktop is an anti-pattern.
Summary
We will develop a mobile application turnkey
IT Sectr creates iOS and Android applications for startups and businesses since 2017. We will advise you and propose the best solution.
Read also