Anda sekarang berada di bagian keempat dari artikel bagus tentang Komponen Navigasi dalam proyek multi-modul. Jika Anda sudah tahu:
-
Bagaimana plugin Safe Args bekerja dan apa fungsinya
Bagaimana Anda bisa membangun pekerjaan dengan Komponen Navigasi dalam proyek multi-modul
Kemudian selamat datang di bagian akhir cerita tentang pengalaman saya dengan pustaka yang luar biasa ini - tentang solusi untuk navigasi multistack seperti iOS.
Anda dapat melihat bagaimana semuanya bekerja di sini
Jika Anda tidak tahu, maka keluar dan masuk biasanya membaca tiga artikel di atas terlebih dahulu.
Selain pustaka Komponen Navigasi, Google telah merilis beberapa add-on frontend yang disebut NavigationUI yang membantu Anda menghubungkan navigasi ke BottomBar, Menu, dan komponen standar lainnya. Namun seringkali ada persyaratan bahwa setiap tab memiliki tumpukannya sendiri dan status saat ini disimpan saat beralih di antara mereka. Sayangnya, di luar kotak, Komponen Navigasi dan NavigationUI tidak melakukan itu.
Dukungan untuk pendekatan ini disediakan oleh Google sendiri di repositori arsitektur-komponen-sampel mereka di GitHub ( https://github.com/android/architecture-components-samples/tree/master/NavigationAdvancedSample ). Esensinya sederhana:
Tambahkan FragmentContainer.
NavHostFragment .
NavHostFragment FragmentManager-a.
, :
. NavigationBottomBar Deep Link-. , deep link- . , βββ . NavigationExtensions 250 loc, lazy- NavHost-, :
/ NavHost-:
fun obtainNavHostFragment(
fragmentManager: FragmentManager,
fragmentTag: String,
navGraphId: Int,
containerId: Int
): NavHostFragment {
// If the Nav Host fragment exists, return it
val existingFragment =
fragmentManager.findFragmentByTag(fragmentTag) as NavHostFragment?
existingFragment?.let { return it }
// Otherwise, create it and return it.
val navHostFragment = NavHostFragment.create(navGraphId)
fragmentManager.beginTransaction()
.add(containerId, navHostFragment, fragmentTag)
.commitNow()
return navHostFragment
}
NavHost-:
protected fun selectTab(tab: Tab) {
val newFragment = obtainNavHostFragment(
childFragmentManager,
getFragmentTag(tabs.indexOf(tab)),
tab.graphId,
containerId
)
val fTrans = childFragmentManager.beginTransaction()
with(fTrans) {
if (selectedFragment != null) detach(selectedFragment!!)
attach(newFragment)
commitNow()
}
selectedFragment = newFragment
currentNavController = selectedFragment!!.navController
tabSelected(tab)
}
βBackβ:
activity?.onBackPressedDispatcher?.addCallback(
viewLifecycleOwner,
object: OnBackPressedCallback(true){
override fun handleOnBackPressed() {
val isNavigatedUp = currentNavController.navigateUp()
if(isNavigatedUp){
return
}else{
activity?.finish()
}
}
}
)
iOS-like , lazy- . βββ , .