Komponent Nawigacja zapewnia prosty i ogólny sposób nawigacji do miejsca docelowego. Ten interfejs obsługuje różne konteksty i struktury UI. Komponentu Nawigacja możesz np. używać z funkcjami tworzenia, widoków, fragmentów, działań, a nawet niestandardowych platform interfejsu użytkownika.
W tym przewodniku opisujemy, jak korzystać z komponentu Nawigacja, aby przechodzić do konkretnych miejsc w różnych kontekstach.
Użyj kontrolera nawigacji
Typ klucza używany do przechodzenia między miejscami docelowymi to NavController
.
Więcej informacji o klasie i sposobie tworzenia jej instancji znajdziesz w artykule Tworzenie kontrolera nawigacji. Z tego przewodnika dowiesz się, jak go używać.
Nawiguj
Niezależnie od używanej platformy UI do przechodzenia do miejsca docelowego możesz używać jednej funkcji: NavController.navigate()
.
navigate()
oferuje wiele przeciążeń. Ilość przeciążenia, którą musisz wybrać,
odpowiada dokładnie Twojej sytuacji. Jedno przeciążenie powinno być używane na przykład podczas przechodzenia do funkcji kompozycyjnej, a drugiego podczas przechodzenia do widoku.
W sekcjach poniżej opisujemy niektóre z najważniejszych przeciążeń (navigate()
), których możesz używać.
Przechodzenie do funkcji kompozycyjnej
Aby przejść do funkcji kompozycyjnej, użyj NavController.navigate<T>
.
Przy tym przeciążeniu navigate()
przyjmuje pojedynczy argument route
, dla którego przekazujesz typ. Pełni funkcję klucza do miejsca docelowego.
@Serializable
object FriendsList
navController.navigate(route = FriendsList)
Aby przejść do funkcji kompozycyjnej na wykresie nawigacyjnym, najpierw zdefiniuj właściwość NavGraph
w taki sposób, aby każde miejsce docelowe odpowiadało jednemu typowi. W przypadku elementów kompozycyjnych robi się to za pomocą funkcji composable()
.
Udostępnianie zdarzeń z funkcji kompozycyjnych
Gdy funkcja kompozycyjna musi przejść do nowego ekranu, nie przekazuj jej odwołania do obiektu NavController
, aby mogła wywoływać metodę navigate()
bezpośrednio.
Zgodnie z zasadami jednokierunkowego przepływu danych (UDF) funkcja kompozycyjna powinna zamiast tego ujawniać zdarzenie obsługiwane przez NavController
.
Mówiąc bardziej bezpośrednio, funkcja kompozycyjna powinna mieć parametr typu () -> Unit
.
Gdy dodajesz miejsca docelowe do elementu NavHost
za pomocą funkcji composable()
, przekaż wywołanie funkcji kompozycyjnej do NavController.navigate()
.
Przykład znajdziesz w podsekcji poniżej.
Przykład
Aby zademonstrować poprzednie sekcje, zapoznaj się z tymi punktami w tym fragmencie:
- Każde miejsce docelowe na wykresie jest tworzone za pomocą trasy, która jest serializowalnym obiektem lub klasą opisującą dane wymagane przez to miejsce docelowe.
- Funkcja kompozycyjna
MyAppNavHost
zawiera instancjęNavController
. - W związku z tym wywołania funkcji
navigate()
powinny występować tam, a nie w niższej funkcji kompozycyjnej, takiej jakProfileScreen
. ProfileScreen
zawiera przycisk, który po kliknięciu przenosi użytkownika do stronyFriendsList
. Nie wywołuje jednak samej funkcjinavigate()
.- Zamiast tego przycisk wywołuje funkcję, która jest widoczna jako parametr
onNavigateToFriends
. - Gdy
MyAppNavHost
dodaje parametrProfileScreen
do wykresu nawigacyjnego, dla elementuonNavigateToFriends
przekazuje lambda, która wywołujenavigate(route = FriendsList
. - Dzięki temu, gdy użytkownik kliknie przycisk
ProfileScreen
, przejdzie prawidłowo do interfejsuFriendsListScreen
.
@Serializable
object Profile
@Serializable
object FriendsList
@Composable
fun MyAppNavHost(
modifier: Modifier = Modifier,
navController: NavHostController = rememberNavController(),
) {
NavHost(
modifier = modifier,
navController = navController,
startDestination = Profile
) {
composable<Profile> {
ProfileScreen(
onNavigateToFriends = { navController.navigate(route = FriendsList) },
/*...*/
)
}
composable<FriendsList> { FriendsListScreen(/*...*/) }
}
}
@Composable
fun ProfileScreen(
onNavigateToFriends: () -> Unit,
/*...*/
) {
/*...*/
Button(onClick = onNavigateToFriends) {
Text(text = "See friends list")
}
}
Nawiguj za pomocą identyfikatora liczby całkowitej
Aby przejść do miejsca docelowego przy użyciu identyfikatora liczby całkowitej, wywołaj przeciążenie navigate(int)
. Wykorzystuje identyfikator zasobu działania lub miejsca docelowego. Ten fragment kodu pokazuje, jak możesz wykorzystać to przeciążenie, aby przejść do sekcji ViewTransactionsFragment
:
Kotlin
viewTransactionsButton.setOnClickListener { view ->
view.findNavController().navigate(R.id.viewTransactionsAction)
}
Java
viewTransactionsButton.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
Navigation.findNavController(view).navigate(R.id.viewTransactionsAction);
}
});
Podczas poruszania się za pomocą identyfikatorów w miarę możliwości korzystaj z działań. Działania dostarczają dodatkowych informacji na wykresie nawigacyjnym, wizualnie pokazując, jak miejsca docelowe są ze sobą powiązane.
Nawigacja za pomocą żądania NavDeepLinkRequest
Aby przejść do miejsca docelowego precyzyjnego linku, użyj przeciążenia navigate(NavDeepLinkRequest)
. Poniższy fragment kodu zawiera implementację tej metody:
Kotlin
val request = NavDeepLinkRequest.Builder
.fromUri("android-app://androidx.navigation.app/profile".toUri())
.build()
findNavController().navigate(request)
Java
NavDeepLinkRequest request = NavDeepLinkRequest.Builder
.fromUri(Uri.parse("android-app://androidx.navigation.app/profile"))
.build()
NavHostFragment.findNavController(this).navigate(request)
W przeciwieństwie do nawigacji na podstawie identyfikatorów działań lub miejsc docelowych, możesz przejść do dowolnego precyzyjnego linku na wykresie, niezależnie od tego, czy miejsce docelowe jest widoczne. Możesz przechodzić do miejsca docelowego na bieżącym wykresie lub do miejsca docelowego na zupełnie innym wykresie.
Działania i typy MIME
Oprócz Uri
NavDeepLinkRequest
obsługuje też precyzyjne linki z działaniami i typami MIME. Aby dodać działanie do prośby, użyj kodu fromAction()
lub setAction()
. Aby dodać typ MIME do żądania, użyj kodu fromMimeType()
lub setMimeType()
.
Aby element NavDeepLinkRequest
prawidłowo pasował do miejsca docelowego niejawnego precyzyjnego linku, identyfikator URI, działanie i typ MIME muszą być zgodne z elementem NavDeepLink
w miejscu docelowym. Identyfikatory URI muszą pasować do wzorca, działania muszą być dokładnie dopasowane, a typy MIME muszą być ze sobą powiązane. Na przykład image/jpg
pasuje do image/\*
Dalsze konteksty
W tym dokumencie opisujemy, jak używać NavController.navigate()
w najczęściej używanych przypadkach użycia. Funkcja ta cechuje się jednak szeregiem przeciążeń, których można używać w różnych kontekstach i w połączeniu z dowolną platformą UI. Więcej informacji o tych przeciążeniach znajdziesz w dokumentacji referencyjnej.
Więcej materiałów
Więcej informacji znajdziesz na tych stronach:
- Tworzenie kontrolera nawigacji
- Nawigacja i stos wsteczny
- Poruszanie się po opcjach
- Bezpieczeństwo pisania w Kotlin DSL i nawigacji w celu tworzenia wiadomości