No Android, um link direto é aquele que leva você diretamente a um destino específico em um app.
O componente de navegação permite criar dois tipos diferentes de links diretos: explícito e implícito.
Criar um link direto explícito
Um link direto explícito é uma instância única
de um link direto que usa uma PendingIntent
para direcionar os usuários a um local específico do app. Você pode mostrar um
link direto explícito como parte de uma notificação ou de um widget de app,
por exemplo.
Quando um usuário abre o app usando um link direto explícito, a backstack da tarefa é
limpa e substituída pelo destino do link direto. Ao
aninhar gráficos,
o destino inicial de cada nível de aninhamento, ou seja, o destino inicial
de cada elemento <navigation>
na hierarquia, também é adicionado à pilha.
Isso significa que, quando um usuário pressiona o botão "Voltar" em um destino de
link direto, ele navega pela pilha de navegação como se tivesse entrado
no app a partir do ponto de entrada.
Você pode usar a classe NavDeepLinkBuilder
para construir uma PendingIntent
,
como mostrado no exemplo abaixo. Se o contexto fornecido não for uma
Activity
, o construtor usará
PackageManager.getLaunchIntentForPackage()
como a atividade padrão para iniciar, se disponível.
Kotlin
val pendingIntent = NavDeepLinkBuilder(context) .setGraph(R.navigation.nav_graph) .setDestination(R.id.android) .setArguments(args) .createPendingIntent()
Java
PendingIntent pendingIntent = new NavDeepLinkBuilder(context) .setGraph(R.navigation.nav_graph) .setDestination(R.id.android) .setArguments(args) .createPendingIntent();
Por padrão, o NavDeepLinkBuilder
inicia seu link direto explícito para o
lançamento padrão da Activity
declarada no manifesto do app. Se
o NavHost
estiver em outra atividade, especifique o nome do componente
ao criar o builder de links diretos:
Kotlin
val pendingIntent = NavDeepLinkBuilder(context) .setGraph(R.navigation.nav_graph) .setDestination(R.id.android) .setArguments(args) .setComponentName(DestinationActivity::class.java) .createPendingIntent()
Java
PendingIntent pendingIntent = new NavDeepLinkBuilder(context) .setGraph(R.navigation.nav_graph) .setDestination(R.id.android) .setArguments(args) .setComponentName(DestinationActivity.class) .createPendingIntent();
Se você tiver um ComponentName
,
poderá transmiti-lo diretamente para o builder:
Kotlin
val componentName = ... val pendingIntent = NavDeepLinkBuilder(context) .setGraph(R.navigation.nav_graph) .setDestination(R.id.android) .setArguments(args) .setComponentName(componentName) .createPendingIntent()
Java
ComponentName componentName = ...; PendingIntent pendingIntent = new NavDeepLinkBuilder(context) .setGraph(R.navigation.nav_graph) .setDestination(R.id.android) .setArguments(args) .setComponentName(componentName) .createPendingIntent();
Se você já tiver um NavController
,
também será possível criar um link direto usando
NavController.createDeepLink()
.
Criar um link direto implícito
Um link direto implícito é uma referência a um destino específico em um app. Quando o link direto é invocado, por exemplo, quando um usuário clica em um link, o Android pode abrir o app no destino correspondente.
Os links diretos podem ser correspondidos por URI, ações de intent e tipos MIME. É possível especificar vários tipos de correspondência para um único link direto, mas a correspondência de argumentos de URI é priorizada, seguida pela de ações e, em seguida, pela de tipos MIME.
Veja um exemplo de link direto que contém um URI, uma ação e um tipo MIME:
<fragment android:id="@+id/a"
android:name="com.example.myapplication.FragmentA"
tools:layout="@layout/a">
<deepLink app:uri="www.example.com"
app:action="android.intent.action.MY_ACTION"
app:mimeType="type/subtype"/>
</fragment>
Você pode usar o Navigation Editor para criar um link direto implícito para um destino, desta forma:
- Na guia Design do Navigation Editor, selecione o destino do link direto.
- Clique em + na seção Deep Links do painel Attributes.
Na caixa de diálogo Add Deep Link exibida, insira as informações do link direto.
Observe o seguinte:
- Os URIs sem um esquema são considerados HTTP ou HTTPS. Por exemplo,
www.google.com
corresponde ahttp://www.google.com
ehttps://www.google.com
. - Os marcadores de parâmetros de caminho na forma de
{placeholder_name}
correspondem a um ou mais caracteres. Por exemplo,http://www.example.com/users/{id}
corresponde ahttp://www.example.com/users/4
. O componente de navegação tenta analisar os valores dos marcadores nos tipos apropriados, combinando nomes dos marcadores com os argumentos definidos para o destino do link direto. Se nenhum argumento for definido com o mesmo nome, um tipoString
padrão será usado como valor do argumento. Você pode usar o caractere curinga * para criar correspondência com 0 ou mais caracteres. - Os marcadores de parâmetros de consulta podem ser usados em vez de ou em conjunto com
parâmetros de caminho. Por exemplo,
http://www.example.com/users/{id}?myarg={myarg}
corresponde ahttp://www.example.com/users/4?myarg=28
. - Os marcadores de parâmetros de consulta para variáveis definidas com valores padrão ou
anuláveis não precisam ser correspondentes. Por exemplo,
http://www.example.com/users/{id}?arg1={arg1}&arg2={arg2}
corresponde ahttp://www.example.com/users/4?arg2=28
ouhttp://www.example.com/users/4?arg1=7
. Esse não é o caso com parâmetros de caminho. Por exemplo,http://www.example.com/users?arg1=7&arg2=28
não corresponde ao padrão acima porque o parâmetro de caminho necessário não é fornecido. - Os parâmetros de consulta irrelevantes não afetam a correspondência de URI de link direto. Por
exemplo,
http://www.example.com/users/{id}
corresponde ahttp://www.example.com/users/4?extraneousParam=7
, mesmo queextraneousParam
não esteja definido no padrão de URI.
- Os URIs sem um esquema são considerados HTTP ou HTTPS. Por exemplo,
Opcional: selecione Auto Verify para exigir que o Google verifique se você é o proprietário do URI. Para ver mais informações, consulte Verificar links de apps para Android.
Clique em Adicionar. Um ícone de link aparece acima do destino selecionado para indicar que o destino tem um link direto.
Clique na guia Code para alternar para a visualização XML. Um elemento
<deepLink>
aninhado foi adicionado ao destino:<deepLink app:uri="https://www.google.com" />
Para ativar o link direto implícito, você também precisa fazer adições ao arquivo
manifest.xml
do app. Adicione um único elemento <nav-graph>
a uma atividade que
aponta para um gráfico de navegação existente, como mostrado no exemplo abaixo:
<?xml version="1.0" encoding="utf-8"?> <manifest xmlns:android="http://schemas.android.com/apk/res/android" package="com.example.myapplication"> <application ... > <activity name=".MainActivity" ...> ... <nav-graph android:value="@navigation/nav_graph" /> ... </activity> </application> </manifest>
Ao criar seu projeto, o componente de navegação substitui o elemento <nav-graph>
por elementos <intent-filter>
gerados para corresponder a todos os links diretos
no gráfico de navegação.
Ao acionar um link direto implícito, o estado da backstack depende de a
Intent
implícita ter sido ou não inicializada pela
sinalização
Intent.FLAG_ACTIVITY_NEW_TASK
:
- Se a sinalização estiver configurada, a backstack da tarefa vai ser limpa e substituída pelo
destino do link direto. Assim como no caso do link direto explícito, ao
aninhar gráficos,
o destino inicial de cada nível de aninhamento, ou seja, o destino inicial
de cada elemento
<navigation>
na hierarquia, também é adicionado à pilha. Isso significa que quando um usuário pressiona o botão "Voltar" em um destino de link direto, ele navega pela pilha de navegação como se tivesse entrado no app a partir do ponto de entrada. - Se a sinalização não estiver configurada, você vai permanecer na pilha de tarefas do app anterior, em que o link direto implícito foi acionado. Nesse caso, o botão "Voltar" levará você de volta ao app anterior, enquanto o botão "Para cima" iniciará a tarefa do app no destino pai hierárquico no gráfico de navegação.
Como processar links diretos
É altamente recomendável usar sempre o
launchMode
padrão de standard
ao usar o componente de navegação. Ao usar o modo de inicialização standard
, o componente de navegação
processa automaticamente os links diretos chamando
handleDeepLink()
para processar qualquer link direto explícito ou implícito na Intent
. No entanto,
isso não acontecerá automaticamente se a Activity
for reutilizada ao usar
um launchMode
alternativo, como singleTop
. Nesse caso, é necessário
chamar handleDeepLink()
manualmente em onNewIntent()
, conforme mostrado no
exemplo a seguir:
Kotlin
override fun onNewIntent(intent: Intent?) { super.onNewIntent(intent) navController.handleDeepLink(intent) }
Java
@Override protected void onNewIntent(Intent intent) { super.onNewIntent(intent); navController.handleDeepLink(intent); }
Outros recursos
Para saber mais sobre a navegação, consulte os recursos a seguir.
Codelabs
Vídeos
- Android Jetpack: gerenciar a navegação da IU com o Navigation Controller (Google I/O 2018) (vídeo em inglês)