NavHost — Jetpack Compose-da navigatsiya grafi uchun kirish nuqtasi bo'lib xizmat qiluvchi composable konteynerdir. U NavController-ni marshrutlar to'plami bilan bog'laydi va back stack holatiga qarab joriy ekranni ko'rsatadi. Android Developers (2025) ma'lumotlariga ko'ra, NavHost navigatsiyaga ega har qanday Compose ilovasi uchun majburiy komponent hisoblanadi. NavHost ichida ixtiyoriy argumentlar, deep links va animatsiya bilan composable marshrutlar ro'yxatdan o'tkaziladi. Har bir marshrut — NavBackStackEntry-ni qabul qiluvchi oddiy composable funksiyadir. NavHost back press, holatni saqlash va rekonfiguratsiyada tiklashni avtomatik boshqaradi.
Asosiy fikrlar
NavHost — joriy navigatsiya ekranini ko'rsatish uchun konteyner ta'minlovchi composable funksiyadir. NavHost NavController, startDestination va Kotlin DSL orqali qurilgan marshrut grafigini qabul qiladi. Joriy marshrut o'zgarganda, NavHost ko'rsatilayotgan composable-ni belgilangan animatsiya bilan almashtiradi.
NavHost ekran almashtirgich sifatida ishlaydi: NavController-dan joriy NavBackStackEntry-ni kuzatadi va tegishli composable blokni ko'rsatadi. Har bir ekran — NavBackStackEntry-ni qabul qiluvchi mustaqil composable funksiyadir. Barcha ekranlar yagona kompozitsiya daraxtida mavjud, ammo NavHost faqat bittasini ko'rsatadi, qolganlarini animatsiya orqali yashiradi.
FragmentManager-dan farqli o'laroq, NavHost har bir ekran uchun Fragment yaratmaydi. Butun lifecycle CompositionLifecycle orqali boshqariladi — composable funksiyalarida onStart/onResume mavjud emas, shuning uchun yon ta'sirlar uchun LaunchedEffect va DisposableEffect ishlatiladi. NavHost avtomatik ravishda NavController-ga obuna bo'ladi va marshrut o'zgarganda UI-ni qayta quradi.
Google ma'lumotlariga ko'ra, NavHost Navigation 2.4.0 versiyasidan boshlab barqaror API hisoblanadi. 2.8.0 versiyasidan boshlab, NavHost Kotlin Serialization orqali Type-Safe Navigation-ni qo'llab-quvvatlaydi, bu string route-larni data-klaslar bilan almashtiradi. NavHost shuningdek ichma-ich graflarni qo'llab-quvvatlaydi, bu modullar bo'yicha navigatsiyani tashkil qilish imkonini beradi.
NavHost ikkita majburiy parametr bilan yaratiladi: navController (NavHostController namunasi) va startDestination (birinchi ekran marshrutining stringi). Uchinchi parametr — builder bloki bo'lib, unda barcha marshrutlar composable(), navigation() va dialog() orqali ro'yxatdan o'tkaziladi.
@Composable
fun AppNavHost(navController: NavHostController) {
NavHost(
navController = navController,
startDestination = "home"
) {
composable("home") { HomeScreen(navController) }
composable("settings") { SettingsScreen(navController) }
}
}
startDestination — NavHost birinchi marta ishga tushirilganda ochiladigan marshrutdir. Agar back stack bo'sh bo'lsa, NavHost avtomatik ravishda startDestination-ni stekka qo'shadi. Rekonfiguratsiya vaqtida (ekran aylantirilganda) NavHost savedState-dan oxirgi marshrutni tiklaydi, startDestination-ni emas.
BottomNavigation uchun startDestination pastki panelning marshrutlaridan biridir. Panelning qolgan marshrutlari alohida composable yozuvlari sifatida qo'shiladi. NavHost Scaffold.content ichida — ilovaning asosiy mazmuni ko'rsatiladigan joyda joylashtirilishi kerak. NavHost TopAppBar va BottomNavigation chiqarib tashlangandan keyin qolgan barcha balandlikni egallaydi.
composable(route, arguments, deepLinks, enterTransition, exitTransition, content) funksiyasi NavHost grafigida marshrutni ro'yxatdan o'tkazadi. route parametri — {paramName} ko'rinishidagi ixtiyoriy placeholderlarga ega yo'lni tavsiflovchi stringdir. Placeholder navigatsiya vaqtida aniq qiymat bilan almashtiriladi.
Content bloki NavBackStackEntry ni qabul qiladi, undan argumentlar olinadi. Ekranning composable funksiyasi faqat NavController-ning joriy marshruti route bilan mos kelganda ko'rsatiladi. Mos kelmaslik holatida composable kompozitsiyadan olib tashlanadi, ammo uning holati rememberSaveable yoki SavedStateHandle bilan ViewModel orqali saqlanishi mumkin.
composable(
route = "article/{articleId}",
arguments = listOf(navArgument("articleId") {
type = NavType.IntType
defaultValue = 0
}),
deepLinks = listOf(navDeepLink { uriPattern = "https://app.example/article/{articleId}" })
) { backStackEntry ->
val articleId = backStackEntry.arguments?.getInt("articleId") ?: 0
ArticleScreen(articleId = articleId)
}
NavHost ichidagi composable yozuvlari soni istalgan bo'lishi mumkin — bir nechtadan yuzlabgacha. Katta ilovalar uchun marshrutlar modullarga bo'linadi va ichma-ich graflar orqali ulanadi. Har bir composable o'zining animatsiya, deep links va argument sozlamalariga ega bo'lishi mumkin.
Marshrut argumentlari composable() da arguments: List<NamedNavArgument> parametri orqali aniqlanadi. Har bir argument navArgument(name) { type; defaultValue } orqali belgilanadi. NavType argument turini aniqlaydi: StringType, IntType, LongType, FloatType, BoolType, ParcelableType va ReferenceType.
| Marshrut parametri | Route namunasi | NavType |
|---|---|---|
| Yo'l (path) | "user/{id}" | NavType.IntType |
| So'rov (query) | "search?q={query}" | NavType.StringType |
| Ixtiyoriy | "details/{id}?tab={tab}" | StringType + defaultValue="" |
| Parcelable | "checkout/{order}" | NavType.ParcelableType |
Argumentlar NavBackStackEntry dan arguments?.getInt("id") orqali olinadi. Majburiy argumentlar uchun defaultValue qoldirilishi mumkin — NavType null dan foydalanadi. Ixtiyoriy argumentlar uchun defaultValue majburiydir, aks holda parametr yo'qligida navigatsiya istisno tashlaydi.
Navigation 2.8.0 versiyasidan Type-Safe Navigation tavsiya etiladi: Kotlin Serialization bilan marshrutlar uchun sealed class yoki data class aniqlang. String route o'rniga composable<RouteType> { backStackEntry -> } dan foydalaning. Bu route-dagi xatolarni bartaraf qiladi va argumentlar uchun NavType-ni avtomatik yaratadi. Migratsiya uchun navigation-compose-typesafe bog'liqligini va Kotlin Serialization plaginini qo'shing.
nested graphs — navigation(route, startDestination) funksiyasi orqali NavHost ichida marshrutlarni guruhlash mexanizmi. Ichma-ich grafning o'z route prefiksi va startDestination-i bor, barcha marshrutlari prefiks orqali mavjud. nested graphs modulli arxitektura uchun ishlatiladi, bunda har bir feature moduli o'z pastki grafini ro'yxatdan o'tkazadi.
Ichma-ich graflarning afzalliklari: marshrutlarning modul ichida izolyatsiyasi, ekranlar guruhi uchun yagona back stack, ichki tuzilmani oshkor qilmasdan prefiks bo'yicha navigatsiya imkoniyati. Masalan, "auth" grafi "auth/login" va "auth/register" marshrutlarini o'z ichiga oladi. Navigatsiya ham to'liq marshrut bo'ylab, ham startDestination-ga yo'naltirish bilan prefiks bo'ylab mumkin.
NavHost(navController = navController, startDestination = "main") {
composable("main") { MainScreen(navController) }
navigation(
route = "auth",
startDestination = "auth/login"
) {
composable("auth/login") { LoginScreen(navController) }
composable("auth/register") { RegisterScreen(navController) }
}
}
nested graphs argumentlarni graf darajasida uzatishni qo'llab-quvvatlaydi: grafning route-da e'lon qilingan parametrlar barcha ichki marshrutlarga uzatiladi. Ichma-ich grafni tozalash uchun popBackStack(route) dan foydalaning — barcha ichki yozuvlarni o'chiradi. Ichma-ich graflar chuqurlik chegarasiga ega emas, ammo o'qish qulayligi uchun 3 darajadan ko'p bo'lmasligi tavsiya etiladi.
NavHost composable marshrutlar o'rtasidagi o'tish animatsiyasini enterTransition, exitTransition, popEnterTransition va popExitTransition parametrlari orqali qo'llab-quvvatlaydi. Animatsiyalar bir marta NavHost uchun belgilanadi va barcha marshrutlarga qo'llaniladi yoki har bir composable uchun individual tarzda. Odatiy holda animatsiya o'chirilgan.
Oddiy konfiguratsiya: enterTransition = slideInHorizontally(initialOffsetX = { it }) — ekran o'ngdan kiradi; exitTransition = slideOutHorizontally(targetOffsetX = { -it }) — ekran chapga chiqadi. Pop-animatsiya uchun yo'nalishlar oynali: ekran chapdan kiradi va o'ngga chiqadi. BottomNavigation uchun slidesiz fadeIn/fadeOut ishlatiladi.
NavHost(
navController = navController,
startDestination = "home",
enterTransition = { slideInHorizontally(initialOffsetX = { it }) + fadeIn() },
exitTransition = { slideOutHorizontally(targetOffsetX = { -it }) + fadeOut() },
popEnterTransition = { slideInHorizontally(initialOffsetX = { -it }) + fadeIn() },
popExitTransition = { slideOutHorizontally(targetOffsetX = { it }) + fadeOut() }
) { /* composable routes */ }
Maxsus animatsiyalar Compose Animation API orqali yaratiladi: AnimatedContentTransitionScope konteyner o'lchamlariga, animatsiya jarayoniga va direction-ga kirishni ta'minlaydi. Shared element transition uchun (bir element boshqa ekranga silliq o'tishi) Accompanist Navigation Animation kutubxonasi yoki sharedElement Modifier orqali maxsus implementatsiya talab qilinadi. Android Developers (2025) ma'lumotlariga ko'ra, standart slide animatsiyasi (o'ngdan kirish, chapga chiqish) navigatsiyaga ega Android ilovalarining 80 foizida qo'llaniladi.
Tez-tez so'raladigan savollar
Texnik jihatdan ha, ammo tavsiya etilmaydi. Har bir NavHost mustaqil back stack yaratadi, bu yagona navigatsiyani buzadi. Istisno — alohida hududlar, masalan, asosiy tarkib uchun NavHost va o'z navigatsiyasiga ega BottomSheet uchun NavHost.
NavHost — ekranlarni almashtiruvchi navigatsiya konteyneri. Scaffold — butun sahifaning layouti (TopAppBar, BottomNavigation, FloatingActionButton). Odatda NavHost Scaffold.content ichida joylashtiriladi. Scaffold navigatsiyani boshqarmaydi, faqat UI komponentlari uchun slotlar ta'minlaydi.
ViewModel NavBackStackEntry doirasida viewModel() orqali yaratiladi. ViewModel-ni ekranlar o'rtasida ulashish uchun parentNavController-dan foydalaning: umumiy ViewModel-ni ota-ona entry-ga bog'lang. Alternativ — NavGraph scope-i bilan DI (Hilt/Koin).
Bu normal xatti-harakat — NavHost marshrutdan chiqishda composable-ni kompozitsiyadan olib tashlaydi. Holatni saqlash uchun UI holati uchun rememberSaveable va biznes mantiqi uchun SavedStateHandle bilan ViewModel dan foydalaning.
Oxirgi marshrutni composable("404") qo'shing va noma'lum deep link bo'lganda unga navigatsiya qiling. NavHost-da catch-all marshrut mavjud emas — navigate() dan oldin Deep Link intent handler-da marshrutni tekshiring. Route topilmasa — 404-ga navigate qiling.
Xulosa
Biz kalit topshirig'i bilan mobil ilovani ishlab chiqamiz
IT Sectr 2017-yildan beri startaplar va korxonalar uchun iOS va Android ilovalarini yaratadi. Biz sizga maslahat beramiz va eng yaxshi yechimni taklif qilamiz.