Search code examples
androidandroid-architecture-navigation

Navigation Component when using Menu Buttons


I'm following this tutorial for learning Navigation Components. My basic set up to test Navigation UI of menu buttons of Toolbar is as

<?xml version="1.0" encoding="utf-8"?>
<menu xmlns:android="http://schemas.android.com/apk/res/android" xmlns:app="http://schemas.android.com/apk/res-auto">
    <item
            android:id="@+id/detail_dest"
            android:icon="@drawable/ic_details"
            android:title="@string/details"
            app:showAsAction="ifRoom"/>

    <item
            android:id="@+id/settings_dest"
            android:icon="@drawable/ic_settings"
            android:title="@string/settings"
            app:showAsAction="ifRoom"/>


    <item
            android:id="@+id/camera_dest"
            android:icon="@drawable/ic_camera"
            android:title="@string/camera"
            app:showAsAction="ifRoom"/>
</menu>

Navigation graph is

<?xml version="1.0" encoding="utf-8"?>
<navigation xmlns:android="http://schemas.android.com/apk/res/android"
            xmlns:app="http://schemas.android.com/apk/res-auto"
            xmlns:tools="http://schemas.android.com/tools" android:id="@+id/nav_graph"
            app:startDestination="@id/mainFragment">

    <fragment android:id="@+id/mainFragment"
              android:name="com.example.navmenu.MainFragment"
              android:label="fragment_main" tools:layout="@layout/fragment_main">

        <action android:id="@+id/action_mainFragment_to_detail_dest"
                app:destination="@id/detail_dest"
                app:enterAnim="@anim/slide_in_right"
                app:exitAnim="@anim/slide_out_left"
                app:popEnterAnim="@anim/slide_in_left"
                app:popExitAnim="@anim/slide_out_right"/>
    </fragment>

    <!-- Detail Fragment -->
    <fragment android:id="@+id/detail_dest"
              android:name="com.example.blankfragments.DetailFragment"
              android:label="fragment_detail" tools:layout="@layout/fragment_detail"/>

    <!-- Settings Fragment -->
    <fragment android:id="@+id/settings_dest"
              android:name="com.example.blankfragments.SettingsFragment"
              android:label="fragment_settings" tools:layout="@layout/fragment_settings"/>

    <fragment android:id="@+id/camera_dest"
              android:name="com.example.blankfragments.CameraFragment"
              android:label="fragment_camera" tools:layout="@layout/fragment_camera"/>
</navigation>

My first question is when i touch a fragment on screen, for instance SettingsFragment when it's already on screen it's re-created, can this be prevented, if so, is it possible only by modifying xml?

Second question is tutorial says that ids of items in menu.xml should be same with fragment ids. detail_dest in menu should be detail_dest in nav_graph either. However i want the transition to be done with Animation as it happens when you use actions. When i change use menu item with id it only goes once to Detail Fragment and without animation, how can i fix this?


Solution

  • My first question is when i touch a fragment on screen, for instance SettingsFragment when it's already on screen it's re-created, can this be prevented, if so, is it possible only by modifying xml?

    This can be prevented. But you can't do this from xml. To do this, you have to write kotlin code.

    override fun onOptionsItemSelected(item: MenuItem): Boolean {
    
            val navController = findNavController(R.id.nav_host_fragment)
            val currentDestID = navController.currentDestination?.id
    
            return if(item.itemId == currentDestID){
                super.onOptionsItemSelected(item)
            }else{
                ((item.onNavDestinationSelected(navController))
                        || super.onOptionsItemSelected(item))
            }
    
    
    }
    

    Here, by item.itemId == currentDestID this condition I have checked whether clicked menu id is the same as the current page id. If the same id is clicked then I have just called super.

    This solution will work only for Options menu

    When i change use menu item with id it only goes once to Detail Fragment and without animation, how can i fix this?

    As of version 2.2.0-alpha02 there is no way to add animation when you are using NavigationUI. You can view the source code here. They have initialized the default animation.