提供彈性的小工具版面配置

本頁說明調整小工具大小和增加彈性的方式 Android 12 (API 級別 31) 中導入的功能。其中也詳細說明瞭 決定小工具的大小

針對小工具大小和版面配置使用改良的 API

從 Android 12 (API 級別 31) 開始,您可以提供更多精細的大小 屬性和彈性版面配置, 以下部分:

  1. 指定其他小工具大小限制。

  2. 提供回應式版面配置精確配置 版面配置。

在先前的 Android 版本中 小工具 OPTION_APPWIDGET_MIN_WIDTHOPTION_APPWIDGET_MIN_HEIGHT, OPTION_APPWIDGET_MAX_WIDTH, 和 OPTION_APPWIDGET_MAX_HEIGHT ,然後預估小工具的大小,但該邏輯並非完全有效 情境。針對指定 Android 12 以上版本的小工具,我們建議 提供回應式完全比對 版面配置

指定其他小工具大小限制

Android 12 新增了 API,可確保小工具 在不同大小的螢幕上,不同尺寸都能更穩定可靠。

除了現有 minWidth 之外, minHeight, minResizeWidth, 和 minResizeHeight 屬性,請使用以下新 appwidget-provider 屬性:

以下 XML 說明如何使用尺寸屬性。

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

提供回應式版面配置

如果版面配置需要根據小工具大小變更,建議您 建立一組小型的版面配置,每組都可用於不同尺寸的版面。如果這是 另一種方法是,另一個方法是根據確切的小工具 資源大小,如本頁所述。

這項功能讓資源調度更順暢,整體系統也更加優異 因為系統不必每次都喚醒應用程式 會以不同大小顯示小工具

以下程式碼範例顯示如何提供版面配置清單。

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);
}

假設小工具包含下列屬性:

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

上述程式碼片段代表:

  • smallView 支援 160 dp (minResizeWidth) × 110 dp (minResizeHeight) 至 160dp × 199dp (下一個截止點 - 1dp)。
  • tallView 支援 160 × 200 dp 到 214 dp (下一個截止點 - 1) × 200 dp。
  • wideView 支援從 215 dp × 110 dp (minResizeHeight) 到 250 dp (maxResizeWidth) × 200 dp (maxResizeHeight)。

小工具必須支援 minResizeWidth × 以上的大小範圍 minResizeHeightmaxResizeWidth × maxResizeHeight。在該範圍內 您可以決定要切換版面配置的截止點。

回應式版面配置範例
圖 1 回應式版面配置範例。

提供確切的版面配置

如果一部分的回應式版面配置無法使用,您可以改為提供 針對顯示小工具的大小,設計不同的版面配置。這是 手機通常有兩種尺寸 (直向和橫向模式) 和四種尺寸 折疊式裝置

如要實作這項解決方案,應用程式必須執行下列步驟:

  1. 超載 AppWidgetProvider.onAppWidgetOptionsChanged(), 系統會在大小組合變更時呼叫此方法

  2. 呼叫 AppWidgetManager.getAppWidgetOptions()。 ,會傳回包含大小的 Bundle

  3. Bundle 存取 AppWidgetManager.OPTION_APPWIDGET_SIZES 金鑰。

,瞭解如何調查及移除這項存取權。

以下程式碼範例說明如何提供確切的版面配置。

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) { }

決定小工具的大小

每個小工具都必須為裝置定義 targetCellWidthtargetCellHeight 搭載 Android 12 以上版本 或 minWidthminHeight (適用於所有使用者) 指出應用程式會使用的最低空間量 根據預設。不過,當使用者將小工具新增到主畫面時 的事件播放次數超過您指定的最小寬度和高度。

Android 主畫面提供一個可用空間格狀,方便使用者瀏覽 放置小工具和圖示。這個網格會因裝置而異:例如 手機可提供 5x4 的格狀版面,而平板電腦則可呈現更大的格狀版面。使用小工具時 並延伸至佔用的儲存格數量下限。 以水平和垂直方向,滿足對 在執行中的裝置上,targetCellWidthtargetCellHeight Android 12 以上版本,或搭載 minWidthminHeight 的限制 搭載 Android 11 (API 級別 30) 以下版本的裝置。

儲存格的寬度和高度,以及套用的自動邊界大小 提供的小工具會因裝置而異請使用下表粗略估算 一般 5x4 網格手機的最小尺寸 您要使用的格線儲存格數量:

儲存格數量 (寬 x 高) 直向模式下的可用大小 (dp) 橫向模式的可用大小 (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 公尺 (73n - 16) x (118 公尺 - 16) (142n - 15) x (66 公尺 - 15)

使用直向模式的儲存格大小,填入您提供的值。 minWidthminResizeWidthmaxResizeWidth 屬性。同樣地 以橫向模式儲存格大小 指出您提供的值 定義 minHeightminResizeHeightmaxResizeHeight 屬性。

這是因為在直向模式下,儲存格的寬度通常會比較小 與橫向模式相同 - 同樣地,儲存格高度通常 。

舉例來說,如果您希望將小工具寬度縮小成單一儲存格, Google Pixel 4 必須將 minResizeWidth 的高度設定設為 56dp。 確保 minResizeWidth 屬性的值較小 ,因為直向儲存格的寬度至少達到 57dp。 同樣地,如果您希望小工具高度可在 相同裝置,您需要將 minResizeHeight 設為最多 50dp minResizeHeight 屬性的值小於 51 dp:因為在橫向模式中,一個儲存格的高度至少為 51dp。

您可以調整每個小工具的大小範圍 minResizeWidth/minResizeHeightmaxResizeWidth/maxResizeHeight 屬性,因此需要配合兩個屬性之間的任何大小範圍進行調整。

舉例來說,如要為刊登位置設定刊登位置的預設尺寸,您可以 設定下列屬性:

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

這表示小工具的預設大小為 3x2 儲存格,如 targetCellWidthtargetCellHeight 屬性—或 180×110 dp,如 由 minWidthminHeight 為執行中的裝置指定 Android 11 以下版本。如果是後者,儲存格中的大小 會因裝置而異。

此外,如要設定支援的小工具大小範圍,可以設定下列 屬性:

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

如上述屬性所指定,小工具的寬度會 可調整大小的範圍為 180 dp 到 530 dp,高度可調整至 110 dp 到 450 dp。 接著,這個小工具可以從 3x2 到 5x2 的儲存格調整大小,但前提是: 條件存在:

  • 裝置採用 5x4 格線。
  • 儲存格數量與可用大小之間的對應 (以 dp 為單位) 遵循下表,其中列出 維度
  • 小工具會根據該尺寸範圍自動調整。

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);

假設小工具採用上述定義的回應式版面配置 程式碼片段。也就是說,指定的 R.layout.widget_weather_forecast_small 使用範圍為 180 dp (minResizeWidth) x 110 dp (minResizeHeight) 到 269x279 dp (下一個截斷點 - 1)。同樣地 R.layout.widget_weather_forecast_medium 使用從 270x110 dp 到 270x279dp, 而 R.layout.widget_weather_forecast_large 則使用 270x280 dp 530 dp (maxResizeWidth) x 450 dp (maxResizeHeight)。

當使用者調整小工具大小時,圖示的外觀會隨之變更, 儲存格,如以下範例所示。

最小 3x2 格狀空間的天氣小工具範例。UI 顯示
            位置名稱 (東京)、溫度 (14°),以及表示位置的符號
            天氣局部多雲。
圖 2. 3x2 R.layout.widget_weather_forecast_small

4x2「Medium」中的「天氣」小工具範例大小調整小工具大小
            這樣就能以先前小工具大小的所有 UI 為基礎
            並加上並提供
            下午 4 點到晚上 7 點。
圖 3 4x2 R.layout.widget_weather_forecast_medium

5x2「Medium」中的天氣小工具範例大小調整小工具大小
            這種方式產生的 UI 會與先前的大小一致,但
            拉長一個儲存格長度,以佔用更多水平空間。
圖 4.5 x 2 R.layout.widget_weather_forecast_medium

5x3「大」中的天氣小工具範例大小調整小工具大小
            這樣就能以先前小工具大小的所有 UI 為基礎
            並在小工具內加入包含天氣預報資料的檢視畫面
            每週二和週三表示晴天或雨天的符號
            以及每天的高低溫
圖 5 5x3 R.layout.widget_weather_forecast_large

5x4 大尺寸的天氣小工具範例大小調整小工具大小
            這樣就能以先前小工具大小的所有 UI 為基礎
            並加上週四和週五 (及其對應的符號)
            指出天氣類型,以及高低溫
            每日費用)。
圖 6.5 x 4 R.layout.widget_weather_forecast_large