在小工具挑選器中新增預覽畫面

如要改善應用程式的小工具挑選器體驗,請在 Android 15 以上版本的裝置上提供生成的小工具預覽畫面,在 Android 12 至 Android 14 裝置上提供縮放的小工具預覽畫面 (指定 previewLayout),並在舊版裝置上提供 previewImage。

您可以建立動態、個人化的生成小工具預覽畫面,準確反映小工具在使用者主畫面上的顯示方式。在 Android 15 以上版本中,系統會透過推送 API 提供預覽畫面,也就是說,應用程式可在生命週期中的任何時間點提供預覽畫面,不必接收來自小工具主機的明確要求。

詳情請參閱 YouTube 上的「使用最新即時資訊和微工具豐富應用程式」。

新增生成的預覽

如要在搭載 Android 15 以上版本的裝置上顯示產生的 Widget 預覽畫面,請先在模組 build.gradle 檔案中將 compileSdk 值設為 35 以上,以便將 RemoteViews 提供給 Widget 挑選器

應用程式可以使用 AppWidgetManager 中的 setWidgetPreview。為防止濫用及降低系統健康疑慮,setWidgetPreview 是有頻率限制的 API。預設限制約為每小時兩次呼叫。

系統不會提供回呼來顯示預覽畫面,因此應用程式必須決定何時呼叫 setWidgetPreviews。更新策略取決於小工具的用途:

  • 如果小工具含有靜態資訊或屬於快速操作,請在應用程式首次啟動時設定預覽畫面。
  • 應用程式有資料後,您就可以設定預覽畫面,例如在使用者登入或初始設定後。
  • 您可以設定定期工作,按照選定的頻率更新預覽畫面。

以下範例會載入 XML 小工具版面配置資源,並設為預覽畫面。compileSdk 建構設定必須為 35 以上,setWidgetPreview 才會顯示為這個程式碼片段中的方法。

AppWidgetManager.getInstance(appContext).setWidgetPreview(
    ComponentName(
        appContext,
        ExampleAppWidgetReceiver::class.java
    ),
    AppWidgetProviderInfo.WIDGET_CATEGORY_HOME_SCREEN,
    RemoteViews("com.example", R.layout.widget_preview)
)

新增可縮放的小工具預覽

從 Android 12 開始,小工具挑選器中顯示的小工具預覽畫面可調整大小。您需要提供 XML 版面配置,並設為小工具的預設大小。先前,小工具預覽畫面是靜態可繪製資源,在某些情況下,預覽畫面無法準確反映小工具新增至主畫面時的顯示方式。

如要實作可縮放的小工具預覽畫面,請改用 appwidget-provider 元素的 previewLayout 屬性提供 XML 版面配置:

<appwidget-provider
    android:previewLayout="@layout/my_widget_preview">
</appwidget-provider>

建議使用與實際小工具相同的版面配置,並採用實際的預設值或測試值。大多數應用程式會使用相同的 previewLayout 和 initialLayout。如需建立準確預覽版面配置的指引,請參閱「建構包含動態項目的準確預覽畫面」。

建議您同時指定 previewLayout 和 previewImage 屬性,這樣一來,如果使用者的裝置不支援 previewLayout,應用程式就能改用 previewImage。previewLayout 屬性的優先順序高於 previewImage 屬性。

新增靜態小工具預覽畫面,確保回溯相容性

如要讓 Android 11 (API 級別 30) 以下版本的小工具挑選器顯示小工具預覽畫面,或做為可調整預覽畫面的備用方案,請指定 previewImage 屬性。

如果您變更小工具的外觀,請更新預覽圖片。

如果您未使用 setWidgetPreview 設定,這個屬性也會做為生成預覽畫面的備用屬性。

建立包含動態項目的準確預覽畫面

圖 1: 小工具預覽畫面未顯示任何清單項目。

本節說明在具有集合檢視畫面的小工具預覽畫面中,顯示多個項目的建議做法,也就是使用 ListView、GridView 或 StackView 的小工具。這適用於可調整大小的小工具預覽畫面,而非產生的預覽畫面。

如果小工具使用其中一種檢視畫面,直接在 previewLayout 中提供實際的小工具版面配置,建立可調整大小的預覽畫面,可能會在小工具預覽畫面未顯示任何項目時降低體驗品質。這是因為集合檢視資料是在執行階段動態設定,看起來類似圖 1 所示的圖片。

如要讓含有集合檢視畫面的小工具預覽畫面在小工具挑選器中正確顯示,建議您另外維護一個專門用於預覽畫面的版面配置檔案。這個獨立版面配置檔案應包含以下內容:

  • 實際的小工具版面配置。
  • 含有假項目的預留位置集合檢視畫面。舉例來說,您可以提供含有多個假清單項目的預留位置 LinearLayout,藉此模擬 ListView。

如要說明 ListView 的範例,請先建立獨立的版面配置檔案:

// res/layout/widget_preview.xml

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
   android:layout_width="match_parent"
   android:layout_height="wrap_content"
   android:background="@drawable/widget_background"
   android:orientation="vertical">

    // Include the actual widget layout that contains ListView.
    <include
        layout="@layout/widget_view"
        android:layout_width="match_parent"
        android:layout_height="wrap_content" />

    // The number of fake items you include depends on the values you provide
    // for minHeight or targetCellHeight in the AppWidgetProviderInfo
    // definition.

    <TextView android:text="@string/fake_item1"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:layout_marginVertical="?attr/appWidgetInternalPadding" />

    <TextView android:text="@string/fake_item2"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:layout_marginVertical="?attr/appWidgetInternalPadding" />

</LinearLayout>

提供 AppWidgetProviderInfo 中繼資料的 previewLayout 屬性時,請指定預覽版面配置檔案。您仍須為 initialLayout 屬性指定實際的小工具版面配置,並在執行階段建構 RemoteViews 時使用實際的小工具版面配置。

<appwidget-provider
    previewLayout="@layout/widget_preview"
    initialLayout="@layout/widget_view" />

複雜清單項目

上一節的範例提供假清單項目,因為清單項目是 TextView 物件。如果項目是複雜的版面配置,提供假項目可能會更複雜。

假設清單項目定義在 widget_list_item.xml 中,且包含兩個 TextView 物件:

<LinearLayout  xmlns:android="http://schemas.android.com/apk/res/android"
        android:layout_width="match_parent"
        android:layout_height="wrap_content">

    <TextView android:id="@id/title"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:text="@string/fake_title" />

    <TextView android:id="@id/content"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:text="@string/fake_content" />
</LinearLayout>

如要提供假清單項目,您可以多次加入版面配置,但這會導致每個清單項目都相同。如要提供不重複的清單項目,請按照下列步驟操作:

  1. 為文字值建立一組屬性:

    <resources>
        <attr name="widgetTitle" format="string" />
        <attr name="widgetContent" format="string" />
    </resources>
    
  2. 使用下列屬性設定文字:

    <LinearLayout  xmlns:android="http://schemas.android.com/apk/res/android"
            android:layout_width="match_parent"
            android:layout_height="wrap_content">
    
        <TextView android:id="@id/title"
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:text="?widgetTitle" />
    
        <TextView android:id="@id/content"
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:text="?widgetContent" />
    </LinearLayout>
    
  3. 請視需要建立多種樣式,以便預覽。重新定義每個樣式的值:

    <resources>
    
        <style name="Theme.Widget.ListItem">
            <item name="widgetTitle"></item>
            <item name="widgetContent"></item>
        </style>
        <style name="Theme.Widget.ListItem.Preview1">
            <item name="widgetTitle">Fake Title 1</item>
            <item name="widgetContent">Fake content 1</item>
        </style>
        <style name="Theme.Widget.ListItem.Preview2">
            <item name="widgetTitle">Fake title 2</item>
            <item name="widgetContent">Fake content 2</item>
        </style>
    
    </resources>
    
  4. 在預覽版面配置中,將樣式套用至假項目:

    <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
       android:layout_width="match_parent"
       android:layout_height="wrap_content" ...>
    
        <include layout="@layout/widget_view" ... />
    
        <include layout="@layout/widget_list_item"
            android:theme="@style/Theme.Widget.ListItem.Preview1" />
    
        <include layout="@layout/widget_list_item"
            android:theme="@style/Theme.Widget.ListItem.Preview2" />
    
    </LinearLayout>