Flexible Widget-Layouts bereitstellen

Auf dieser Seite werden Optimierungen der Widget-Größe und größere Flexibilität beschrieben. in Android 12 (API-Level 31) eingeführt. Außerdem wird beschrieben, wie Sie eine Größe für Ihr Widget bestimmen.

Verbesserte APIs für Widget-Größen und -Layouts verwenden

Ab Android 12 (API-Level 31) können Sie detailliertere Größenangaben machen Attribute und flexible Layouts. Gehen Sie dazu wie in den folgenden Abschnitten:

  1. Geben Sie zusätzliche Größenbeschränkungen für das Widget an.

  2. Die Bereitstellung von responsiven Layouts oder genauen Layouts.

In früheren Android-Versionen ist es möglich, die Größenbereiche eines mithilfe des OPTION_APPWIDGET_MIN_WIDTH, OPTION_APPWIDGET_MIN_HEIGHT, OPTION_APPWIDGET_MAX_WIDTH, und OPTION_APPWIDGET_MAX_HEIGHT und dann die Größe des Widgets abschätzen, aber diese Logik funktioniert nicht in allen Situationen. Für Widgets, die auf Android 12 oder höher ausgerichtet sind, empfehlen wir responsive oder genaue Layouts.

Zusätzliche Größenbeschränkungen für Widgets angeben

Unter Android 12 werden APIs hinzugefügt, mit denen du prüfen kannst, ob dein Widget zuverlässiger auf verschiedenen Geräten mit unterschiedlichen Bildschirmgrößen.

Zusätzlich zum vorhandenen minWidth minHeight, minResizeWidth, und minResizeHeight Attribute verwenden, verwenden Sie die folgenden neuen appwidget-provider-Attribute:

  • targetCellWidth und targetCellHeight: Definieren Sie die Zielgröße des Widgets in Bezug auf Zellen im Launcher-Raster. Wenn definiert sind, werden diese Attribute anstelle von minWidth oder minHeight verwendet.

  • maxResizeWidth und maxResizeHeight: definieren Sie die maximale Größe, auf die der Launcher die Größe des Widgets ändern kann.

Der folgende XML-Code zeigt, wie die Größenattribute verwendet werden.

<appwidget-provider
  ...
  android:targetCellWidth="3"
  android:targetCellHeight="2"
  android:maxResizeWidth="250dp"
  android:maxResizeHeight="110dp">
</appwidget-provider>

Responsive Layouts bereitstellen

Wenn das Layout je nach Größe des Widgets geändert werden muss, empfehlen wir, Erstellen eines kleinen Satzes von Layouts, die jeweils für eine Reihe von Größen gültig sind. Wenn dieses nicht möglich ist, besteht eine andere Möglichkeit darin, Layouts basierend auf dem genauen Widget zur Laufzeit, wie auf dieser Seite beschrieben.

Diese Funktion ermöglicht eine reibungslosere Skalierung und ein insgesamt besseres System da das System die App nicht jedes Mal neu aktivieren muss, wird das Widget in einer anderen Größe angezeigt.

Das folgende Codebeispiel zeigt, wie Sie eine Liste von Layouts bereitstellen.

Kotlin

override fun onUpdate(...) {
    val smallView = ...
    val tallView = ...
    val wideView = ...

    val viewMapping: Map<SizeF, RemoteViews> = mapOf(
            SizeF(150f, 100f) to smallView,
            SizeF(150f, 200f) to tallView,
            SizeF(215f, 100f) to wideView
    )
    val remoteViews = RemoteViews(viewMapping)

    appWidgetManager.updateAppWidget(id, remoteViews)
}

Java

@Override
public void onUpdate(...) {
    RemoteViews smallView = ...;
    RemoteViews tallView = ...;
    RemoteViews wideView = ...;

    Map<SizeF, RemoteViews> viewMapping = new ArrayMap<>();
    viewMapping.put(new SizeF(150f, 100f), smallView);
    viewMapping.put(new SizeF(150f, 200f), tallView);
    viewMapping.put(new SizeF(215f, 100f), wideView);
    RemoteViews remoteViews = new RemoteViews(viewMapping);

    appWidgetManager.updateAppWidget(id, remoteViews);
}

Angenommen, das Widget hat die folgenden Attribute:

<appwidget-provider
    android:minResizeWidth="160dp"
    android:minResizeHeight="110dp"
    android:maxResizeWidth="250dp"
    android:maxResizeHeight="200dp">
</appwidget-provider>

Das obige Code-Snippet bedeutet Folgendes:

  • smallView unterstützt ab 160 dp (minResizeWidth) × 110 dp (minResizeHeight) bis 160 dp × 199 dp (nächste Begrenzung – 1 dp).
  • tallView unterstützt 160 dp × 200 dp bis 214 dp (nächste Begrenzung – 1) × 200dp.
  • wideView unterstützt 215 dp × 110 dp (minResizeHeight) bis 250 dp (maxResizeWidth) × 200dp (maxResizeHeight).

Dein Widget muss folgende Größen unterstützen: minResizeWidth × minResizeHeight bis maxResizeWidth × maxResizeHeight. Innerhalb dieses Bereichs können Sie festlegen, wann das Layout gewechselt werden soll.

<ph type="x-smartling-placeholder">
</ph> Beispiel für ein responsives Layout
Abbildung 1. Beispiel für ein responsives Layout.

Genaue Layouts bereitstellen

Wenn eine kleine Anzahl responsiver Layouts nicht möglich ist, können Sie stattdessen verschiedene Layouts, die auf die Größen zugeschnitten sind, in denen das Widget angezeigt wird. Dies ist normalerweise zwei Größen für Smartphones (Hoch- und Querformat) und vier Größen für faltbare Geräte.

Zur Implementierung dieser Lösung muss Ihre Anwendung die folgenden Schritte ausführen:

  1. Überlastung AppWidgetProvider.onAppWidgetOptionsChanged(), Er wird aufgerufen, wenn sich der Satz von Größen ändert.

  2. Rufen Sie uns unter AppWidgetManager.getAppWidgetOptions() an. Dadurch wird ein Bundle zurückgegeben, das die Größen enthält.

  3. Greifen Sie über Bundle auf den Schlüssel AppWidgetManager.OPTION_APPWIDGET_SIZES zu.

Das folgende Codebeispiel zeigt, wie exakte Layouts bereitgestellt werden.

Kotlin

override fun onAppWidgetOptionsChanged(
        context: Context,
        appWidgetManager: AppWidgetManager,
        id: Int,
        newOptions: Bundle?
) {
    super.onAppWidgetOptionsChanged(context, appWidgetManager, id, newOptions)
    // Get the new sizes.
    val sizes = newOptions?.getParcelableArrayList<SizeF>(
            AppWidgetManager.OPTION_APPWIDGET_SIZES
    )
    // Check that the list of sizes is provided by the launcher.
    if (sizes.isNullOrEmpty()) {
        return
    }
    // Map the sizes to the RemoteViews that you want.
    val remoteViews = RemoteViews(sizes.associateWith(::createRemoteViews))
    appWidgetManager.updateAppWidget(id, remoteViews)
}

// Create the RemoteViews for the given size.
private fun createRemoteViews(size: SizeF): RemoteViews { }

Java

@Override
public void onAppWidgetOptionsChanged(
    Context context, AppWidgetManager appWidgetManager, int appWidgetId, Bundle newOptions) {
    super.onAppWidgetOptionsChanged(context, appWidgetManager, appWidgetId, newOptions);
    // Get the new sizes.
    ArrayList<SizeF> sizes =
        newOptions.getParcelableArrayList(AppWidgetManager.OPTION_APPWIDGET_SIZES);
    // Check that the list of sizes is provided by the launcher.
    if (sizes == null || sizes.isEmpty()) {
      return;
    }
    // Map the sizes to the RemoteViews that you want.
    Map<SizeF, RemoteViews> viewMapping = new ArrayMap<>();
    for (SizeF size : sizes) {
        viewMapping.put(size, createRemoteViews(size));
    }
    RemoteViews remoteViews = new RemoteViews(viewMapping);
    appWidgetManager.updateAppWidget(id, remoteViews);
}

// Create the RemoteViews for the given size.
private RemoteViews createRemoteViews(SizeF size) { }

Größe für das Widget festlegen

Für jedes Widget muss eine targetCellWidth und ein targetCellHeight für Geräte definiert sein mit Android 12 oder höher – oder minWidth und minHeight für alle Android-Versionen und gibt an, wie viel Speicherplatz mindestens verbraucht wird. ist standardmäßig aktiviert. Wenn Nutzende jedoch ein Widget zu ihrem Startbildschirm hinzufügen, die angegebene Mindestbreite und -höhe überschreitet.

Android-Startbildschirme bieten Nutzenden ein Raster mit verfügbaren Bereichen, auf denen sie Widgets und Symbole zu platzieren. Dieses Raster kann je nach Gerät variieren. zum Beispiel viele Mobiltelefone haben ein 5x4-Raster und Tablets können ein größeres Raster bieten. Wenn Ihr Widget wird er so gestreckt, dass er die Mindestanzahl an Zellen belegt, horizontal und vertikal angeordnet sein, um die Einschränkungen targetCellWidth und targetCellHeight auf aktiven Geräten Android 12 oder höher oder Einschränkungen für minWidth und minHeight bei Geräte mit Android 11 (API-Level 30) oder niedriger

Sowohl die Breite und Höhe einer Zelle als auch die Größe der automatisch angewendeten Ränder kann je nach Gerät variieren. Verwenden Sie die folgende Tabelle für eine grobe Schätzung. eines typischen 5x4-Raster-Handsets unter Berücksichtigung der Anzahl der gewünschten belegten Rasterzellen:

Anzahl der Zellen (Breite x Höhe) Verfügbare Größe im Hochformat (dp) Verfügbare Größe im Querformat (dp)
1x1 57x102dp 127x51dp
2x1 130x102dp 269x51dp
3x1 203x102dp 412x51dp
4x1 276x102dp 554x51dp
5x1 349x102dp 697x51dp
5x2 349x220dp 697x117dp
5x3 349x337dp 697x184dp
5x4 349x455dp 697x250dp
n x m (73n–16) x (118m–16) (142n–15) x (66m–15)

Verwenden Sie die Zellengrößen im Hochformat, um die Werte anzugeben, die Sie für die Attribute minWidth, minResizeWidth und maxResizeWidth. In ähnlicher Weise verwenden Sie die Zellgrößen im Querformat, um die von Ihnen bereitgestellten Werte für die Attribute minHeight, minResizeHeight und maxResizeHeight.

Der Grund dafür ist, dass die Zellenbreite im Hochformat in der Regel kleiner ist. als im Querformat. Die Zellenhöhe im Querformat kleiner als im Hochformat.

Wenn Sie z. B. möchten, dass die Breite des Widgets auf einer Zelle Google Pixel 4 hast, musst du minResizeWidth auf höchstens 56 dp einstellen. um sicherzustellen, dass der Wert für das Attribut minResizeWidth kleiner ist als 57 dp, da eine Zelle im Hochformat mindestens 57 dp breit ist. Wenn Sie möchten, dass die Größe des Widgets in einer Zelle im Gerät verwendet haben, müssen Sie minResizeHeight auf höchstens 50 dp einstellen, der Wert für das Attribut minResizeHeight ist kleiner als 51 dp, da eine Zelle im Querformat mindestens 51 dp hoch ist.

Die Größe jedes Widgets kann innerhalb der Größenbereiche zwischen den minResizeWidth/minResizeHeight und maxResizeWidth/maxResizeHeight -Attributen und muss daher an alle Größenbereiche zwischen ihnen angepasst werden.

Um beispielsweise die Standardgröße des Widgets für die Platzierung festzulegen, können Sie Legen Sie die folgenden Attribute fest:

<appwidget-provider
    android:targetCellWidth="3"
    android:targetCellHeight="2"
    android:minWidth="180dp"
    android:minHeight="110dp">
</appwidget-provider>

Dies bedeutet, dass die Standardgröße des Widgets 3 x 2 Zellen beträgt, wie durch den Attribute targetCellWidth und targetCellHeight – oder 180 × 110 dp, wie angegeben durch minWidth und minHeight für Geräte, die ausgeführt werden Android 11 oder niedriger Im letzteren Fall kann die Größe in Zellen variieren je nach Gerät.

Um die unterstützten Größenbereiche Ihres Widgets festzulegen, können Sie außerdem Folgendes festlegen: Attribute:

<appwidget-provider
    android:minResizeWidth="180dp"
    android:minResizeHeight="110dp"
    android:maxResizeWidth="530dp"
    android:maxResizeHeight="450dp">
</appwidget-provider>

Wie durch die vorhergehenden Attribute angegeben, ist die Breite des Widgets Die Größe kann von 180 dp bis 530 dp und die Höhe von 110 dp bis 450 dp angepasst werden. Die Größe des Widgets kann dann von 3 x 2 in 5 x 2 Zellen geändert werden, solange Folgendes zutrifft: Bedingungen vorhanden sind:

  • Das Gerät hat das 5x4-Raster.
  • Zuordnung zwischen der Anzahl der Zellen und der verfügbaren Größe in dps entspricht der Tabelle mit der Schätzung des Minimums auf dieser Seite.
  • Das Widget passt sich an diesen Größenbereich an.

Kotlin

val smallView = RemoteViews(context.packageName, R.layout.widget_weather_forecast_small)
val mediumView = RemoteViews(context.packageName, R.layout.widget_weather_forecast_medium)
val largeView = RemoteViews(context.packageName, R.layout.widget_weather_forecast_large)

val viewMapping: Map<SizeF, RemoteViews> = mapOf(
        SizeF(180f, 110f) to smallView,
        SizeF(270f, 110f) to mediumView,
        SizeF(270f, 280f) to largeView
)

appWidgetManager.updateAppWidget(appWidgetId, RemoteViews(viewMapping))

Java

RemoteViews smallView = 
    new RemoteViews(context.getPackageName(), R.layout.widget_weather_forecast_small);
RemoteViews mediumView = 
    new RemoteViews(context.getPackageName(), R.layout.widget_weather_forecast_medium);
RemoteViews largeView = 
    new RemoteViews(context.getPackageName(), R.layout.widget_weather_forecast_large);

Map<SizeF, RemoteViews> viewMapping = new ArrayMap<>();
viewMapping.put(new SizeF(180f, 110f), smallView);
viewMapping.put(new SizeF(270f, 110f), mediumView);
viewMapping.put(new SizeF(270f, 280f), largeView);
RemoteViews remoteViews = new RemoteViews(viewMapping);

appWidgetManager.updateAppWidget(id, remoteViews);

Angenommen, das Widget verwendet die in den vorherigen Code-Snippets. Das bedeutet, dass das als R.layout.widget_weather_forecast_small wird von 180 dp (minResizeWidth) × verwendet 110 dp (minResizeHeight) bis 269 x 279 dp (nächste Begrenzung – 1). In ähnlicher Weise R.layout.widget_weather_forecast_medium wird von 270 × 110 dp bis 270 × 279 dp verwendet, und R.layout.widget_weather_forecast_large von 270 x 280 dp bis 530dp (maxResizeWidth) x 450dp (maxResizeHeight).

Wenn der Nutzer die Größe des Widgets ändert, ändert sich sein Erscheinungsbild, um sich an die jeweilige Größe in wie in den folgenden Beispielen gezeigt.

<ph type="x-smartling-placeholder">
</ph> Beispiel für ein Wetter-Widget in der kleinsten 3x2-Rastergröße Die Benutzeroberfläche zeigt
            den Standortnamen (Tokio), die Temperatur (14 °) und das Symbol für
            teilweise bewölkt.
Abbildung 2. 3x2 R.layout.widget_weather_forecast_small.

<ph type="x-smartling-placeholder">
</ph> Beispiel für ein Wetter-Widget in der Größe 4 x 2 (M) Größe. Größe des Widgets ändern
            und baut auf der gesamten
Benutzeroberfläche der vorherigen Widget-Größe auf,
            mit dem Label
„Weitgehend bewölkt“ und eine Vorhersage der Temperaturen von
            16:00 bis 19:00 Uhr.
Abbildung 3. 4x2 R.layout.widget_weather_forecast_medium.

<ph type="x-smartling-placeholder">
</ph> Beispiel für ein Wetter-Widget in der Größe 5 x 2 in der Größe „M“ Größe. Größe des Widgets ändern
            Dies führt zur selben Benutzeroberfläche wie die vorherige Größe, nur dass sie
            um eine Zellenlänge gestreckt, um mehr horizontalen Platz zu belegen.
Abbildung 4. 5x2 R.layout.widget_weather_forecast_medium.

<ph type="x-smartling-placeholder">
</ph> Beispiel für ein Wetter-Widget im Format 5 x 3 in der Größe „Large“ Größe. Größe des Widgets ändern
            auf der Benutzeroberfläche
der vorherigen Widget-Größen
            und fügt dem Widget eine Ansicht mit einer Vorhersage des Wetters hinzu.
            am Dienstag und Mittwoch. Symbole, die auf sonniges oder regnerisches Wetter hinweisen
            sowie Höchst- und Tiefsttemperaturen für jeden Tag.
Abbildung 5. 5 × 3 R.layout.widget_weather_forecast_large.

<ph type="x-smartling-placeholder">
</ph> Beispiel für ein Wetter-Widget in der Größe 5 x 4 (Large) Größe. Größe des Widgets ändern
            auf der Benutzeroberfläche
der vorherigen Widget-Größen
            und fügt Donnerstag und Freitag sowie die entsprechenden Symbole
            die die Art des Wetters sowie Höchst- und Tiefsttemperaturen
            für jeden Tag).
Abbildung 6: 5x4 R.layout.widget_weather_forecast_large.