Navegação circular

Um exemplo claro de necessidade de retorno a um destino é a navegação circular. Este documento descreve esse caso de uso.

Cenário

Digamos que seu app tenha três destinos: A, B e C. Ele também tem ações que levam de A a B, de B a C e de C de volta para A. O gráfico dessa navegação é exibido da seguinte maneira:

uma demonstração de navegação circular
Figura 1. Um gráfico de navegação circular com três destinos: A, B e C.

Com cada ação de navegação, o NavController adiciona o novo destino à backstack. Assim, navegar repetidamente pelo fluxo no diagrama faria com que a backstack tivesse vários conjuntos de cada destino: A, B, C, A, B, C, A, B, C.

Solução

Para evitar repetições na backstack, especifique popUpTo() e inclusive na chamada para NavController.navigate() ou na ação de navegação.

Considere um caso em que, depois de chegar ao destino C, a backstack tem uma instância de cada destino: A, B, C. É necessário definir popUpTo() e inclusive na ação ou chamada para navigate(), que leva o usuário do destino C para o destino A.

Nesse caso, quando o usuário navega do destino C de volta ao destino A, NavController também aparece como A. Isso significa que ele remove B e C da pilha. Com inclusive = true, ele também exibe o primeiro A, limpando a pilha de forma eficaz.

Implementação no Compose

Confira a seguir a implementação da solução para popUpTo() circular no Compose:

// When creating your `NavGraph` in your `NavHost`.
composable("c") {
    DestinationC(
        onNavigateToA = {
          navController.navigate("a") {
            popUpTo("a") {
              inclusive = true
            }
          }
        },
    )
}

Implementação no Views

Confira a seguir a implementação da solução para popUpTo circular no Views:

<fragment
    android:id="@+id/c"
    android:name="com.example.myapplication.C"
    android:label="fragment_c"
    tools:layout="@layout/fragment_c">

    <action
        android:id="@+id/action_c_to_a"
        app:destination="@id/a"
        app:popUpTo="@+id/a"
        app:popUpToInclusive="true"/>
</fragment>