メタデータを使用してアプリを構成する

Navigation 3 では、メタデータを使用して、NavEntrySceneNavDisplay などのさまざまなライブラリ コンポーネント間で任意の情報を共有します。メタデータは、最も基本的なレベルでは Map<String, Any> です。ただし、このライブラリは、メタデータの読み取りと書き込みをよりシンプルで型安全にするための追加の抽象化を提供します

NavEntry メタデータを提供する

アプリが NavEntry インスタンスを直接ビルドする場合は、metadata コンストラクタ パラメータを使用してエントリのメタデータを提供します。

when (key) {
    is Home -> NavEntry(key, metadata = mapOf("key" to "value")) {}
}

アプリで entryProvider DSL を使用する場合は、entry 関数の metadata パラメータを使用してメタデータを提供します。この関数には 2 つのオーバーロードがあります。1 つはマップを直接受け取るもの、もう 1 つはエントリのキーを引数として渡すラムダを受け取るものです。

entry<Home>(metadata = mapOf("key" to "value")) { /* ... */ }
entry<Conversation>(metadata = { key: Conversation ->
    mapOf("key" to "value: ${key.id})")
}) { /* ... */ }

Scene メタデータを提供する

デフォルトでは、Scene.metadata は、entries プロパティの最後のエントリの metadata を返すカスタム ゲッターを使用します。null の場合は空のマップを返します。Scene インターフェースを実装する際に、必要に応じてこのデフォルトの動作をオーバーライドできます。

メタデータ DSL を使用する

ライブラリの 1.1.0-beta01 リリースで導入されたメタデータドメイン固有言語(DSL)は、メタデータの保存に使用される Map<String, Any> を作成するためのタイプセーフ ビルダーを提供します。

メタデータキーを定義する

DSL は、NavMetadataKey インターフェースを使用して、メタデータキーに関連付けられた値の型の一貫性を維持します。

メタデータキーを定義する際の慣例は、それらのキーに関連付けられた値を読み取るクラス(関数やコンポーザブルの場合は関連オブジェクト)のネストされたオブジェクトとして含めることです。

// For classes such as scene strategies or nav entry decorators, you can define the keys
// as nested object.
class MySceneStrategy<T : Any> : SceneStrategy<T> {

    // ...

    object MyStringMetadataKey : NavMetadataKey<String>
}

// An example from NavDisplay.
// Because NavDisplay is a function, the metadata keys are defined in an object with the same name.
public object NavDisplay {

    public object TransitionKey :
        NavMetadataKey<AnimatedContentTransitionScope<Scene<*>>.() -> ContentTransform>
}

DSL を使用してメタデータを構築する

メタデータ マップを作成するには、ラムダ パラメータを受け取る metadata 関数を使用します。このラムダ内で、put 関数を使用して、NavMetadataKey と対応する値を使用してマップにエントリを追加します。

entry<Home>(
    metadata = metadata {
        put(NavDisplay.TransitionKey) { fadeIn() togetherWith fadeOut() }
        // An additional benefit of the metadata DSL is the ability to use conditional logic
        if (condition) {
            put(MySceneStrategy.MyStringMetadataKey, "Hello, world!")
        }
    }
) {
    // ...
}

メタデータキーを使用してメタデータを読み取る

メタデータ DSL には、NavMetadataKey を使用してメタデータの読み取りを簡素化する関数も用意されています。

// import androidx.navigation3.runtime.contains
// import androidx.navigation3.runtime.get

val hasMyString: Boolean = metadata.contains(MySceneStrategy.MyStringMetadataKey)
val myString: String? = metadata[MySceneStrategy.MyStringMetadataKey]