Open In App

Customizing Material Navigation Rail in Android

Last Updated : 08 Oct, 2021
Improve
Improve
Like Article
Like
Save
Share
Report

In the article, Material Design Component Navigation Rail in Android, it’s been discussed how to implement one of the navigation components that is Navigation Rail especially for the larger screens like desktops or tablets. So in this article, it’s been continued with the customization of the Navigation Rail in android. Have a look at the following image to get an overview of the entire discussion.

Customizing Material Navigation Rail in Android

Create an empty activity project

To create a new project in Android Studio please refer to How to Create/Start a New Project in Android Studio.

Add Required Dependency

Include google material design components dependency in the build.gradle file. After adding the dependencies don’t forget to click on the “Sync Now” button present at the top right corner. Note that the Navigation Rail is introduced in the latest release of the material design components version that is 1.4.0 and above.

implementation ‘com.google.android.material:material:1.4.0’

Note that while syncing your project you need to be connected to the network and make sure that you are adding the dependency to the app-level Gradle file as shown below. Note that, the layout is going to remain the same as in the previous article.

Essential Customizations are now discussed one by one

The labels for the icons are optional

There are four modes for labels for each of the icons. Those are:

selected -> The labels are shown only to the selected items on the navigation rail.

labeled -> The labels are shown for all the items.

unlabeled -> All the labels are hidden, even though the item is selected.

auto -> The labels behave as “labelled” when there 3 or less than 3 items and “selected” when there are 4 items or more.

To include these values in XML there is an attribute for the navigation rail that is:

app:labelVisibilityMode=”value”

Have a look at the following example and output:

XML




<?xml version="1.0" encoding="utf-8"?>
<androidx.constraintlayout.widget.ConstraintLayout 
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:clipToPadding="false"
    tools:context=".MainActivity">
  
    <com.google.android.material.navigationrail.NavigationRailView
        android:id="@+id/navigationRail"
        android:layout_width="wrap_content"
        android:layout_height="match_parent"
        android:clipToPadding="false"
        app:headerLayout="@layout/navigation_rail_fab"
        app:labelVisibilityMode="unlabeled"
        app:layout_constraintBottom_toBottomOf="parent"
        app:layout_constraintStart_toStartOf="parent"
        app:layout_constraintTop_toTopOf="parent"
        app:menu="@menu/navigation_rail_menu" />
  
</androidx.constraintlayout.widget.ConstraintLayout>


Output UI:

Adding labels for icons

There is also a badge for items in the Navigation Rail. For example, whenever the new notification or count of the content inside the particular fragment increases, then it can only be informed to the user by increasing the count of the badge or simply a dot badge. Have a look at the following example to get an idea. Navigate to the app > res > layout > activity_main.xml and add the below code to that file. Below is the code for the activity_main.xml file. 

XML




<?xml version="1.0" encoding="utf-8"?>
<androidx.constraintlayout.widget.ConstraintLayout 
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:clipToPadding="false"
    tools:context=".MainActivity">
  
    <com.google.android.material.navigationrail.NavigationRailView
        android:id="@+id/navigationRail"
        android:layout_width="wrap_content"
        android:layout_height="match_parent"
        android:clipToPadding="false"
        app:headerLayout="@layout/navigation_rail_fab"
        app:labelVisibilityMode="labeled"
        app:layout_constraintBottom_toBottomOf="parent"
        app:layout_constraintStart_toStartOf="parent"
        app:layout_constraintTop_toTopOf="parent"
        app:menu="@menu/navigation_rail_menu" />
  
</androidx.constraintlayout.widget.ConstraintLayout>


Below is the code for the MainActivity.kt file. Comments are added inside the code to understand the code in more detail.

Kotlin




import android.os.Bundle
import androidx.appcompat.app.AppCompatActivity
import com.google.android.material.navigationrail.NavigationRailView
  
class MainActivity : AppCompatActivity() {
    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContentView(R.layout.activity_main)
  
        // instance of navigation rail
        val navigationRail: NavigationRailView = findViewById(R.id.navigationRail)
  
        // instance of navigation rail badge
        val badge = navigationRail.getOrCreateBadge(R.id.images)
        badge.isVisible = true
        badge.number = 99
    }
}


Output UI:

The best practice for adding any badges for the icons is, if there is a need of temporary hiding the badge until the next notification is received, then, in this case, changing the visibility of BadgeDrawable like the following:

Kotlin




val badgeDrawable = navigationRail.getBadge(R.id.images)
if (badgeDrawable != null) {
    badgeDrawable.isVisible = false
    badgeDrawable.clearNumber()
}


Changing the Elevation of the Navigation Rail container

There is attribute elevation. This attribute only affects the Navigation Rail container. The attribute is:

app:elevation=”value_in_dp”

Have a look at the following example and its output:

XML




<?xml version="1.0" encoding="utf-8"?>
<androidx.constraintlayout.widget.ConstraintLayout
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:clipToPadding="false"
    tools:context=".MainActivity">
  
    <com.google.android.material.navigationrail.NavigationRailView
        android:id="@+id/navigationRail"
        android:layout_width="wrap_content"
        android:layout_height="match_parent"
        android:clipToPadding="false"
        app:elevation="18dp"
        app:headerLayout="@layout/navigation_rail_fab"
        app:labelVisibilityMode="labeled"
        app:layout_constraintBottom_toBottomOf="parent"
        app:layout_constraintStart_toStartOf="parent"
        app:layout_constraintTop_toTopOf="parent"
        app:menu="@menu/navigation_rail_menu" />
  
</androidx.constraintlayout.widget.ConstraintLayout>


Output UI:

Changing the color of the Navigation Rail container

There is XML attribute for Navigation Rail to change the style or the color of the Navigation Rail that is:

style=”@style/Widget.MaterialComponents.NavigationRailView.Colored.Compact”

Note that, by including this the size of the Navigation Rail becomes compact and it is advised to remove the Floating Action Button removing the header layout attribute in the Navigation Rail. Have a look at the following example to get an idea.

Changing the TextAppearance of the labels

The default text appearance of the labels is Caption in the Material Design Type system so that needs to be overridden with the custom font. So in the themes.xml file invoke the custom style for the Caption type system.

XML




<style name="TextAppearance.MdcTypographyStyles.Caption" parent="TextAppearance.MaterialComponents.Caption">
    <item name="fontFamily">@font/poppins_regular</item>
    <item name="android:fontFamily">@font/poppins_regular</item>
    <item name="android:textSize">12sp</item>
</style>


Now include the TextAppearance.MdcTypographyStyles.Caption in the attributes under the Navigation Rail:

app:itemTextAppearanceActive=”@style/TextAppearance.MdcTypographyStyles.Caption”

app:itemTextAppearanceInactive=”@style/TextAppearance.MdcTypographyStyles.Caption”

Output UI:

Some other Attributes of Navigation Rail Container are:

Element

Attribute

Related Method

Color app:backgroundTint N/A
Elevation app:elevation setElevation

Some other Attributes of Navigation Rail Items are:

Element

Attribute

Related Method

Menu resource app:menu

inflateMenu

getMenu

Ripple (inactive) app:itemRippleColor

setItemRippleColor

getItemRippleColor

Ripple (active) app:itemRippleColor

setItemRippleColor

getItemRippleColor

Label visibility mode app:labelVisibilityMode

setLabelVisibilityMode

getLabelVisibilityMode

Some other Attributes of Navigation Rail Items Icon are:

Element

Attribute

Related Method

Icon android:icon N/A
Size app:itemIconSize

setItemIconSize

setItemIconSizeRes

getItemIconSize

Color (inactive) app:itemIconTint

setItemIconTintList

getItemIconTintList

Color (active) app:itemIconTint

setItemIconTintList

getItemIconTintList

Some other Attributes of Navigation Rail Items Text Labels are:

Element

Attribute

Related Method

Text label android:title N/A
Color (inactive) app:itemTextColor

setItemTextColor

getItemTextColor

Color (active) app:itemTextColor

setItemTextColor

getItemTextColor

Typography (inactive) app:itemTextAppearanceInactive

setItemTextAppearanceInactive

getItemTextAppearanceInactive

Typography (active) app:itemTextAppearanceActive

setItemTextAppearanceActive

getItemTextAppearanceActive



Like Article
Suggest improvement
Previous
Next
Share your thoughts in the comments

Similar Reads