Gezinme bileşeni, Kotlin tabanlı alana özgü bir dil sağlar veya
Kotlin'in type-safe parametresini temel alan DSL
inşaatçılar
, Bu API, grafiğinizi bildirerek oluşturmak yerine Kotlin kodunuzda oluşturmanıza olanak tanır
daha kolay olur. Bu, uygulamanızın özel bir kitle oluşturmak
gezinmeyi kolaylaştırır. Örneğin, uygulamanız bir
harici bir web hizmetinden gezinme yapılandırmasını
dinamik olarak bir gezinme grafiği oluşturmak için
onCreate()
işlevi.
Bağımlılıklar
Kotlin DSL'yi Parçalarla birlikte kullanmak için aşağıdaki bağımlılığı uygulamanızın
build.gradle
dosyası:
Groovy
dependencies { def nav_version = "2.8.4" api "androidx.navigation:navigation-fragment-ktx:$nav_version" }
Kotlin
dependencies { val nav_version = "2.8.4" api("androidx.navigation:navigation-fragment-ktx:$nav_version") }
Grafik oluşturma
Burada, Google Ads kurallarından yola çıkarak hazırlanan Sunflower
uygulamasında gösterilir. Bunun için
Örneğin, iki hedefimiz var: home
ve plant_detail
. home
Hedef, kullanıcı uygulamayı ilk kez başlattığında mevcuttur. Bu hedef
kullanıcının bahçesindeki bitkilerin bir listesini görüntüler. Kullanıcı
bitkiler olduğunda uygulama plant_detail
hedefine gidiyor.
Şekil 1'de bu hedefler,
Uygulamanın kullandığı plant_detail
hedef ve bir işlem (to_plant_detail
)
home
- plant_detail
arası rotayı izleyin.
Kotlin DSL Nav Grafiği Barındırma
Uygulamanızın gezinme grafiğini oluşturabilmek için öncelikle
grafiğe dönüştürülebilir. Bu örnekte parçalar kullanıldığı için, grafiği
NavHostFragment
bir
FragmentContainerView
:
<!-- activity_garden.xml -->
<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">
<androidx.fragment.app.FragmentContainerView
android:id="@+id/nav_host"
android:name="androidx.navigation.fragment.NavHostFragment"
android:layout_width="match_parent"
android:layout_height="match_parent"
app:defaultNavHost="true" />
</FrameLayout>
Bu örnekte app:navGraph
özelliğinin ayarlanmadığına dikkat edin. Grafik
bir kaynak olarak tanımlanmadığından
res/navigation
klasörü olduğundan onCreate()
öğesinin bir parçası olarak ayarlanması gerekir
bu etkinliği takip etmeniz gerekir.
XML'de, bir işlem hedef kimliğini bir veya daha fazla bağımsız değişkenle birbirine bağlar. Ancak, Navigasyon DSL'sini kullanırken bir rota, yol gösterir. Yani DSL'yi kullanırken işlem kavramı yoktur.
Bir sonraki adım, işletme hedefinizi tanımlarken kullanacağınız rotaları grafiğe dönüştürülebilir.
Grafiğiniz için rota oluşturun
XML tabanlı gezinme grafikleri, bir üründen diğerine
adımına geçelim. Her id
için sayısal bir sabit sayı oluşturulur
özelliğinin değeri. Derleme zamanında oluşturulan bu statik kimlikler
Böylece, Gezinme DSL'sini kullanmak için çalışma zamanında gezinme grafiğinizi oluştururken kullanabilirsiniz.
serialize edilebilir
türler yerine
Kimlikler. Her rota, benzersiz bir türle temsil edilir.
Bağımsız değişkenlerle çalışırken, bunlar rotaya eklenir türü ekleyin. Bu şekilde güvenli yazın. kullanabilirsiniz.
@Serializable data object Home
@Serializable data class Plant(val id: String)
NavGraphBuilder DSL ile grafik oluşturma
Güzergahlarınızı tanımladıktan sonra, gezinme grafiğini oluşturabilirsiniz.
val navController = findNavController(R.id.nav_host_fragment)
navController.graph = navController.createGraph(
startDestination = Home
) {
fragment<HomeFragment, Home> {
label = resources.getString(R.string.home_title)
}
fragment<PlantDetailFragment, PlantDetail> {
label = resources.getString(R.string.plant_detail_title)
}
}
Bu örnekte, iki parçalı hedef
fragment()
DSL oluşturucu işlevi. Bu işlev, iki tür gerektirir
bağımsız değişkenler
,
Önce bir Fragment
sınıfı
API'yi kullanabilirsiniz. Bunu ayarlamak
tanımlanmış parça hedeflerde android:name
özelliğini ayarlayarak
anlamına gelir.
İkincisi, rota. Bu, Any
tarihinden itibaren seri hale getirilebilir bir tür olmalıdır. Google
bu hedef tarafından kullanılacak gezinme bağımsız değişkenlerini içermelidir.
ve türlerini inceleyelim.
İşlev ayrıca, ve özel öğeler için yerleşik oluşturucu işlevlerinin yanı sıra argümanlar ve derin bağlantılar.
Kotlin DSL grafiğinizle gezinme
Son olarak, home
konumundan plant_detail
konumuna gitmek için şu dosyayı kullanabilirsiniz:
NavController.navigate()
şunu arar:
private fun navigateToPlant(plantId: String) {
findNavController().navigate(route = PlantDetail(id = plantId))
}
PlantDetailFragment
işlevinde,
geçerli
NavBackStackEntry
ve sesli arama yapıyorum
toRoute
çift tıklayın.
val plantDetailRoute = findNavController().getBackStackEntry<PlantDetail>().toRoute<PlantDetail>()
val plantId = plantDetailRoute.id
PlantDetailFragment
, ViewModel
kullanıyorsa rota örneğini şunu kullanarak alın:
SavedStateHandle.toRoute
.
val plantDetailRoute = savedStateHandle.toRoute<PlantDetail>()
val plantId = plantDetailRoute.id
Bu kılavuzun geri kalanında, yaygın olarak kullanılan gezinme grafiği öğeleri, hedefler, bunları nasıl kullanacağınızı öğreneceksiniz.
Hedefler
Kotlin DSL, üç hedef türü için yerleşik destek sağlar:
Her biri kendine ait olan Fragment
, Activity
ve NavGraph
hedefleri
oluşturmak ve yapılandırmak için kullanılabilen satır içi uzantı işlevi
seçeceğiz.
Parça hedefleri
İlgili içeriği oluşturmak için kullanılan
fragment()
DSL işlevi, kullanıcı arayüzünün parça sınıfı ve
bu hedefi benzersiz şekilde tanımlamak için kullanılan rota türü ve ardından bir lambda
Burada açıklandığı gibi ek yapılandırma sağlayabileceğiniz yöntem
Kotlin DSL grafiğiniz bölümünde görünür.
fragment<MyFragment, MyRoute> {
label = getString(R.string.fragment_title)
// custom argument types, deepLinks
}
Aktivite hedefi
İlgili içeriği oluşturmak için kullanılan
activity()
DSL işlevi, rota için bir tür parametresi alır ancak
tüm etkinlik sınıflarını içerir. Bunun yerine, anahtar kelimeler için isteğe bağlı bir activityClass
bir lambda var. Bu esneklik sayesinde etkinlik hedefi tanımlayabilirsiniz.
dolaylı bir istek kullanılarak başlatılması gereken
intent değeri kullanıldığında açıkça
daha anlaşılır hale gelemez. Parça hedeflerde olduğu gibi,
Etiket, özel bağımsız değişkenler ve derin bağlantılar yapılandırabilirsiniz.
activity<MyRoute> {
label = getString(R.string.activity_title)
// custom argument types, deepLinks...
activityClass = MyActivity::class
}
Navigasyon grafiğinin hedefi
İlgili içeriği oluşturmak için kullanılan
navigation()
DSL işlevi, iç içe yerleştirilmiş bir gezinme oluşturmak için kullanılabilir
grafiği'ne dokunun. Bu işlev bir tür alır
parametresini kullanabilirsiniz. Ayrıca iki bağımsız değişken gerekir:
grafiğin başlangıç hedefinin rotası ve ileri doğru giden bir lambda
Grafiği yapılandırın. Geçerli öğeler arasında diğer hedefler, özel bağımsız değişken yer alır
derin bağlantılar ve bu sayfa için açıklayıcı bir etiket
hedef.
Bu etiket, aşağıdakileri kullanarak gezinme grafiğini kullanıcı arayüzü bileşenlerine bağlamak için yararlı olabilir:
NavigationUI
.
@Serializable data object HomeGraph
@Serializable data object Home
navigation<HomeGraph>(startDestination = Home) {
// label, other destinations, deep links
}
Özel hedefleri destekleme
Yeni bir hedef türü kullanıyorsanız
doğrudan Kotlin DSL'yi desteklemeyense bu hedefleri
kullanarak Kotlin DSL'nizi
addDestination()
:
// The NavigatorProvider is retrieved from the NavController
val customDestination = navigatorProvider[CustomNavigator::class].createDestination().apply {
route = Graph.CustomDestination.route
}
addDestination(customDestination)
Alternatif olarak, tekli artı operatörünü yeni bir oluşturulan hedefi grafiğe doğrudan ekleyin:
// The NavigatorProvider is retrieved from the NavController
+navigatorProvider[CustomNavigator::class].createDestination().apply {
route = Graph.CustomDestination.route
}
Hedef bağımsız değişkenleri sağlama
Hedef bağımsız değişkenleri, rota sınıfının bir parçası olarak tanımlanabilir. Bunlar, herhangi bir Kotlin sınıfı için belirtilen şekilde tanımlanabilir. Gerekli bağımsız değişkenler boş değerli olmayan türler olarak tanımlanır ve isteğe bağlı bağımsız değişkenler varsayılan olarak tanımlanır değerler.
Rotaları ve bunların bağımsız değişkenlerini göstermek için kullanılan temel mekanizma dizedir.
kullanır. Rotaları modellemek için dize kullanmak, gezinme durumunun depolanmasını ve
yapılandırma sırasında diskten geri yüklendi
sistem tarafından başlatılan ve işlem
ölüm ile ilişkilendirilebilir. İşte bu nedenle
Her gezinme bağımsız değişkeni serileştirilebilir olmalıdır; yani,
bağımsız değişken değerinin bellek içi gösterimini
String
Kotlin serileştirmesi
eklenti
Google Analytics 4'teki temel alan
anahtar kelimeler
@Serializable
ek açıklaması bir nesneye eklendi.
@Serializable
data class MyRoute(
val id: String,
val myList: List<Int>,
val optionalArg: String? = null
)
fragment<MyFragment, MyRoute>
Özel türler sağlama
Özel bağımsız değişken türleri için özel bir NavType
sınıfı sağlamanız gerekir. Bu
, türünüzün bir rotadan veya derin bağlantıdan tam olarak nasıl ayrıştırıldığını kontrol etmenize olanak tanır.
Örneğin, bir arama ekranını tanımlamak için kullanılan bir rota, şu özelliklere sahip bir sınıfı içerebilir: şu arama parametrelerini temsil eder:
@Serializable
data class SearchRoute(val parameters: SearchParameters)
@Serializable
data class SearchParameters(
val searchQuery: String,
val filters: List<String>
)
Özel NavType
şöyle yazılabilir:
val SearchParametersType = object : NavType<SearchParameters>(
isNullableAllowed = false
) {
override fun put(bundle: Bundle, key: String, value: SearchParameters) {
bundle.putParcelable(key, value)
}
override fun get(bundle: Bundle, key: String): SearchParameters {
return bundle.getParcelable(key) as SearchParameters
}
override fun serializeAsValue(value: SearchParameters): String {
// Serialized values must always be Uri encoded
return Uri.encode(Json.encodeToString(value))
}
override fun parseValue(value: String): SearchParameters {
// Navigation takes care of decoding the string
// before passing it to parseValue()
return Json.decodeFromString<SearchParameters>(value)
}
}
Bu, daha sonra Kotlin DSL'nizde diğer türler gibi kullanılabilir:
fragment<SearchFragment, SearchRoute> {
label = getString(R.string.plant_search_title)
typeMap = mapOf(typeOf<SearchParameters>() to SearchParametersType)
}
Hedefe giderken rotanızın bir örneğini oluşturun:
val params = SearchParameters("rose", listOf("available"))
navController.navigate(route = SearchRoute(params))
Parametre, hedefteki rotadan edinilebilir:
val searchRoute = navController().getBackStackEntry<SearchRoute>().toRoute<SearchRoute>()
val params = searchRoute.parameters
Derin bağlantılar
Derin bağlantılar, XML ile desteklenen herhangi bir hedefe eklenebilir. gezinme grafiğidir. Derin bağlantı oluşturma bölümünde belirtilen prosedürlerin tümü sürece uygulanır. bir derin bağlantı oluşturmayı öğreneceksiniz.
Dolaylı derin bağlantı oluştururken
ancak o zaman hangisi için analiz edilebilecek bir XML gezinme kaynağınız yoksa
<deepLink>
öğeleri. Bu nedenle, <nav-graph>
öğesi; AndroidManifest.xml
dosyanıza intent
filtreler ekleyebilirsiniz. Amaç
sağladığınız filtrenin temel yolu, işlemi ve mime türüyle
uygulamanızın derin bağlantılarını kullanın.
Derin bağlantılar, bir hedefe, içindeki deepLink
işlevi çağırılarak eklenir
lambda var. Rotayı parametreleştirilmiş bir tür olarak kabul eder ve
basePath
parametresini kullanın.
Ayrıca,
deepLinkBuilder
lambda var.
Aşağıdaki örnek, Home
hedefi için bir derin bağlantı URI'si oluşturmaktadır.
@Serializable data object Home
fragment<HomeFragment, Home>{
deepLink<Home>(basePath = "www.example.com/home"){
// Optionally, specify the action and/or mime type that this destination
// supports
action = "android.intent.action.MY_ACTION"
mimeType = "image/*"
}
}
URI biçimi
Derin bağlantı URI'si biçimi, rotanın alanlarından otomatik olarak oluşturulur kullanarak aşağıdaki kuralları kullanabilirsiniz:
- Gerekli parametreler yol parametreleri olarak eklenmiştir (örnek:
/{id}
) - Varsayılan değere sahip parametreler (isteğe bağlı parametreler) query olarak eklenir
parametreleri (örnek:
?name={name}
) - Koleksiyonlar sorgu parametreleri olarak eklenir (örnek:
?items={value1}&items={value2}
) - Parametrelerin sırası, rotadaki alanların sıralamasıyla eşleşir
Örneğin, şu rota türü:
@Serializable data class PlantDetail(
val id: String,
val name: String,
val colors: List<String>,
val latinName: String? = null,
)
şu şekilde oluşturulmuş bir URI biçimine sahiptir:
basePath/{id}/{name}/?colors={color1}&colors={color2}&latinName={latinName}
Ekleyebileceğiniz derin bağlantı sayısıyla ilgili bir sınır yoktur. Her aradığınızda
deepLink()
o hedef için tutulan listeye yeni bir derin bağlantı eklenir.
Sınırlamalar
Güvenli Bağımsız Değişkenler eklentisi
Kotlin DSL ile uyumlu değildir. Bunun nedeni, eklentinin
Directions
ve Arguments
sınıflarını oluşturabilirsiniz.