Dynamische Updates in Kacheln anzeigen

Ab Version 1.2 von Kacheln können Sie Plattformdaten-Updates mit dynamischen Ausdrücken streamen. Anschließend können Sie diese Aktualisierungen mit Animationen in Ihren Kacheln verknüpfen. Ihre App erhält jede Sekunde Updates für diesen Wert.

Wenn Sie dynamische Ausdrücke verwenden, müssen Sie die gesamte Kachel nicht aktualisieren, wenn sich ihr Inhalt ändert. Um die Nutzerinteraktion mit Ihren Kacheln zu steigern, sollten Sie dynamische Objekte animieren.

Dynamische Ausdrücke mit Datenquellen verknüpfen

Die Namespaces androidx.wear.protolayout und androidx.wear.protolayout.material enthalten viele Klassen, deren Felder dynamische Ausdrücke akzeptieren. Hier einige Beispiele:

Wenn Sie einen dynamischen Ausdruck als möglichen Wert für ein Element in Ihrer Kachel verwenden möchten, verwenden Sie den entsprechenden dynamischen Property-Typ *Prop des Elements und übergeben Sie die Datenquelle an die Methode setDynamicValue() der Builder-Klasse des dynamischen Property-Typs.

Kacheln unterstützen die folgenden dynamischen Attributtypen:

Wenn Sie einen dynamischen Ausdruck verwenden, der sich auf physische Dimensionen auswirkt (jeder Wert in einem Kachel, außer Farbe), müssen Sie auch eine Reihe von zugehörigen Einschränkungen angeben, z. B. ein Stringformat. Mithilfe dieser Einschränkungen kann der System-Renderer den maximalen Platz bestimmen, den ein Wert in Ihrer Kachel einnehmen kann. Normalerweise geben Sie diese Einschränkungen auf Elementebene und nicht auf Ebene des dynamischen Ausdrucks an, indem Sie eine Methode aufrufen, die mit setLayoutConstraintsForDynamic* beginnt.

Das folgende Code-Snippet zeigt, wie Aktualisierungen der Herzfrequenz mit drei Ziffern und dem Fallback-Wert -- angezeigt werden:

override fun onTileRequest(requestParams: RequestBuilders.TileRequest) =
    Futures.immediateFuture(
        Tile.Builder()
            .setResourcesVersion(RESOURCES_VERSION)
            .setFreshnessIntervalMillis(60 * 60 * 1000) // 60 minutes
            .setTileTimeline(
                Timeline.fromLayoutElement(
                    Text.Builder(
                        this,
                        TypeBuilders.StringProp.Builder("--")
                            .setDynamicValue(
                                PlatformHealthSources.heartRateBpm()
                                    .format()
                                    .concat(DynamicBuilders.DynamicString.constant(" bpm"))
                            )
                            .build(),
                        TypeBuilders.StringLayoutConstraint.Builder("000").build(),
                    )
                        .build()
                )
            )
            .build()
    )

Wenige Ausdrücke in einer Kachel verwenden

Wear OS begrenzt die Anzahl der Ausdrücke, die eine einzelne Kachel haben kann. Wenn eine Kachel zu viele dynamische Gesamtausdrücke enthält, werden dynamische Werte ignoriert und das System greift auf die statischen Werte zurück, die Sie für die jeweiligen dynamischen Attributtypen angeben.

Dynamische Daten in einem Statusobjekt zusammenführen

Sie können die neuesten Updates aus Datenquellen in einem state zusammenfassen, den Sie zum Rendern von Werten an Ihre Kachel übergeben.

So verwenden Sie Statusinformationen in Ihren Kacheln:

  1. Legen Sie eine Reihe von Schlüsseln fest, die die verschiedenen Werte des Status Ihrer Kachel darstellen. In diesem Beispiel werden Schlüssel für die Wasseraufnahme und eine qqq-Anmerkung erstellt:

    companion object {
        val KEY_WATER_INTAKE = intAppDataKey("key_water_intake")
        val KEY_NOTE = stringAppDataKey("key_note")
    }

  2. Rufen Sie in Ihrer Implementierung von onTileRequest() setState() auf und stellen Sie die anfänglichen Zuordnungen von jedem Schlüssel zu einem bestimmten dynamischen Datenwert her:

    override fun onTileRequest(
        requestParams: RequestBuilders.TileRequest
    ): ListenableFuture<Tile?> {
        // If the tile hasn't had any state set yet, use the default values
        val state =
            if (requestParams.currentState.keyToValueMapping.isNotEmpty())
                requestParams.currentState
            else
                StateBuilders.State.Builder()
                    .setStateMap(
                        dynamicDataMapOf(
                            KEY_WATER_INTAKE mapTo 200,
                            KEY_NOTE mapTo "Good"
                        )
                    )
                    .build()
    
        return Futures.immediateFuture(
            Tile.Builder()
                // Set resources, timeline, and other tile properties.
                .setState(state)
                .build()
        )
    }

  3. Wenn Sie Ihr Layout erstellen, verwenden Sie an der Stelle, an der Sie diese Daten aus dem Status anzeigen möchten, ein Objekt vom Typ Dynamic*. Sie können auch animate() aufrufen, um eine Animation vom vorherigen zum aktuellen Wert zu zeigen:

    val waterIntakeValue =
        DynamicBuilders.DynamicInt32.from(KEY_WATER_INTAKE)

  4. Bei Bedarf können Sie den Status auch mit neuen Werten aktualisieren. Das kann Teil des LoadAction einer Kachel sein.

    In diesem Beispiel wird der Wert für die Wasseraufnahme auf 400 aktualisiert:

    val loadAction =
        loadAction(
            dynamicDataMapOf(
                KEY_WATER_INTAKE mapTo 400,
                KEY_NOTE mapTo "Outstanding"
            )
        )