Implement Flutter themes using Provider
Target Audience: Beginner
Recipe: Toggle Flutter themes from one type to another using Provider dependency injection and state management package.
Focus Widget: Provider plugin
Goal: Implementing themes using Provider plugin. Implement a simple UI with an image, text and a button to switch themes. Page's default theme is light. Clicking on "Switch Theme" button will apply dark theme to page, and vice versa.
Light Theme:
Dark Theme:
Checkout the companion video here
What is Provider
Provider is a plugin/package that provides dependency injection and state management solution for a Flutter App. It's built with robust and scalable Flutter widgets.
pubspec.yaml
Step #1. Add package dependency in pubspec.yaml
:
dependencies:
flutter:
sdk: flutter
#Dependency for Provider plugin
provider: ^3.1.0 #ChangeNotifier, Consumer, Providers
Step #2. Implement theme ChangeNotifier
I'll be using two themes: Light and Dark. Let's use enum
to declare these two themes:
enum MyThemes { light, dark }
Now, I need a ChangeNotifier
that'll notify my app about the change occurred in theme preference.
class ThemesNotifier with ChangeNotifier {}
Next comes defining ThemeData
for light
and dark
themes:
static final List<ThemeData> themeData = [
ThemeData(
brightness: Brightness.light,
primaryColor: Colors.blue,
accentColor: Colors.lightBlueAccent),
ThemeData(
brightness: Brightness.dark,
primaryColor: Colors.orange,
accentColor: Colors.yellowAccent)
];
Let's initialize default MyThemes
and ThemeData
:
MyThemes _currentTheme = MyThemes.light;
ThemeData _currentThemeData = themeData[0];
Lastly, setters and getters to update and access MyThemes
and ThemeData
:
void switchTheme() => currentTheme == MyThemes.light
? currentTheme = MyThemes.dark
: currentTheme = MyThemes.light;
set currentTheme(MyThemes theme) {
if (theme != null) {
_currentTheme = theme;
_currentThemeData =
currentTheme == MyThemes.light ? themeData[0] : themeData[1];
//Notifies the theme change to app
notifyListeners();
}
}
get currentTheme => _currentTheme;
get currentThemeData => _currentThemeData;
Step #3. Notifying theme change to App
Sample App 'Themes Demo''s build(...)
method uses theme
attribute to assign ThemeData
to app like below. Provider.of<ThemesNotifier>(context).currentThemeData
is notified about a theme change happened in ThemesNotifier
's switchTheme()
method.
@override
Widget build(BuildContext context) {
return MaterialApp(
theme: Provider.of<ThemesNotifier>(context).currentThemeData,
home: Scaffold(
appBar: AppBar(
title: Text("Themes Demo"),
),
body: body(),
));
}
Theme change is requested from Switch Theme
button :
RaisedButton(
child: Text("Switch Theme"),
onPressed: () {
Provider.of<ThemesNotifier>(context).switchTheme();
},
),
That's all !
Running on Flutter Web
Note: Flutter Web project setup has been changed since Flutter 1.9 release.
Please follow the direction on setting up Flutter Web project here.
Source code repo: Recipe source code is available here
References:
Happy cooking with Flutter
Liked the article ? Couldn't find a topic of your interest ? Please leave comments or email me about topics you would like me to write
Follow me at twitter