Jetpack Navigation

Komponen Arsitektur Navigasi menyederhanakan penerapan navigasi, sekaligus membantu Anda memvisualisasikan alur navigasi aplikasi. Library ini memberikan sejumlah manfaat, termasuk:

  • Penanganan otomatis atas transaksi fragmen
  • Menangani atas dan kembali dengan benar secara default
  • Perilaku default untuk animasi dan transisi
  • Deep linking sebagai operasi class pertama
  • Menerapkan pola UI navigasi (seperti panel navigasi dan navigasi bawah ) dengan sedikit pekerjaan tambahan
  • Keamanan jenis ketika meneruskan informasi saat bernavigasi
  • Alat Android Studio untuk memvisualisasikan dan mengedit alur navigasi aplikasi

Yang akan Anda lakukan

Dalam codelab ini, Anda akan mengerjakan aplikasi contoh seperti berikut:

Semua aktivitas dan fragmen telah dibuat untuk Anda. Anda akan menggunakan Komponen Navigasi untuk menghubungkannya dan untuk melakukannya, terapkan hal berikut:

  • Grafik navigasi visual
  • Navigasi menurut tujuan dan tindakan
  • Animasi transisi
  • Navigasi menu, navigasi bawah, dan navigasi panel samping menu
  • Penerusan argumen dengan jenis yang aman
  • Deep link

Prasyarat

  • Pengetahuan Kotlin dasar (codelab ini ada di Kotlin)
  • Android Studio 3.2 atau yang lebih baru
  • Emulator atau perangkat yang menjalankan API 14+

Mendapatkan Kode

Clone codelab navigasi dari GitHub:

$ git clone https://github.com/googlecodelabs/android-navigation

Atau, Anda dapat mendownload repositori sebagai file Zip:

Download Zip

Mendapatkan Android Studio 3.3 atau versi yang lebih baru

Pastikan Anda menggunakan Android Studio 3.3 atau yang lebih tinggi. Versi ini diperlukan untuk alat navigasi Android Studio.

Jika Anda perlu mendownload Android Studio versi terbaru, Anda dapat melakukannya di sini.

Ringkasan Navigasi

Komponen Navigasi terdiri dari tiga bagian utama, yang bekerja secara selaras. Bagian-bagian tersebut adalah:

  1. Grafik Navigasi (Resource XML baru) - Ini adalah resource yang berisi semua informasi terkait navigasi di satu lokasi terpusat. Resource ini mencakup semua tempat di aplikasi Anda, yang dikenal sebagai tujuan, serta potensi jalur yang dapat diambil pengguna melalui aplikasi Anda.
  2. NavHostFragment (Tampilan XML tata letak) - Ini adalah widget khusus yang Anda tambahkan ke tata letak. Widget ini menampilkan tujuan yang berbeda dari Grafik Navigasi Anda.
  3. NavController (Objek Kotlin/Java) - Ini adalah objek yang melacak posisi saat ini dalam grafik navigasi. Objek ini mengatur pertukaran konten tujuan di NavHostFragment saat Anda menelusuri grafik navigasi.

Saat menavigasi, Anda akan menggunakan objek NavController, memberitahukannya ke mana Anda ingin pergi atau jalur yang ingin Anda ambil di Grafik Navigasi. NavController kemudian akan menampilkan tujuan yang sesuai di NavHostFragment.

Itu adalah garis besarnya. Mari kita lihat seperti apa penerapannya, dimulai dengan resource Grafik Navigasi yang baru.

Tujuan

Komponen Navigasi memperkenalkan konsep tujuan. Tujuan adalah tempat mana pun yang dapat Anda jadikan tujuan navigasi di dalam aplikasi, biasanya berupa fragmen atau aktivitas. Ini didukung secara langsung, tetapi Anda juga dapat membuat jenis tujuan kustom Anda sendiri jika diperlukan.

Grafik navigasi adalah jenis resource baru yang menentukan semua potensi jalur yang dapat diambil oleh pengguna melalui aplikasi. Jenis resource ini secara visual menunjukkan semua tujuan yang dapat dijangkau dari tujuan tertentu. Android Studio menampilkan grafik tersebut di Navigation Editor-nya. Berikut ini bagian dari grafik navigasi awal yang akan Anda buat untuk aplikasi:

Beranda, Langkah Satu, dan Langkah Dua

Menjelajahi Navigation Editor

1. Buka res/navigation/mobile_navigation.xml

2. Klik Design untuk membuka mode Design:

Berikut yang akan Anda lihat:

Grafik navigasi ini menampilkan tujuan yang tersedia. Tanda panah di antara tujuan disebut tindakan. Anda akan mempelajari tindakan lebih lanjut nanti.

3. Klik tujuan untuk melihat atributnya.

4. Klik tindakan mana pun, yang diwakili dengan tanda panah, untuk melihat atributnya.

Anatomi file XML navigasi

Semua perubahan yang Anda buat di Navigation Editor grafis mengubah file XML dasar, mirip dengan cara Layout Editor mengubah XML tata letak.

Klik tab Text:

Anda akan melihat beberapa XML seperti ini:

<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/home_dest">

    <!-- ...tags for fragments and activities here -->

</navigation>

Pemberitahuan:

  • <navigation> adalah node root setiap grafik navigasi.
  • <navigation> berisi satu atau beberapa tujuan, yang diwakili oleh elemen <activity> atau <fragment>.
  • app:startDestination adalah atribut yang menentukan tujuan yang diluncurkan secara default saat pengguna pertama kali membuka aplikasi.

Mari kita lihat tujuan fragmen:

<fragment
    android:id="@+id/flow_step_one_dest"
    android:name="com.example.android.codelabs.navigation.FlowStepFragment"
    tools:layout="@layout/flow_step_one_fragment">
    <argument
        .../>

    <action
        android:id="@+id/next_action"
        app:destination="@+id/flow_step_two_dest">
    </action>
</fragment>

Pemberitahuan:

  • android:id menentukan ID untuk fragmen yang dapat Anda gunakan untuk mereferensikan tujuan di tempat lain dalam XML ini dan kode Anda.
  • android:name mendeklarasikan nama class yang sepenuhnya memenuhi syarat dari fragmen untuk membuat instance saat Anda bernavigasi ke tujuan tersebut.
  • tools:layout menentukan tata letak yang harus ditampilkan di editor grafis.

Beberapa tag <fragment> juga berisi <action>, <argument>,, dan <deepLink>, yang semuanya akan kita bahas nanti.

Aplikasi contoh dimulai dengan beberapa tujuan dalam grafik. Pada langkah ini, Anda akan menambahkan tujuan baru. Anda harus menambahkan tujuan ke grafik navigasi sebelum dapat menavigasi ke tujuan tersebut.

1. Buka res/navigation/mobile_navigation.xml, dan klik tab Design.

2. Klik ikon Tujuan Baru, lalu pilih "settings_fragment"

Hasilnya adalah tujuan baru, yang menampilkan pratinjau tata letak fragmen di tampilan desain.

Perhatikan bahwa Anda juga dapat mengedit file XML secara langsung untuk menambahkan tujuan:

mobile_navigation.xml

<fragment
    android:id="@+id/settings_dest"
    android:name="com.example.android.codelabs.navigation.SettingsFragment"
    android:label="@string/settings"
    tools:layout="@layout/settings_fragment" />

Sekarang, Anda memiliki grafik navigasi hebat ini, namun Anda tidak benar-benar menggunakannya untuk menavigasi.

Aktivitas dan Navigasi

Komponen Navigasi mengikuti panduan yang diuraikan di dalam Prinsip Navigasi. Prinsip Navigasi menyarankan Anda agar menggunakan aktivitas sebagai titik entri untuk aplikasi. Aktivitas juga akan berisi navigasi global, seperti navigasi bawah.

Sebagai perbandingan, fragmen akan menjadi tata letak spesifik tujuan yang sebenarnya.

Agar semua ini berfungsi, Anda perlu mengubah tata letak aktivitas agar berisi widget khusus yang disebut NavHostFragment. NavHostFragment menukar berbagai tujuan fragmen ke dalam dan ke luar saat Anda bernavigasi melalui grafik navigasi.

Tata letak sederhana yang mendukung navigasi yang mirip dengan gambar di atas terlihat seperti ini. Contoh kode ini dapat ditemukan di res/layout-470dp/navigation_activity.xml:

<LinearLayout
    .../>
    <androidx.appcompat.widget.Toolbar
        .../>
    <fragment
        android:layout_width="match_parent"
        android:layout_height="0dp"
        android:layout_weight="1"
        android:id="@+id/my_nav_host_fragment"
        android:name="androidx.navigation.fragment.NavHostFragment"
        app:navGraph="@navigation/mobile_navigation"
        app:defaultNavHost="true"
        />
    <com.google.android.material.bottomnavigation.BottomNavigationView
        .../>
</LinearLayout>

Pemberitahuan:

  • Ini adalah tata letak untuk aktivitas. Ini berisi navigasi global, termasuk navigasi bawah dan toolbar
  • android:name="androidx.navigation.fragment.NavHostFragment" dan app:defaultNavHost="true" menghubungkan tombol kembali sistem ke NavHostFragment
  • app:navGraph="@navigation/mobile_navigation" mengaitkan NavHostFragment dengan grafik navigasi. Grafik navigasi ini menentukan semua tujuan yang dapat dijadikan tujuan navigasi oleh pengguna, dalam NavHostFragment ini.

Terakhir, ketika pengguna melakukan sesuatu seperti mengklik tombol, Anda perlu memicu perintah navigasi. Class khusus yang disebut NavController adalah pemicu pertukaran fragmen di NavHostFragment.

// Command to navigate to flow_step_one_dest
findNavController().navigate(R.id.flow_step_one_dest)

Perhatikan bahwa Anda meneruskan tujuan atau ID tindakan untuk menavigasi. Ini adalah ID yang ditentukan dalam XML grafik navigasi. Ini adalah contoh penerusan ID tujuan.

NavController sangat efektif karena ketika Anda memanggil metode seperti navigate() atau popBackStack(),, perintah ini akan diterjemahkan ke dalam operasi framework yang sesuai berdasarkan jenis tujuan yang dituju atau asal tujuan. Misalnya, saat Anda memanggil navigate() dengan tujuan aktivitas, NavController memanggil startActivity() sebagai ganti Anda.

Ada beberapa cara untuk mendapatkan objek NavController yang dikaitkan dengan NavHostFragment Anda. Di Kotlin, sebaiknya gunakan salah satu fungsi ekstensi berikut, tergantung pada apakah Anda memanggil kembali perintah navigasi dari dalam fragmen, aktivitas, atau tampilan:

Sekarang giliran Anda untuk bernavigasi menggunakan NavController. Anda akan menghubungkan tombol Navigate To Destination untuk bernavigasi ke tujuan flow_step_one_dest (yaitu tujuan yang merupakan FlowStepFragment):

1. Buka HomeFragment.kt

2. Hubungkan navigate_destination_button di onViewCreated()

HomeFragment.kt

val button = view.findViewById<Button>(R.id.navigate_destination_button)
button?.setOnClickListener {
    findNavController().navigate(R.id.flow_step_one_dest, null)
}

3. Jalankan aplikasi dan klik tombol Navigate To Destination. Perhatikan bahwa tombol akan menavigasi ke tujuan flow_step_one_dest.

Kode pemroses klik akan terlihat seperti ini:

val button = view.findViewById<Button>(R.id.navigate_destination_button)
button?.setOnClickListener(
        Navigation.createNavigateOnClickListener(R.id.flow_step_one_dest, null)
)

Setiap panggilan navigate() memiliki transisi default tidak terlalu menarik yang berkaitan dengannya, seperti yang terlihat di bawah ini:

Dari Beranda, pengguna mengklik Navigate to destination dan menuju ke langkah pertama.

Transisi default, serta atribut lainnya yang berkaitan dengan panggilan, dapat diganti dengan menyertakan kumpulan NavOptions. NavOptions menggunakan pola Builder yang memungkinkan Anda mengganti dan menetapkan hanya opsi yang diperlukan. Ada juga ktx DSL untuk NavOptions, yang akan Anda gunakan.

Untuk transisi animasi, Anda dapat menentukan resource animasi XML di folder resource anim, lalu menggunakan animasi tersebut untuk transisi. Beberapa contoh disertakan di dalam kode aplikasi:

Menambahkan Transisi Kustom

Perbarui kode sehingga menekan tombol Navigate To Destination akan menampilkan animasi transisi kustom.

1. Buka HomeFragment.kt

2. Tentukan NavOptions dan teruskan ke dalam panggilan navigate() ke navigate_destination_button

val options = navOptions {
    anim {
        enter = R.anim.slide_in_right
        exit = R.anim.slide_out_left
        popEnter = R.anim.slide_in_left
        popExit = R.anim.slide_out_right
    }
}
view.findViewById<Button>(R.id.navigate_destination_button)?.setOnClickListener {
    findNavController().navigate(R.id.flow_step_one_dest, null, options)
}

3. Hapus kode yang ditambahkan pada langkah 5, jika masih ada

4. Pastikan bahwa mengetuk tombol Navigate To Destination membuat fragmen bergeser ke dalam layar dan menekannya kembali membuatnya bergeser keluar dari layar

Tindakan

Sistem navigasi juga memungkinkan Anda bernavigasi melalui tindakan. Seperti yang dijelaskan sebelumnya, garis yang ditampilkan di grafik navigasi adalah representasi visual tindakan.

Navigasi menurut tindakan memiliki manfaat berikut dibandingkan navigasi menurut tujuan:

  • Anda dapat memvisualisasikan jalur navigasi melalui aplikasi
  • Tindakan dapat berisi atribut terkait tambahan yang dapat Anda tetapkan, seperti animasi transisi, nilai argumen, dan perilaku data sebelumnya
  • Anda dapat menggunakan safe args plugin untuk menavigasi, yang akan segera Anda lihat

Berikut visual dan XML untuk tindakan yang menghubungkan flow_step_one_dest dan flow_step_two_dest:

<fragment
    android:id="@+id/flow_step_one_dest"
    android:name="com.example.android.codelabs.navigation.FlowStepFragment">

    <argument
        .../>

    <action
        android:id="@+id/next_action"
        app:destination="@+id/flow_step_two_dest">
    </action>
</fragment>

<fragment
    android:id="@+id/flow_step_two_dest"
    android:name="com.example.android.codelabs.navigation.FlowStepFragment">
    <!-- ...removed for simplicity-->
</fragment>

Pemberitahuan:

  • Tindakan ini akan menjadi bertingkat di dalam tujuan - ini adalah tujuan yang akan Anda jadikan awal navigasi
  • Tindakan mencakup argumen tujuan yang mengacu pada flow_step_two_dest; ini adalah ID tempat yang Anda jadikan tujuan navigasi
  • ID untuk tindakan adalah "next_action"

Berikut adalah contoh lain dari tindakan yang menghubungkan flow_step_two_dest ke home_dest:

<fragment
    android:id="@+id/home_dest"
    android:name="com.example.android.codelabs.navigation.HomeFragment"
    .../>

<fragment
    android:id="@+id/flow_step_two_dest"
    android:name="com.example.android.codelabs.navigation.FlowStepFragment">

    <argument
        .../>

    <action
        android:id="@+id/next_action"
        app:popUpTo="@id/home_dest">
    </action>
</fragment>

Pemberitahuan:

  • ID next_action yang sama digunakan untuk tindakan yang menghubungkan flow_step_two_dest ke home_dest. Anda dapat bernavigasi menggunakan id next_action dari flow_step_one_dest atau flow_step_two_dest. Ini adalah contoh bagaimana tindakan dapat memberikan tingkat abstraksi dan dapat mengarahkan Anda ke berbagai tempat berdasarkan konteksnya.
  • Atribut popUpTo sedang digunakan - tindakan ini akan memunculkan fragmen dari data sebelumnya sampai Anda mencapai home_dest

Saatnya untuk menghubungkan tombol Navigate with Action agar berfungsi sesuai dengan namanya!

1. Buka file mobile_navigation.xml dalam mode Design

2. Tarik tanda panah dari home_dest ke flow_step_one_dest:

3. Dengan tanda panah tindakan yang dipilih (biru), ubah properti tindakan sehingga:

  • ID = next_action
  • Transisi untuk Enter = slide_in_right
  • Transisi untuk Exit = slide_out_left
  • Transisi untuk Pop Enter = slide_in_left
  • Transisi untuk Pop Exit = slide_out_right

4. Klik tab Text

Perhatikan tindakan next_action yang baru ditambahkan di bawah tujuan home_dest:

mobile_navigation.xml

<fragment android:id="@+id/home_dest"
        ...>

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

5. Buka HomeFragment.kt

6. Tambahkan pemroses klik ke navigate_action_button

HomeFragment.kt

 view.findViewById<Button>(R.id.navigate_action_button)?.setOnClickListener(
        Navigation.createNavigateOnClickListener(R.id.next_action, null)
)

7. Pastikan bahwa mengetuk Navigate To Action sekarang akan menavigasi ke layar berikutnya.

Safe Args

Komponen navigasi memiliki plugin Gradle, disebut safe args, yang membuat class objek dan builder sederhana untuk jenis akses yang aman ke argumen yang ditentukan bagi tujuan dan tindakan.

Safe args memungkinkan Anda membuang kode seperti ini saat meneruskan nilai antar-tujuan:

val username = arguments?.getString("usernameKey")

Dan, sebagai gantinya, ganti dengan kode yang telah menghasilkan penyetel dan pengambil.

val username = args.username

Meneruskan nilai menggunakan safe args

1. Buka file project build.gradle dan lihat plugin safe args:

build.gradle

dependencies {
        classpath "androidx.navigation:navigation-safe-args-gradle-plugin:$navigationVersion"
    //...
    }

2. Buka file app/build.gradle dan perhatikan plugin yang diterapkan:

app/build.gradle

apply plugin: 'com.android.application'
apply plugin: 'kotlin-android'
apply plugin: 'androidx.navigation.safeargs.kotlin'

android {
   //...
}

3. Buka mobile_navigation.xml, dan perhatikan bahwa argumen ditentukan di tujuan flow_step_one_dest.

mobile_navigation.xml

<fragment
    android:id="@+id/flow_step_one_dest"
    android:name="com.example.android.codelabs.navigation.FlowStepFragment"
    tools:layout="@layout/flow_step_one_fragment">
    <argument
        android:name="flowStepNumber"
        app:argType="integer"
        android:defaultValue="1"/>

    <action...>
    </action>
</fragment>

Menggunakan tag <argument>, safeargs menghasilkan class yang disebut FlowStepFragmentArgs.

Karena XML menyertakan argumen yang disebut flowStepNumber, yang ditetapkan oleh android:name="flowStepNumber", class FlowStepFragmentArgs yang dihasilkan akan menyertakan variabel flowStepNumber dengan pengambil dan penyetel.

4. Buka FlowStepFragment.kt

5. Buat baris kode yang ditampilkan di bawah ini menjadi komentar:

FlowStepFragment.kt

// Comment out this line
// val flowStepNumber = arguments?.getInt("flowStepNumber")

Kode gaya lama ini bukan jenis yang aman. Sebaiknya gunakan safe args.

6. Perbarui FlowStepFragment untuk menggunakan kode yang dihasilkan class FlowStepFragmentArgs. Ini akan mendapatkan argumen FlowStepFragment memiliki jenis yang aman:

FlowStepFragment.kt

val safeArgs: FlowStepFragmentArgs by navArgs()
val flowStepNumber = safeArgs.flowStepNumber

Class Direction Safe Args

Anda juga dapat menggunakan safe args untuk bernavigasi dengan jenis yang aman, dengan atau tanpa menambahkan argumen. Lakukan dengan menggunakan class Direction yang dihasilkan.

Class Direction dihasilkan untuk setiap tujuan yang berbeda dengan tindakan. Class Direction mencakup metode untuk setiap tindakan yang dimiliki tujuan.

Misalnya, pemroses klik navigate_action_button di HomeFragment.kt dapat diubah menjadi:

HomeFragment.kt

// Note the usage of curly braces since we are defining the click listener lambda
view.findViewById<Button>(R.id.navigate_action_button)?.setOnClickListener {
    val flowStepNumberArg = 1
    val action = HomeFragmentDirections.nextAction(flowStepNumberArg)
    findNavController().navigate(action)
}

Komponen Navigasi mencakup class NavigationUI dan ekstensi kotlin navigation-ui-ktx. NavigationUI memiliki metode statis yang mengaitkan item menu dengan tujuan navigasi, dan navigation-ui-ktx adalah kumpulan fungsi ekstensi dengan fungsi yang sama. Jika NavigationUI menemukan item menu dengan ID yang sama sebagai tujuan pada grafik saat ini, item menu akan dikonfigurasi untuk menavigasi ke tujuan tersebut.

Menggunakan NavigationUI dengan menu Opsi

Salah satu cara termudah untuk menggunakan NavigationUI adalah membuatnya menyederhanakan penyiapan menu opsi. Secara khusus, NavigationUI menyederhanakan penanganan callback onOptionsItemSelected.

1. Buka MainActivity.kt

Perhatikan bahwa Anda sudah memiliki kode untuk meng-inflate menu overflow_menu di onCreateOptionsMenu

2. Buka res/menu/overflow_menu.xml

3. Perbarui menu tambahan untuk menyertakan settings_dest

overflow_menu.xml

<item
    android:id="@+id/settings_dest"
    android:icon="@drawable/ic_settings"
    android:menuCategory="secondary"
    android:title="@string/settings" />

4. Buka MainActivity.kt

5. Buat NavigationUI agar menangani onOptionsItemSelected dengan metode helper onNavDestinationSelected. Jika item menu tidak dimaksudkan untuk menavigasi, tangani dengan super.onOptionsItemSelected

MainActivity.kt

override fun onOptionsItemSelected(item: MenuItem): Boolean {
    return item.onNavDestinationSelected(findNavController(R.id.my_nav_host_fragment))
            || super.onOptionsItemSelected(item)
}

6. Jalankan aplikasi Anda. Menu ActionBar akan dapat digunakan untuk membuka SettingsFragment.

Menggunakan NavigationUI untuk mengonfigurasi Navigasi Bawah

Kode ini sudah berisi kode tata letak XML untuk menerapkan navigasi bawah, itulah sebabnya Anda melihat menu navigasi bawah. Tetapi, kode ini tidak menavigasi ke mana pun.

1. Buka res/layout/navigation_activity/navigation_activity.xml (h470dp) dan klik tab Text

Perhatikan bahwa kode tata letak XML untuk navigasi bawah tersedia dan mengacu pada bottom_nav_menu.xml

<com.google.android.material.bottomnavigation.BottomNavigationView
    android:id="@+id/bottom_nav_view"
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    app:menu="@menu/bottom_nav_menu" />

2. Buka res/menu/bottom_nav_menu.xml

Perhatikan bahwa ada dua item untuk navigasi bawah dan bahwa id-nya cocok dengan tujuan grafik navigasi:

bottom_nav_menu.xml

<menu xmlns:android="http://schemas.android.com/apk/res/android">
    <item
        android:id="@id/home_dest"
        android:icon="@drawable/ic_home"
        android:title="@string/home" />
    <item
        android:id="@id/deeplink_dest"
        android:icon="@drawable/ic_android"
        android:title="@string/deeplink" />
</menu>

Mari kita buat navigasi bawah melakukan tugasnya menggunakan NavigationUI.

3. Buka MainActivity.kt

4. Terapkan metode setupBottomNavMenu menggunakan setupWithNavController(bottomNavigationView: BottomNavigationView, navController: NavController)

MainActivity.kt

private fun setupBottomNavMenu(navController: NavController) {
    val bottomNav = findViewById<BottomNavigationView>(R.id.bottom_nav_view)
    bottomNav?.setupWithNavController(navController)
}

Kini navigasi bawah Anda telah berfungsi!

Menggunakan NavigationUI untuk mengonfigurasi Panel Navigasi

Terakhir, mari kita gunakan NavigationUI untuk mengonfigurasi navigasi samping dan panel navigasi, termasuk menangani ActionBar dan navigasi atas yang benar. Anda akan melihat ini jika memiliki layar yang cukup besar atau jika layar terlalu pendek untuk navigasi bawah.

Pertama, amati bagaimana kode XML tata letak yang tepat sudah ada di dalam aplikasi.

1. Buka navigation_activity.xml dan navigation_activity.xml (w960dp)

Perhatikan bahwa kedua tata letak berisi NavigationView yang terhubung ke nav_drawer_menu. Pada versi tablet (w960dp), NavigationView akan selalu ditampilkan di layar. Pada perangkat yang lebih kecil, NavigationView akan bertingkat di dalam DrawerLayout.

Sekarang untuk mulai menerapkan navigasi NavigationView.

2. Buka MainActivity.kt

3. Terapkan metode setupNavigationMenu menggunakan setupWithNavController(navigationView: NavigationView, navController: NavController). Perhatikan bahwa versi metode ini memerlukan NavigationView dan bukan BottomNavigationView.

MainActivity.kt

private fun setupNavigationMenu(navController: NavController) {
    val sideNavView = findViewById<NavigationView>(R.id.nav_view)
    sideNavView?.setupWithNavController(navController)
}

Sekarang menu tampilan navigasi akan muncul di layar, tetapi tidak akan memengaruhi ActionBar.

Menyiapkan ActionBar memerlukan pembuatan instance AppBarConfiguration. Tujuan dari AppBarConfiguration adalah menentukan opsi konfigurasi yang Anda inginkan untuk toolbar, toolbar yang menciut, dan panel tindakan. Opsi konfigurasi mencakup apakah panel tersebut harus menangani tata letak panel samping dan tujuan mana yang dianggap sebagai tujuan tingkat atas.

Tujuan tingkat atas adalah tujuan level root aplikasi Anda. Tujuan ini tidak menampilkan tombol "atas" di panel aplikasi, dan tujuan menampilkan ikon panel samping jika tujuan menggunakan tata letak panel samping.

4. Buat AppBarConfiguration dengan meneruskan kumpulan ID tujuan tingkat atas dan tata letak panel samping.

MainActivity.kt

val drawerLayout : DrawerLayout? = findViewById(R.id.drawer_layout)
appBarConfiguration = AppBarConfiguration(
        setOf(R.id.home_dest, R.id.deeplink_dest),
        drawerLayout)

Setelah memiliki AppBarConfiguration, Anda dapat memanggil NavigationUI.setupActionBarWithNavController. Tindakan ini akan melakukan hal berikut:

  • Menampilkan judul di ActionBar berdasarkan label tujuan
  • Menampilkan tombol Atas setiap kali Anda tidak berada di tujuan tingkat atas
  • Menampilkan ikon panel samping (ikon hamburger) saat Anda berada di tujuan tingkat atas

5. Terapkan setupActionBarWithNavController

MainActivity.kt

private fun setupActionBar(navController: NavController,
                           appBarConfig : AppBarConfiguration) {
    setupActionBarWithNavController(navController, appBarConfig)
}

Anda juga harus memiliki NavigationUI untuk menangani apa yang terjadi saat tombol Atas ditekan.

6. Ganti onSupportNavigationUp dan panggil NavigationUI.navigateUp, menggunakan AppBarConfiguration yang sama.

MainActivity.kt

override fun onSupportNavigateUp(): Boolean {
    return findNavController(R.id.my_nav_host_fragment).navigateUp(appBarConfiguration)
}

7. Jalankan kode. Jika membuka aplikasi di layar terpisah, Anda akan memiliki panel navigasi yang berfungsi. Ikon atas dan ikon panel samping akan ditampilkan pada waktu yang tepat dan bekerja dengan benar.

Menambahkan tujuan baru ke NavigationView adalah hal yang mudah. Setelah panel navigasi berfungsi bersama dengan navigasi atas dan kembali, Anda hanya perlu menambahkan item menu baru.

8. Buka menu/nav_drawer_menu.xml

9. Tambahkan item menu baru untuk settings_dest

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

Sekarang panel navigasi Anda menampilkan layar Setelan sebagai tujuan. Kerja bagus!

Komponen navigasi juga menyertakan dukungan deep link. Deep link adalah cara untuk langsung ke bagian tengah navigasi aplikasi, baik dari link URL yang sebenarnya atau intent tertunda dari notifikasi.

Salah satu manfaat penggunaan library navigasi untuk menangani deep link adalah memastikan pengguna memulai dari tujuan yang sesuai dengan data sebelumnya dari titik entri lainnya seperti widget aplikasi, notifikasi, atau link web (dibahas pada langkah berikutnya).

Navigasi menyediakan class NavDeepLinkBuilder untuk membuat PendingIntent yang akan mengarahkan pengguna ke tujuan tertentu.

Kita akan menggunakan NavDeepLinkBuilder untuk menghubungkan widget aplikasi ke tujuan.

1. Buka DeepLinkAppWidgetProvider.kt

2. Tambahkan PendingIntent yang dibuat dengan NavDeepLinkBuilder:

DeepLinkAppWidgetProvider

val args = Bundle()
args.putString("myarg", "From Widget");
val pendingIntent = NavDeepLinkBuilder(context)
        .setGraph(R.navigation.mobile_navigation)
        .setDestination(R.id.deeplink_dest)
        .setArguments(args)
        .createPendingIntent()

remoteViews.setOnClickPendingIntent(R.id.deep_link_button, pendingIntent)

Pemberitahuan:

  • setGraph mencakup grafik navigasi.
  • setDestination menentukan tujuan link.
  • setArguments mencakup argumen yang ingin Anda teruskan ke deep link Anda.

3. Tambahkan widget Deep Link ke layar utama. Sentuh lama layar utama untuk melihat opsi untuk menambahkan widget.

Sentuh lama

Scroll ke bawah untuk menemukan widget

Setelah selesai, Anda akan memiliki widget deep link.

4. Ketuk widget, dan pastikan bahwa tujuan Android terbuka dengan argumen yang benar. Seharusnya tertulis "From Widget" di bagian atas karena itu adalah argumen yang Anda teruskan di DeepLinkAppWidgetProvider.

5. Pastikan bahwa menekan tombol kembali akan membawa Anda ke tujuan home_dest.

Data sebelumnya untuk deep link ditentukan menggunakan grafik navigasi yang Anda teruskan. Jika Aktivitas eksplisit yang Anda pilih memiliki aktivitas induk, Aktivitas induk tersebut juga disertakan.

Data sebelumnya dibuat menggunakan tujuan yang ditentukan dengan app:startDestination. Dalam aplikasi ini, kami hanya memiliki satu aktivitas dan satu tingkat navigasi, sehingga data sebelumnya akan membawa Anda ke tujuan home_dest.

Navigasi yang lebih rumit dapat menyertakan grafik navigasi bertingkat. app:startDestination di setiap tingkat grafik bertingkat menentukan data sebelumnya. Untuk informasi selengkapnya tentang deep link dan grafik bertingkat, lihat Prinsip Navigasi.

Salah satu penggunaan paling umum deep link adalah dengan mengizinkan link web membuka aktivitas di aplikasi Anda. Sebelumnya, Anda menggunakan filter intent dan mengaitkan URL dengan aktivitas yang ingin Anda buka.

Library navigasi membuat ini sangat sederhana dan memungkinkan Anda memetakan URL langsung ke tujuan di grafik navigasi.

<deepLink> adalah elemen yang dapat Anda tambahkan ke tujuan dalam grafik. Setiap elemen <deepLink> memiliki satu atribut yang diperlukan: app:uri.

Selain pencocokan URI langsung, fitur berikut ini didukung:

  • URI yang tidak memiliki skema dianggap sebagai http dan https. Misalnya, www.example.com akan cocok dengan http://www.example.com dan https://www.example.com.
  • Anda dapat menggunakan placeholder dalam bentuk {placeholder_name} untuk mencocokkan satu karakter atau lebih. Nilai String placeholder tersedia dalam Paket argumen yang memiliki kunci dengan nama yang sama. Misalnya, http://www.example.com/users/{id} akan cocok dengan http://www.example.com/users/4.
  • Anda dapat menggunakan karakter pengganti .* untuk mencocokkan nol atau beberapa karakter.
  • NavController akan menangani intent ACTION_VIEW secara otomatis dan mencari deep link yang cocok.

Pada langkah ini, Anda akan menambahkan deep link ke www.example.com.

1. Buka mobile_navigation.xml

2. Tambahkan elemen <deepLink> ke tujuan deeplink_dest.

mobile_navigation.xml

<fragment
    android:id="@+id/deeplink_dest"
    android:name="com.example.android.codelabs.navigation.DeepLinkFragment"
    android:label="@string/deeplink"
    tools:layout="@layout/deeplink_fragment">

    <argument
        android:name="myarg"
        android:defaultValue="Android!"/>

    <deepLink app:uri="www.example.com/{myarg}" />
</fragment>

3. Buka AndroidManifest.xml

4. Tambahkan tag nav-graph. Ini akan memastikan filter intent yang benar dihasilkan

AndroidManifest.xml

<activity android:name=".MainActivity">
    <intent-filter>
        <action android:name="android.intent.action.MAIN" />
        <category android:name="android.intent.category.DEFAULT" />
        <category android:name="android.intent.category.LAUNCHER" />
    </intent-filter>

    <nav-graph android:value="@navigation/mobile_navigation" />
</activity>

5. Luncurkan aplikasi Anda menggunakan deep link. Ada 2 cara untuk melakukannya:

  • Gunakan adb:
adb shell am start -a android.intent.action.VIEW -d "http://www.example.com/urlTest" 
  • Navigasikan melalui aplikasi Google. Anda akan dapat menempatkan www.example.com/urlTest di kotak penelusuran dan jendela disambiguasi akan muncul. Pilih Navigation codelab

Dibuka menggunakan kotak penelusuran

(bukan di Chrome)

Dialog disambiguasi

Anda akan melihat pesan "urlTest" di layar. Pesan ini diteruskan ke fragmen, dari URL.

Ada satu bagian lagi dari aplikasi codelab yang dapat Anda coba, yaitu tombol keranjang belanja.

Ini adalah rangkuman keterampilan yang telah Anda pelajari selama codelab ini. Langkah ini tidak mencakup pemberian komentar, jadi coba sendiri:

  1. Buat class fragmen baru
  2. Tambahkan fragmen sebagai tujuan ke grafik navigasi Anda
  3. Buat ikon keranjang belanja membuka class fragmen baru Anda menggunakan NavigationUI untuk menangani menu.

Anda telah memahami konsep dasar di balik komponen Navigasi! Dalam codelab ini, Anda mempelajari:

  • Struktur grafik navigasi
  • NavHostFragment dan NavController
  • Cara menavigasi ke tujuan tertentu
  • Cara melakukan navigasi berdasarkan tindakan
  • Cara meneruskan argumen antar-tujuan, termasuk menggunakan plugin safeargs baru
  • Menavigasi menggunakan menu, navigasi bawah, dan panel navigasi
  • Menavigasi melalui deep link


Anda dapat terus menjelajah dengan aplikasi ini atau mulai menggunakan navigasi di aplikasi Anda sendiri.

Ada banyak hal lain yang dapat dicoba, termasuk:

  • Melepaskan tujuan dari data sebelumnya (atau manipulasi data sebelumnya apa pun)
  • Grafik navigasi bertingkat
  • Navigasi bersyarat
  • Menambahkan dukungan untuk tujuan baru

Untuk informasi selengkapnya tentang Komponen Navigasi, lihat dokumentasi. Jika Anda tertarik mempelajari Komponen Arsitektur lainnya, coba codelab berikut: