Navigationのexplicit deep link詳細

Kenji Abe
Aug 24, 2019

--

Photo by Daniel Kuruvilla on Unsplash

Navigationにはdeep linkという機能があります。

deep linkに二種類あって、一つはURIを指定するimplicit deep linkで、もう一つは直接遷移先を指定するexplicit deep linkです。

今回はexplicit deep linkについてです。ドキュメントでは少ししか記載されてないですが、色々使い方があります。

環境

  • Navigation 2.1.0-rc01

どういうときに使うのか

例えば、通知やWidgetからActivityを起動するときにNavigationにある特定のFragmentに遷移したい場合などに使います。

上のようなNavigationがあったとして、通知から起動する場合に最初からsecondのほうに遷移してほしいときには、explicit deep linkで行えます。

基本的な使い方

基本的な使い方としては上の通りです。細かいことは後述しますが、NavGraphのidと遷移先のidを指定して、 PendingIntent を作ってくれます。

この PendingIntent を通知など設定することで、通知をタップすると対象のActivityが起動すると同時に対象のFragmentへ遷移します。

引数は setArguments を使って渡すことができます。

createPendingIntent() ではなく、 createTaskStackBuilder() を使うことで TaskStackBuilder を作ることも可能です。

Activity

先程のコードを見ると、どこにもActivityが指定されていません。

どのActivityを起動するのかは NavDeepLinkBuilder のコンストラクタに渡すContextによります。
ContextがActivityの場合は、そのActivityが起動することになります。
ApplicationContextの場合は、 PackageManager.getLaunchIntentForPackage() が返すActivityになります。(アプリの起動Activityがほとんどです)

このようなContextによる指定の他に明示的に指定する方法もあります。

setComponentName にActivityクラスを渡すことでActivityを指定することが可能です。

NavGraphとDestination

NavDeepLinkBuilder に指定するNavGraphとDestinationは起動したいActivityでちゃんと指定されてる必要があります。ここが一致しない場合は、Fragmentの遷移が行われません。

また、指定したNavGraph内に該当のDestinationが無い場合はクラッシュします。

BackStackとNested Graph

explicit deep linkはNavGraphに設定されている startDestination のFragmentが必ずBackStackに積まれて、その次に指定したDestinationのFragmentが表示されることになります。

例えば、上のようなNavGraphがあった場合です。thirdを指定して起動した場合は、first -> thirdのようにBackStackが積まれます。

また、first -> second -> thirdのようにBackStackを設定したい場合は、Nested Graphを使用します。

Nested Graphを使うことで、その startDestination もBackStackに積まれることになります。

ActivityのStack

色々試したのですが、簡単に設定する方法が見つかりませんでした。Intentのflagの影響で挙動が変わってしまって、単純にはいかなさそうです。

もし、必要な場合は自分でActivityに引数を渡して自分で制御するほうがシンプルな気がします。

まとめ

deep linkといえばURIを使った方法がよく知られていますが(implicit deep link)、こういった遷移も可能になっています。

あまり込み入ったことをせずに単純に使うだけなら便利そうです。

--

--

Kenji Abe

Programmer / Gamer / Google Developers Expert for Android, Kotlin / @STAR_ZERO