At this year’s IO conference, a set of libraries called Android Jetpack was announced. Most of the components in Android Jetpack we’ve already touched on, but there are some new ones as well, one of which is Navigation.

Introduction to the

Navigation is used to manage page jumps in your APP. At first, I thought it was meant to replace startActivity, but it’s not, as you’ll see below.

In addition, iOS students may have a sense of deja vu, Navigation should learn from Storyboard.

use

Let’s first look at the implementation of Navigation.

Add the dependent

First, you need Android Studio 3.2 or higher to use Navigation.

Add dependencies to build.gradle:

implementation "android.arch.navigation:navigation-fragment:$nav_version"
implementation "android.arch.navigation:navigation-ui:$nav_version"
Copy the code

Create navigation XML file

When creating the XML File using “Android Resource File”, you can see that there is a Navigation option in the type:

Once you’ve created it, you’re back to the visual interface you saw at the beginning of this article. Click the “Add” icon in the upper left corner, you will see Activity and Fragment. Here we add two activities and two fragments:

Configure the Action

There is a small circle to the right of the Fragment. Click and drag it to another page. This will add a jump Action to the Fragment.

As you can see, the Activity does not have this small circle on its right side, so Navigation does not handle jumps initiated from the Activity.

The first page is displayed with a small house in the upper left corner, but since the Activity cannot initiate a jump, it deletes the MainActivity and uses the MainFragment as the main page. And add actions that jump to SecondFragment and SecondActivity:

The automatically generated XML code looks like this:

<?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"
    app:startDestination="@id/mainFragment">

    <fragment
        android:id="@+id/mainFragment"
        android:name="com.example.navigation.MainFragment"
        android:label="fragment_main"
        tools:layout="@layout/fragment_main">
        <action
            android:id="@+id/action_mainFragment_to_secondFragment"
            app:destination="@id/secondFragment"
            app:enterAnim="@anim/slide_in_right" />
        <action
            android:id="@+id/action_mainFragment_to_secondActivity"
            app:destination="@id/secondActivity" />
    </fragment>
    <fragment
        android:id="@+id/secondFragment"
        android:name="com.example.navigation.SecondFragment"
        android:label="fragment_second"
        tools:layout="@layout/fragment_second" />
    <activity
        android:id="@+id/secondActivity"
        android:name="com.example.navigation.SecondActivity"
        android:label="activity_second"
        tools:layout="@layout/activity_second" />

</navigation>
Copy the code

Add fragments to the layout

Now, our first page is the MainFragment, and the Fragment needs the Activity as the container. Modify the layout of the MainActivity:

<?xml version="1.0" encoding="utf-8"? >
<FrameLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    android:layout_width="match_parent"
    android:layout_height="match_parent">

    <fragment
        android:id="@+id/fragment"
        android:name="androidx.navigation.fragment.NavHostFragment"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        app:defaultNavHost="true"
        app:navGraph="@navigation/nav" />

</FrameLayout>
Copy the code

There are three properties to note. Android :name specifies the type of the Fragment to be NavHostFragment, and App :navGraph specifies the Navigation file. App :defaultNavHost=”true” to make Navigation return an event. Click on the back button to return the previous “page”, which may be an Activity. It can also be a Fragment.

Now that the simple configuration of Navigation is complete, let’s see how to use it.

Configuration jump

In Navigation, page jumps are handled by the NavController. There are three ways to obtain the NavController:

NavHostFragment.findNavController(Fragment)
Navigation.findNavController(Activity, @IdRes int viewId)
Navigation.findNavController(View)
Copy the code

To navigate, pass in the id of the Action via the navigate method, for example:

NavHostFragment
            .findNavController(this)
            .navigate(R.id.action_firstFragment_to_secondFragment)
Copy the code

After simply configuring the two jumps, let’s see what happens so far:

The ginseng

The jump of the page is not without data transfer. Using Navigation, parameters can be passed through the Bundle just like the previous jump:

val bundle = Bundle()
bundle.putString("name"."SouthernBox")
NavHostFragment
            .findNavController(this)
            .navigate(R.id.action_firstFragment_to_secondFragment, bundle)
Copy the code

The bundle can be retrieved from intent.extras if it is a Fragment or from Arguments if it is a Fragment.

It is also possible to configure the pass-through in the Navigation XML file, but this method currently supports very few data types, even Boolean, and I have encountered bugs, so it is not recommended.

Animated transitions

If you need a custom page transition animation, you can easily do it using Navigation.

For example, if we need a cut scene from right to left, create an XML file for the animation:

<?xml version="1.0" encoding="utf-8"? >
<set xmlns:android="http://schemas.android.com/apk/res/android">

    <translate
        android:duration="600"
        android:fromXDelta="100%"
        android:toXDelta="0" />

</set>
Copy the code

Then we will go back to the visual editing page of Navigation, click on the line to jump to, and the cutscene configuration option will appear on the right, set XXXX to the animation we just created:

That’s it. Here’s what it looks like:

So much for Navigation.

thinking

As you probably already know, Navigation is primarily used to handle fragments, so it’s not used to replace startActivity, but rather to replace FragmentTransaction operations.

In the official documentation, you can see a suggestion to migrate traditional jumps to Navigation. My simple understanding is that the original jump between two activities is gradually changed to use one Activity as a container and two fragments as a page jump.

This reminds me of a controversial remark made last year by Jake Wharton, now at Google:

“An APP only needs one Activity.”

In the past, this approach had to deal with complex Fragment stack processing, and in the early days, there were a lot of Fragment pits, which could easily lead to page penetration. Navigation now solves these problems.

All of these, can it be said that the government indirectly supports the practice of “using less Activity and more Fragment”? What do you think?