flutter-theming
Compare original and translation side by side
🇺🇸
Original
English🇨🇳
Translation
ChineseGoal
目标
Updates and manages Flutter application styling by migrating legacy Material 2 implementations to Material 3, normalizing component themes, updating deprecated button classes, and adapting UI idioms for cross-platform consistency. Assumes a Flutter environment using Dart.
通过将旧版Material 2实现迁移到Material 3、规范组件主题、更新已弃用的按钮类、适配UI习惯用语以实现跨平台一致性,来更新和管理Flutter应用的样式。本教程假设你使用的是基于Dart的Flutter开发环境。
Instructions
操作指引
-
Analyze Current Theme State Review the existing Flutter codebase to identify legacy Material 2 components, deprecated button classes (,
FlatButton,RaisedButton), and outdated theme properties (e.g.,OutlineButton,accentColorincolor). STOP AND ASK THE USER: "What is the primary seed color for the new Material 3 ColorScheme, and which target platforms (iOS, Android, Windows, macOS, Linux, Web) should be prioritized for platform idioms?"AppBarTheme -
Decision Logic: Component Migration When encountering legacy widgets, use the following decision tree to determine the replacement:
- IF -> REPLACE WITH
BottomNavigationBar(usesNavigationBar).NavigationDestination - IF -> REPLACE WITH
Drawer(usesNavigationDrawer).NavigationDrawerDestination - IF -> REPLACE WITH
ToggleButtons(usesSegmentedButtonandButtonSegmentfor selection).Set - IF -> REPLACE WITH
FlatButton.TextButton - IF -> REPLACE WITH
RaisedButton(orElevatedButtonfor no elevation).FilledButton - IF -> REPLACE WITH
OutlineButton.OutlinedButton
- IF
-
Implement App-Wide Material 3 Theme Define the globalusing
ThemeData. EnsureColorScheme.fromSeedis implicitly or explicitly true. Remove all references to deprecated accent properties (useMaterial3,accentColor,accentColorBrightness,accentTextTheme).accentIconThemedartMaterialApp( title: 'App Name', theme: ThemeData( useMaterial3: true, colorScheme: ColorScheme.fromSeed( seedColor: Colors.deepPurple, brightness: Brightness.light, ), // Use colorScheme.secondary instead of accentColor ), darkTheme: ThemeData( useMaterial3: true, colorScheme: ColorScheme.fromSeed( seedColor: Colors.deepPurple, brightness: Brightness.dark, ), ), home: const MyHomePage(), ); -
Normalize Component Themes Update all component theme definitions into use their
ThemeDataequivalents. Do not use the base theme classes for configuration.*ThemeData- ->
cardThemeCardThemeData - ->
dialogThemeDialogThemeData - ->
tabBarThemeTabBarThemeData - ->
appBarTheme(ReplaceAppBarThemeDatawithcolor)backgroundColor - ->
bottomAppBarThemeBottomAppBarThemeData - ->
inputDecorationThemeInputDecorationThemeData
dartThemeData( colorScheme: ColorScheme.fromSeed(seedColor: Colors.blue), appBarTheme: const AppBarThemeData( backgroundColor: Colors.blue, // Do not use 'color' elevation: 4.0, ), cardTheme: const CardThemeData( elevation: 2.0, ), ); -
Migrate Buttons and Button Styles Replace legacy buttons. Use thestatic method for simple overrides, or
styleFrom()withButtonStylefor state-dependent styling.MaterialStatePropertydart// Simple override using styleFrom TextButton( style: TextButton.styleFrom( foregroundColor: Colors.blue, disabledForegroundColor: Colors.red, ), onPressed: () {}, child: const Text('TextButton'), ) // State-dependent override using MaterialStateProperty OutlinedButton( style: ButtonStyle( side: MaterialStateProperty.resolveWith<BorderSide>( (Set<MaterialState> states) { if (states.contains(MaterialState.pressed)) { return const BorderSide(color: Colors.blue, width: 2); } return const BorderSide(color: Colors.grey, width: 1); } ), ), onPressed: () {}, child: const Text('OutlinedButton'), ) -
Decision Logic: Platform Idioms Apply platform-specific adaptations based on the host OS to reduce cognitive load and build user trust.
- Scrollbars: IF desktop platform -> Set (or
thumbVisibility: true). IF mobile -> Use default auto-hiding behavior.alwaysShown - Text Selection: IF text is informational and non-interactive -> Wrap in to allow mouse selection on Web/Desktop.
SelectableText - Button Ordering: IF Windows -> Place confirmation button on the LEFT. IF macOS/Linux/Android/iOS -> Place confirmation button on the RIGHT.
dart// Platform-aware button ordering TextDirection btnDirection = Platform.isWindows ? TextDirection.rtl : TextDirection.ltr; Row( children: [ const Spacer(), Row( textDirection: btnDirection, children: [ TextButton( onPressed: () => Navigator.pop(context, false), child: const Text('Cancel'), ), ElevatedButton( onPressed: () => Navigator.pop(context, true), child: const Text('OK'), ), ], ), ], ) - Scrollbars: IF desktop platform -> Set
-
Validate-and-Fix Scan the generated code to verify that no,
FlatButton,RaisedButton, orOutlineButtonclasses remain. Verify thatButtonThemedoes not use theAppBarThemeproperty. Fix any instances found.color
-
分析当前主题状态 检查现有的Flutter代码库,找出旧版Material 2组件、已弃用的按钮类(、
FlatButton、RaisedButton)以及过时的主题属性(例如OutlineButton中的AppBarTheme、accentColor)。 停下并询问用户: "新的Material 3 ColorScheme的主种子色是什么,平台适配习惯用语应该优先适配哪些目标平台(iOS、Android、Windows、macOS、Linux、Web)?"color -
决策逻辑:组件迁移 遇到旧版组件时,使用以下决策树确定替换方案:
- 如果是-> 替换为
BottomNavigationBar(使用NavigationBar)。NavigationDestination - 如果是-> 替换为
Drawer(使用NavigationDrawer)。NavigationDrawerDestination - 如果是-> 替换为
ToggleButtons(使用SegmentedButton和ButtonSegment实现选择功能)。Set - 如果是-> 替换为
FlatButton。TextButton - 如果是-> 替换为
RaisedButton(无阴影需求可使用ElevatedButton)。FilledButton - 如果是-> 替换为
OutlineButton。OutlinedButton
- 如果是
-
实现全局Material 3主题 使用定义全局
ColorScheme.fromSeed,确保ThemeData隐式或显式为true。移除所有对已弃用的accent相关属性的引用(useMaterial3、accentColor、accentColorBrightness、accentTextTheme)。accentIconThemedartMaterialApp( title: 'App Name', theme: ThemeData( useMaterial3: true, colorScheme: ColorScheme.fromSeed( seedColor: Colors.deepPurple, brightness: Brightness.light, ), // Use colorScheme.secondary instead of accentColor ), darkTheme: ThemeData( useMaterial3: true, colorScheme: ColorScheme.fromSeed( seedColor: Colors.deepPurple, brightness: Brightness.dark, ), ), home: const MyHomePage(), ); -
规范组件主题 将中所有组件主题定义更新为对应的
ThemeData类型,不要使用基础主题类进行配置。*ThemeData- ->
cardThemeCardThemeData - ->
dialogThemeDialogThemeData - ->
tabBarThemeTabBarThemeData - ->
appBarTheme(将AppBarThemeData替换为color)backgroundColor - ->
bottomAppBarThemeBottomAppBarThemeData - ->
inputDecorationThemeInputDecorationThemeData
dartThemeData( colorScheme: ColorScheme.fromSeed(seedColor: Colors.blue), appBarTheme: const AppBarThemeData( backgroundColor: Colors.blue, // Do not use 'color' elevation: 4.0, ), cardTheme: const CardThemeData( elevation: 2.0, ), ); -
迁移按钮与按钮样式 替换旧版按钮。简单样式覆盖可以使用静态方法,状态相关样式则使用搭配
styleFrom()的MaterialStateProperty。ButtonStyledart// Simple override using styleFrom TextButton( style: TextButton.styleFrom( foregroundColor: Colors.blue, disabledForegroundColor: Colors.red, ), onPressed: () {}, child: const Text('TextButton'), ) // State-dependent override using MaterialStateProperty OutlinedButton( style: ButtonStyle( side: MaterialStateProperty.resolveWith<BorderSide>( (Set<MaterialState> states) { if (states.contains(MaterialState.pressed)) { return const BorderSide(color: Colors.blue, width: 2); } return const BorderSide(color: Colors.grey, width: 1); } ), ), onPressed: () {}, child: const Text('OutlinedButton'), ) -
决策逻辑:平台适配习惯用语 根据宿主操作系统应用平台特定适配,降低用户认知成本,建立用户信任。
- 滚动条: 如果是桌面平台 -> 设置(或
thumbVisibility: true)。如果是移动端 -> 使用默认的自动隐藏行为。alwaysShown - 文本选择: 如果是信息类非交互文本 -> 包裹在中,支持Web/桌面端鼠标选择。
SelectableText - 按钮排序: 如果是Windows系统 -> 将确认按钮放在左侧。如果是macOS/Linux/Android/iOS -> 将确认按钮放在右侧。
dart// Platform-aware button ordering TextDirection btnDirection = Platform.isWindows ? TextDirection.rtl : TextDirection.ltr; Row( children: [ const Spacer(), Row( textDirection: btnDirection, children: [ TextButton( onPressed: () => Navigator.pop(context, false), child: const Text('Cancel'), ), ElevatedButton( onPressed: () => Navigator.pop(context, true), child: const Text('OK'), ), ], ), ], ) - 滚动条: 如果是桌面平台 -> 设置
-
验证与修复 扫描生成的代码,确认没有残留、
FlatButton、RaisedButton或OutlineButton类。确认ButtonTheme没有使用AppBarTheme属性,修复所有发现的问题。color
Constraints
约束条件
- Single Source of Truth: All colors must be derived from the (e.g.,
ColorScheme). Do not hardcode hex colors unless explicitly requested.Theme.of(context).colorScheme.primary - No Legacy Buttons: Never output ,
FlatButton, orRaisedButton.OutlineButton - No Accent Properties: Never use ,
accentColor,accentColorBrightness, oraccentTextTheme. UseaccentIconThemeandcolorScheme.secondaryinstead.colorScheme.onSecondary - Component Theme Suffixes: Always append to component themes when configuring
Data(e.g.,ThemeData, notCardThemeData).CardTheme - AppBar Background: Never use the property in
colororAppBarTheme; strictly useAppBarThemeData.backgroundColor
- 唯一数据源: 所有颜色必须派生自(例如
ColorScheme)。除非明确要求,否则不要硬编码十六进制颜色。Theme.of(context).colorScheme.primary - 禁止使用旧版按钮: 绝对不要输出、
FlatButton或RaisedButton。OutlineButton - 禁止使用Accent相关属性: 绝对不要使用、
accentColor、accentColorBrightness或accentTextTheme,请改用accentIconTheme和colorScheme.secondary。colorScheme.onSecondary - 组件主题后缀: 配置时,组件主题必须始终加上
ThemeData后缀(例如使用Data而非CardThemeData)。CardTheme - AppBar背景配置: 绝对不要在或
AppBarTheme中使用AppBarThemeData属性,严格使用color。backgroundColor