在 Compose for Wear OS 中從 Material 2.5 遷移至 Material 3

Material 3 Expressive 是新一代的 Material Design,提供更新後的主題設定、元件,以及動態色彩等個人化功能。

本指南主要說明如何將應用程式從 Wear Compose Material 2.5 (androidx.wear.compose) Jetpack 程式庫遷移至 Wear Compose Material 3 (androidx.wear.compose.material3) Jetpack 程式庫。

做法

如要將應用程式程式碼從 M2.5 遷移至 M3,請按照 Compose Material 遷移手機指南中所述的方法操作,特別是:

依附元件

M3 的套件和版本與 M2.5 不同:

M2.5

implementation("androidx.wear.compose:compose-material:1.4.0")

M3

implementation("androidx.wear.compose:compose-material3:1.5.0-beta01")

請前往 Wear Compose Material 3 版本頁面查看 M3 的最新版本。

Wear Compose Foundation 程式庫 1.5.0-beta01 版推出了一些新元件,可與 Material 3 元件搭配使用。同樣地,在 Wear OS 6 (API 級別 36) 以上版本中執行時,Wear Compose Navigation 程式庫的 SwipeDismissableNavHost 會提供更新的動畫。更新至 Wear Compose Material 3 版本時,建議一併更新 Wear Compose Foundation 和 Navigation 程式庫:

implementation("androidx.wear.compose:compose-foundation:1.5.0-beta01")
implementation("androidx.wear.compose:compose-navigation:1.5.0-beta01")

主題設定

在 M2.5 和 M3 中,主題可組合項的名稱都是 MaterialTheme,但匯入套件和參數並不相同。在 M3 中,Colors 參數已重新命名為 ColorScheme,並引入 MotionScheme 以實作轉場效果。

M2.5

import androidx.wear.compose.material.MaterialTheme

MaterialTheme(
        colors = AppColors,
        typography = AppTypography,
        shapes = AppShapes,
        content = content
)

M3

import androidx.wear.compose.material3.MaterialTheme

MaterialTheme(
        colorScheme = AppColorScheme,
        typography = AppTypography,
        shapes = AppShapes,
        motionScheme = AppMotionScheme,
        content = content
)

顏色

M3 的色彩系統與 M2.5 有明顯差異。顏色參數的數量有所增加,名稱也不同,且分別對應至 M3 元件。在 Compose 中,這適用於 M2.5 Colors 類別、M3 ColorScheme 類別和相關函式:

M2.5

import androidx.wear.compose.material.Colors

val appColorScheme: Colors = Colors(
   // M2.5 Color parameters
)

M3

import androidx.wear.compose.material3.ColorScheme

val appColorScheme: ColorScheme = ColorScheme(
   // M3 ColorScheme parameters
)

下表說明 M2.5 和 M3 之間的主要差異:

M2.5

M3

Color

已重新命名為 ColorScheme

13 種顏色

28 種顏色

新的動態色彩主題設定

全新三次色,讓你盡情展現個人風格

動態色彩主題

M3 的其中一項新功能是動態色彩主題設定。如果使用者變更錶面顏色,UI 中的顏色也會隨之變更。

使用 dynamicColorScheme 函式實作動態色彩配置,並在無法使用動態色彩配置時提供 defaultColorScheme 做為備用方案。

@Composable
fun myApp() {
  val myColorScheme = myBrandColors()
  val dynamicColorScheme = dynamicColorScheme(LocalContext.current)
  MaterialTheme(colorScheme = dynamicColorScheme ?: myBrandColors) {...}
}

字體排版

M3 的字體排版系統與 M2 不同,且包含下列功能:

  • 九種新的文字樣式
  • Flex 字型,可根據不同的粗細、寬度和圓弧度自訂字型比例
  • AnimatedText,使用彈性字型

M2.5

import androidx.wear.compose.material.Typography

val Typography = Typography(
   // M2.5 TextStyle parameters
)

M3

import androidx.wear.compose.material3.Typography

val Typography = Typography(
   // M3 TextStyle parameters
)

Flex 字型

Flex 字型可讓設計人員為特定大小指定字型寬度和粗細。

文字樣式

以下 TextStyles 可在 M3 中使用。這些預設會由 M3 的各種元件採用。

字體排版

TextStyle

螢幕

displayLarge、displayMedium、displaySmall

標題

titleLarge、titleMedium、titleSmall

標籤

labelLarge、labelMedium、labelSmall

內文

bodyLarge、bodyMedium、bodySmall、bodyExtraSmall

數字

numeralExtraLarge、numeralLarge、numeralMedium、numeralSmall、numeralExtraSmall

弧形

arcLarge、arcMedium、arcSmall

形狀

M3 的形狀系統與 M2 不同。形狀參數的數量有所增加,名稱也不同,且分別對應至 M3 元件。可用的形狀大小如下:

  • 特小
  • 特大

在 Compose 中,這適用於 M2 Shapes 類別和 M3 Shapes 類別:

M2.5

import androidx.wear.compose.material.Shapes

val Shapes = Shapes(
   // M2.5 Shapes parameters
)

M3

import androidx.wear.compose.material3.Shapes

val Shapes = Shapes(
   // M3 Shapes parameters
)

請參閱「在 Compose 中從 Material 2 遷移至 Material 3」一文,瞭解如何對應形狀參數。

形狀變形

M3 推出形狀變形功能:形狀現在會根據互動方式變形。

形狀變形行為可做為多個圓形按鈕的變化版本,請參閱下方說明:

按鈕

形狀變形函式

IconButton

IconButtonDefaults.animatedShape() 會在按下圖示按鈕時顯示動畫

IconToggleButton

IconToggleButtonDefaults.animatedShape() 會在按下圖示切換鈕時顯示動畫,

IconToggleButtonDefaults.variantAnimatedShapes() 會在按下圖示切換鈕時,為勾選/取消勾選進行動畫效果

TextButton

TextButtonDefaults.animatedShape():按下文字按鈕時顯示動畫

TextToggleButton

TextToggleButtonDefaults.animatedShapes() 會在按下按鈕時為文字切換按鈕加上動畫效果,而 TextToggleButtonDefaults.variantAnimatedShapes() 會在按下按鈕時為文字切換按鈕加上動畫效果,並在勾選/取消勾選時顯示動畫效果

元件和版面配置

M3 支援 M2.5 的大多數元件和版面配置。不過,M2.5 中沒有部分 M3 元件和版面配置。此外,部分 M3 元件的變化版本比 M2.5 的同等元件還多。

雖然部分元件需要特別注意,但建議您以下列函式對應做為起點:

Material 2.5

Material 3

androidx.wear.compose.material.dialog.Alert

androidx.wear.compose.material3.AlertDialog

androidx.wear.compose.material.Button

androidx.wear.compose.material3.IconButtonandroidx.wear.compose.material3.TextButton

androidx.wear.compose.material.Card

androidx.wear.compose.material3.Card

androidx.wear.compose.material.TitleCard

androidx.wear.compose.material3.TitleCard

androidx.wear.compose.material.AppCard

androidx.wear.compose.material3.AppCard

androidx.wear.compose.material.Checkbox

沒有 M3 同等項目,請改用 androidx.wear.compose.material3.CheckboxButtonandroidx.wear.compose.material3.SplitCheckboxButton

androidx.wear.compose.material.Chip

androidx.wear.compose.material3.Button
androidx.wear.compose.material3.OutlinedButton
androidx.wear.compose.material3.FilledTonalButton
androidx.wear.compose.material3.ChildButton

androidx.wear.compose.material.CompactChip

androidx.wear.compose.material3.CompactButton

androidx.wear.compose.material.InlineSlider

androidx.wear.compose.material3.Slider

androidx.wear.compose.material.LocalContentAlpha

已移除,因為 Material 3 中的 TextIcon 未使用

androidx.wear.compose.material.PositionIndicator

androidx.wear.compose.material3.ScrollIndicator

androidx.wear.compose.material.RadioButton

沒有 M3 同等項目,請改用 androidx.wear.compose.material3.RadioButtonandroidx.wear.compose.material3.SplitRadioButton

androidx.wear.compose.material.SwipeToRevealCard

androidx.wear.compose.material3.SwipeToReveal

androidx.wear.compose.material.SwipeToRevealChip

androidx.wear.compose.material3.SwipeToReveal

android.wear.compose.material.Scaffold

androidx.wear.compose material3.AppScaffoldandroidx.wear.compose.material3.ScreenScaffold

androidx.wear.compose.material.SplitToggleChip

沒有 M3 對應項目,請遷移至 androidx.wear.compose.material3.SplitCheckboxButton androidx.wear.compose.material3.SplitSwitchButtonandroidx.wear.compose.material3.SplitRadioButton

androidx.wear.compose.material.Switch

沒有 M3 同等項目,請改用 androidx.wear.compose.material3.SwitchButtonandroidx.wear.compose.material3.SplitSwitchButton

androidx.wear.compose.material.ToggleButton

androidx.wear.compose.material3.IconToggleButtonandroidx.wear.compose.material3.TextToggleButton

androidx.wear.compose.material.ToggleChip

androidx.wear.compose.material3.CheckboxButton
androidx.wear.compose.material3.RadioButton
androidx.wear.compose.material3.SwitchButton

androidx.wear.compose.material.Vignette

已移除,因為這項元素並未納入 Wear OS 適用的 Material 3 表情符號設計

以下是 Material 3 元件的完整清單:

Material 3

Material 2.5 等同元件 (如果不是 M3 的新元件)

androidx.wear.compose.material3.AlertDialog

androidx.wear.compose.material.dialog.Alert

androix.wear.compose.material3.AnimatedPage

新影片

androidx.wear.compose.material3.AnimatedText

新影片

androidx.wear.compose material3.AppScaffold

android.wear.compose.material.Scaffold (搭配 androidx.wear.compose.material3.ScreenScaffold)

androidx.wear.compose.material3.Button

androidx.wear.compose.material.Chip

androidx.wear.compose.material3.ButtonGroup

新影片

androidx.wear.compose.material3.Card

androidx.wear.compose.material.Card

androidx.wear.compose.material3.CheckboxButton

androidx.wear.compose.material.ToggleChip,搭配核取方塊切換控制項

androidx.wear.compose.material3.ChildButton

androidx.wear.compose.material.Chip (僅限不需背景時使用)

androidx.wear.compose.material3.CircularProgressIndicator

androidx.wear.compose.material.CircularProgressIndicator

androidx.wear.compose.material3.CompactButton

androidx.wear.compose.material.CompactChip

androidx.wear.compose.material3.ConfirmationDialog

androidx.wear.compose.material.dialog.Confirmation

androidx.wear.compose.material3.curvedText

androidx.wear.compose.material.curvedText

androidx.wear.compose.material3.DatePicker

新影片

androidx.wear.compose.material3.Dialog

androidx.wear.compose.material.dialog.Dialog

androidx.wear.compose.material3.EdgeButton

新影片

androidx.wear.compose.material3.FadingExpandingLabel

新影片

androidx.wear.compose.material3.FilledTonalButton

如需色調按鈕背景,請使用 androidx.wear.compose.material.Chip

androidx.wear.compose.material3.HorizontalPageIndicator

androidx.wear.compose.material.HorizontalPageIndicator

androidx.wear.compose.material3.HorizontalPagerScaffold

新影片

androidx.wear.compose.material3.Icon

androidx.wear.compose.material.Icon

androidx.wear.compose.material3.IconButton

androidx.wear.compose.material.Button

androidx.wear.compose.material3.IconToggleButton

androidx.wear.compose.material.ToggleButton

androidx.wear.compose.material3.LevelIndicator

新影片

androidx.wear.compose.material3.LinearProgressIndicator

新影片

androidx.wear.compose.material3.ListHeader

androidx.wear.compose.material.ListHeader

androidx.wear.compose.material3.ListSubHeader

新影片

androidx.wear.compose.material3.MaterialTheme

androidx.wear.compose.material.MaterialTheme

androidx.wear.compose.material3.OpenOnPhoneDialog

新影片

androidx.wear.compose.material3.Picker

androidx.wear.compose.material.Picker

androidx.wear.compose.material3.PickerGroup

androidx.wear.compose.material.PickerGroup

androix.wear.compose.material3.RadioButton

androidx.wear.compose.material.ToggleChip,搭配圓形按鈕切換控制項

androidx.wear.compose.material3.ScreenScaffold

android.wear.compose.material.Scaffold (搭配 androidx.wear.compose material3.AppScaffold)

androidx.wear.compose.material3.ScrollIndicator

androidx.wear.compose.material.PositionIndicator

androidx.wear.compose.material3.scrollaway

androidx.wear.compose.material.scrollaway

androidx.wear.compose.material3.SegmentedCircularProgressIndicator

新影片

androidx.wear.compose.material3.Slider

androidx.wear.compose.material.InlineSlider

androidx.wear.compose.material3.SplitRadioButton

androidx.wear.compose.material.SplitToggleChip

androidx.wear.compose.material3.SplitCheckboxButton

androidx.wear.compose.material.SplitToggleChip

androidx.wear.compose.material3.SplitSwitchButton

androidx.wear.compose.material.SplitToggleChip

androidx.wear.compose.material3.Stepper

androidx.wear.compose.material.Stepper

androidx.wear.compose.material3.SwipeToDismissBox

androidx.wear.compose.material.SwipeToDismissBox

androidx.wear.compose.material3.SwipeToReveal

androidx.wear.compose.material.SwipeToRevealCardandroidx.wear.compose.material.SwipeToRevealChip

androidx.wear.compose.material3.SwitchButton

androidx.wear.compose.material.ToggleChip 搭配切換鈕切換控制項

androidx.wear.compose.material3.Text

androidx.wear.compose.material.Text

androidx.wear.compose.material3.TextButton

androidx.wear.compose.material.Button

androidx.wear.compose.material3.TextToggleButton

androidx.wear.compose.material.ToggleButton

androidx.wear.compose.material3.TimeText

androidx.wear.compose.material.TimeText

androidx.wear.compose.material3.VerticalPagerScaffold

新影片

最後,以下是 Wear Compose Foundation 程式庫 1.5.0-beta01 版中一些相關元件的清單:

Wear Compose Foundation 1.5.0-beta

androidx.wear.compose.foundation.hierarchicalFocusGroup

用於在應用程式中為可組合項加註解,以便追蹤組合項的有效部分,並協調焦點。

androidx.compose.foundation.pager.HorizontalPager

這是一個可水平捲動的分頁器,以 Compose Foundation 元件為基礎,並提供 Wear 專屬強化功能,可提升效能並遵循 Wear OS 指南。

androidx.compose.foundation.pager.VerticalPager

這是一個垂直捲動的分頁器,以 Compose 基礎元件為基礎,並採用 Wear 專屬增強功能,可改善效能並遵循 Wear OS 規範。

androidx.wear.foundation.lazy.TransformingLazyColumn

可用於取代 ScalingLazyColumn,為每個項目新增捲動轉換效果。

按鈕

M3 的按鈕與 M2.5 不同。M2.5 方塊已由按鈕取代。Button 實作會為 Text maxLinestextAlign 提供預設值。您可以在 Text 元素中覆寫這些預設值。

M2.5

import androidx.wear.compose.material.Chip

//M2.5 Buttons
Chip(...)
CompactChip(...)
Button(...)

M3

import androidx.wear.compose.material3.Button

//M3 Buttons
Button(...)
CompactButton(...)
IconButton(...)
TextButton(...)

M3 也提供新的按鈕變化版本。詳情請參閱 Compose Material 3 API 參考資料總覽

M3 推出了新的按鈕:EdgeButtonEdgeButton 提供 4 種尺寸:XS、S、M 和 L。EdgeButton 實作會根據可自訂的大小,為 maxLines 提供預設值。

如果您使用 TransformingLazyColumnScalingLazyColumn,請將 EdgeButton 傳遞至 ScreenScaffold,以便進行變形,並隨著捲動變更形狀。請參閱下方程式碼,瞭解如何搭配 ScreenScaffoldTransformingLazyColumn 使用 EdgeButton

import androidx.wear.compose.material3.EdgeButton
import androidx.wear.compose.material3.ScreenScaffold

ScreenScaffold(
   scrollState = state,
   contentPadding = contentPadding,
   edgeButton = {
      EdgeButton(...)
   }
){ contentPadding ->
   TransformingLazyColumn(state = state, contentPadding = contentPadding,){
   // additional code here
   }
}

Scaffold

M3 的 Scaffold 與 M2.5 不同。在 M3 中,AppScaffold 和新的 ScreenScaffold 可組合函式已取代 Scaffold。AppScaffoldScreenScaffold 會排版畫面的結構,並協調 ScrollIndicatorTimeText 元件的轉場效果。

AppScaffold 可讓靜態畫面元素 (例如 TimeText) 在應用程式內轉換期間 (例如滑動關閉) 保持可見。它會為主要應用程式內容提供一個位置,通常會由導覽元件 (例如 SwipeDismissableNavHost) 提供

您為 Activity 宣告一個 AppScaffold,並為每個 Screen 使用 ScreenScaffold

M2.5

import androidx.wear.compose.material.Scaffold

Scaffold {...}

M3

import androidx.wear.compose.material3.AppScaffold
import androidx.wear.compose.material3.ScreenScaffold

AppScaffold {
   // Define the navigation hierarchy within the AppScaffold,
   // such as using SwipeDismissableNavHost.
   SwipeDismissableNavHost(...) {
      composable("home") {
         HomeScreen()
      }
      //other screens
   }
}
fun HomeScreen() {
    val scrollState = rememberScrollState()
    ScreenScaffold(scrollState = scrollState) {
    //rest of the screen code
    }
}

如果您使用的是搭配 HorizontalPagerIndicatorHorizontalPager,可以遷移至 HorizontalPagerScaffoldHorizontalPagerScaffold 會放在 AppScaffold 中。AppScaffoldHorizontalPagerScaffold 會排版 Pager 的結構,並協調 HorizontalPageIndicator 和 vTimeText 元件的轉場效果。

HorizontalPagerScaffold 預設會在畫面中間顯示 HorizontalPageIndicator,並根據 Pager 是否正在分頁,顯示/隱藏 TimeTextHorizontalPageIndicator,這由 PagerState 決定。

此外,還有一個新的 AnimatedPage 元件,可根據位置使用縮放和遮蔽效果,為 Pager 中的頁面製作動畫。

import androidx.wear.compose.material3.AppScaffold
import androidx.wear.compose.material3.HorizontalPagerScaffold
import androidx.wear.compose.material3.ScreenScaffold
import androidx.wear.compose.foundation.pager.HorizontalPager
import androidx.wear.compose.foundation.pager.rememberPagerState

AppScaffold {
    val pagerState = rememberPagerState(pageCount = { 10 })

    HorizontalPagerScaffold(pagerState = pagerState) {
       HorizontalPager(
          state = pagerState,
        ) { page ->
            AnimatedPage(pageIndex = page, pagerState = pagerState) {
                ScreenScaffold {

   }
}

最後,M3 會導入 VerticalPagerScaffold,其模式與 HorizontalPagerScaffold 相同:

import androidx.wear.compose.material3.AppScaffold
import androidx.wear.compose.material3.HorizontalPagerScaffold
import androidx.wear.compose.material3.ScreenScaffold
import androidx.wear.compose.foundation.pager.VerticalPager
import androidx.wear.compose.foundation.pager.rememberPagerState

AppScaffold {
   val pagerState = rememberPagerState(pageCount = { 10 })

   VerticalPagerScaffold(pagerState = pagerState) {
      VerticalPager(
         state = pagerState
      ) { page ->
             AnimatedPage(pageIndex = page, pagerState = pagerState){
                ScreenScaffold {
        
   }
}

預留位置

M2.5 和 M3 之間有一些 API 變更。Placeholder.PlaceholderDefaults 現在提供兩個修飾符:

請參閱下方 Placeholder 元件的其他變更。

M2.5

M3

PlaceholderState.startPlaceholderAnimation

已移除

PlaceholderState.placeholderProgression

已移除

PlaceholderState.isShowContent

已重新命名為 !PlaceholderState.isVisible

PlaceholderState.isWipeOff

已移除

PlaceholderDefaults.painterWithPlaceholderOverlayBackgroundBrush

已移除

PlaceholderDefaults.placeholderBackgroundBrush

已移除

PlaceholderDefaults.placeholderChipColors

已移除

SwipeDismissableNavHost

SwipeDismissableNavHostwear.compose.navigation 的一部分。當此元件與 M3 搭配使用時,M3 MaterialTheme 會更新 LocalSwipeToDismissBackgroundScrimColorLocalSwipeToDismissContentScrimColor

TransformingLazyColumn

TransformingLazyColumnwear.compose.lazy.foundation 的一部分,可在捲動期間支援縮放和變形動畫,進而提升使用者體驗。

ScalingLazyColumn 類似,它提供 rememberTransformingLazyColumnState() 來建立 TransformingLazyColumnState,並在組合中記住該 TransformingLazyColumnState

如要新增縮放和變形動畫,請在每個清單項目中加入下列內容:

  • Modifier.transformedHeight,可讓您使用 TransformationSpec 計算項目的轉換高度,您可以使用 rememberTransformationSpec(),除非您需要進一步自訂。
  • SurfaceTransformation
import androidx.wear.compose.material3.AppScaffold
import androidx.wear.compose.material3.ScreenScaffold
import androidx.wear.compose.material3.SurfaceTransformation
import androidx.wear.compose.material3.lazy.rememberTransformationSpec
import androidx.wear.compose.material3.lazy.transformedHeight
import androidx.wear.compose.foundation.lazy.rememberTransformingLazyColumnState
import androidx.wear.compose.foundation.lazy.TransformingLazyColumn

val state = rememberTransformingLazyColumnState()
val transformationSpec = rememberTransformationSpec()
AppScaffold {
   ScreenScaffold(state) { contentPadding ->
      TransformingLazyColumn(state = state, contentPadding = contentPadding) {
         items(count = 50) {
            Button(
               onClick = {},
               modifier =
                        Modifier.fillMaxWidth().transformedHeight(this, transformationSpec),
                        transformation = SurfaceTransformation(transformationSpec),
                    ) {
                        Text("Item $it")
                    }
                }
            }
        }
    }

實用連結

如要進一步瞭解如何在 Compose 中從 M2.5 遷移至 M3,請參閱下列其他資源。

範例

GitHub 上的 Material3 分支中的 Wear OS 範例

Compose for Wear OS 程式碼研究室

API 參考資料和原始碼

設計