What is Theme in Flutter?
Theme is a powerful system in Flutter that allows you to define and apply consistent styling across your entire app. It centralizes colors, typography, shapes, and other visual properties, making it easy to maintain a uniform look and feel. With themes, you can switch between light and dark modes, customize individual components, and even create your own theme extensions.
Basic Usage: ThemeData
Themes are typically defined in the MaterialApp widget using the theme (for light mode) and darkTheme parameters. You provide a ThemeData object that describes the colors, fonts, and shapes for your app.
Now throughout your app, you can access the current theme using Theme.of(context).
Accessing Theme Properties
Once you've defined a theme, you can use Theme.of(context) to retrieve the current theme data and use its properties. This is especially useful for colors and text styles.
Key Properties of ThemeData
- brightness:
Brightness.lightorBrightness.dark. Influences default colors of many widgets. - primaryColor: The primary background color for app bars, buttons, etc.
- colorScheme: A modern way to define colors. Replaces the older
primaryColor,accentColor, etc. It includesprimary,secondary,surface,error, and more. - textTheme: Defines the default text styles (displayLarge, headlineMedium, bodyLarge, etc.).
- fontFamily: Default font for text.
- appBarTheme: Customizes the appearance of AppBars.
- buttonTheme: Customizes button styles (older approach; prefer
elevatedButtonTheme). - elevatedButtonTheme, textButtonTheme, outlinedButtonTheme: Specific button themes.
- inputDecorationTheme: For TextFields and forms.
- cardTheme: For Cards.
- dividerTheme: For Dividers.
- iconTheme: Default icon color and size.
Using ColorScheme (Modern Approach)
Flutter now recommends using colorScheme for theming colors. It provides a complete set of semantic colors that work well with both light and dark themes. You can create one easily with ColorScheme.fromSeed().
This automatically generates a full color scheme based on your seed color, including primary, secondary, tertiary, and surface variants.
Light and Dark Theme Switching
To support both light and dark modes, define both theme and darkTheme, then set themeMode. You can also let users toggle the mode by changing the themeMode dynamically.
For more control, you can customize the dark theme by copying the light theme and adjusting brightness:
Text Themes
textTheme defines the typography scale for your app. You can override individual styles while keeping others.
Theme Extensions
For custom app‑specific styles, you can create a ThemeExtension. This allows you to add your own properties to the theme and access them with Theme.of(context).extension<MyColors>().
Local Theme Overrides
Sometimes you want to change the theme for a specific part of the widget tree. Use Theme widget with a copy of the current theme.
Common Mistakes Beginners Make
- Not using
Theme.of(context)– Hardcoding colors instead of using theme values makes your app hard to maintain and prevents easy theme switching. - Confusing
primaryColorwithcolorScheme.primary: The modern approach usescolorScheme. If you set both, they might conflict. PrefercolorScheme. - Forgetting to set
useMaterial3: Material 3 is the default for new Flutter apps, but you need to enable it explicitly if you want the latest design. - Overriding too much: You don't need to redefine every property. Start from a base theme and override only what you need.
- Not providing a dark theme: Users expect dark mode support; if you don't provide one, your app may look broken in dark mode.
- Using
Theme.of(context)before the theme is available: Ensure yourBuildContextis under aMaterialAppthat provides the theme.
Key Points to Remember
- Define themes in
MaterialAppusingthemeanddarkTheme. - Use
Theme.of(context)to access the current theme anywhere. - Prefer
colorSchemefor defining colors; it's the modern and flexible approach. - Text styles are managed via
textTheme; use predefined names (headlineMedium, bodyLarge, etc.). - For custom properties, create a
ThemeExtension. - Override themes locally with the
Themewidget andcopyWith. - Always consider both light and dark themes for a polished app.
Common Interview Questions
- How does theme inheritance work in Flutter?
- What is the difference between
ThemeDataandThemewidget? - Explain the purpose of
colorSchemeand how it differs from usingprimaryColordirectly. - How would you implement a dark mode toggle in your app?
- What are
ThemeExtensions and when would you use them? - How can you override the text style for all buttons without changing the global text theme?