Skip to content

Commit 3dfd216

Browse files
committed
Bump version 0.3.12 retain theme across restart
1 parent e59b3bf commit 3dfd216

File tree

4 files changed

+60
-12
lines changed

4 files changed

+60
-12
lines changed

CHANGELOG.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -15,6 +15,7 @@ au](https://solidcommunity.au/docs/solidui)
1515

1616
## 0.4.0 Refine and Tune
1717

18+
+ Retain app theme across restart [0.3.12 20260409 gjw]
1819
+ Add get key if required to login [0.3.11 20260406 tonypioneer]
1920
+ Fine tune UX for SolidScaffold elements [0.3.10 20260406 gjw]
2021
+ List files/folder count in FileBrowser, not just file count [0.3.9 20260402 gjw]

lib/src/widgets/solid_login.dart

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -202,6 +202,9 @@ class _SolidLoginState extends State<SolidLogin> with WidgetsBindingObserver {
202202
WidgetsBinding.instance.addObserver(this);
203203
solidThemeNotifier.addListener(_onThemeChanged);
204204

205+
// Load the persisted theme preference before the first build.
206+
_initTheme();
207+
205208
// Initialise focus nodes for keyboard navigation.
206209

207210
_loginFocusNode = FocusNode(debugLabel: 'loginButton');
@@ -297,6 +300,11 @@ class _SolidLoginState extends State<SolidLogin> with WidgetsBindingObserver {
297300
void _onThemeChanged() => mounted ? setState(() {}) : null;
298301
bool get isDarkMode => SolidLoginThemeHelper.isDarkMode(context);
299302

303+
Future<void> _initTheme() async {
304+
await solidThemeNotifier.initialize();
305+
if (mounted) setState(() {});
306+
}
307+
300308
Future<void> _initPackageInfo() async {
301309
if (!mounted) return;
302310
await setAppDirName(widget.appDirectory);

lib/src/widgets/solid_theme_notifier.dart

Lines changed: 50 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -24,17 +24,25 @@
2424
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
2525
// SOFTWARE.
2626
///
27-
/// Authors: Tony Chen
27+
/// Authors: Tony Chen, Graham Williams
2828
2929
library;
3030

3131
import 'package:flutter/material.dart';
3232
import 'package:flutter/scheduler.dart';
3333

34+
import 'package:shared_preferences/shared_preferences.dart';
35+
3436
import 'package:solidui/src/widgets/solid_preferences_models.dart';
3537

38+
/// SharedPreferences key for persisting the theme mode across app restarts.
39+
40+
const _kThemeModeKey = 'solidui_theme_mode';
41+
3642
/// Notifier for managing theme state across the application.
37-
/// The theme always starts in System mode.
43+
///
44+
/// Theme is persisted across app restarts using SharedPreferences. On first
45+
/// launch (no saved preference) the theme defaults to System mode.
3846
3947
class SolidThemeNotifier extends ChangeNotifier {
4048
ThemeMode _themeMode = ThemeMode.system;
@@ -52,36 +60,54 @@ class SolidThemeNotifier extends ChangeNotifier {
5260
5361
bool get isInitialized => _isInitialized;
5462

55-
/// Initialises the notifier.
56-
/// Theme always starts in System mode.
63+
/// Initialises the notifier by loading the persisted theme preference.
64+
///
65+
/// Must be awaited before the first build so that the correct theme is
66+
/// applied without a flash:
67+
///
68+
/// ```dart
69+
/// Future<void> _initTheme() async {
70+
/// await _themeNotifier.initialize();
71+
/// if (mounted) setState(() {});
72+
/// }
73+
/// ```
5774
5875
Future<void> initialize() async {
5976
if (_isInitialized) return;
6077

61-
_themeMode = ThemeMode.system;
78+
// Load previously saved theme mode from SharedPreferences.
79+
final prefs = await SharedPreferences.getInstance();
80+
final saved = prefs.getString(_kThemeModeKey);
81+
_themeMode = _themeModeFromString(saved);
6282
_isInitialized = true;
6383
notifyListeners();
6484
}
6585

66-
/// Sets a specific theme mode.
86+
/// Sets a specific theme mode and persists it to SharedPreferences.
6787
6888
void setThemeMode(ThemeMode themeMode) {
6989
if (_themeMode == themeMode) return;
7090

7191
_themeMode = themeMode;
7292
notifyListeners();
93+
94+
// Persist asynchronously — fire and forget is safe here since
95+
// SharedPreferences writes are fast and non-critical.
96+
SharedPreferences.getInstance().then(
97+
(prefs) => prefs.setString(_kThemeModeKey, _themeModeToString(themeMode)),
98+
);
7399
}
74100

75-
/// Toggles between System mode and the opposite of current system mode.
101+
/// Toggles between System mode and the opposite of the current system mode.
76102
///
77-
/// When in System mode, switches to the opposite of current system
78-
/// mode. When in Light or Dark mode, switches back to System mode.
103+
/// When in System mode, switches to the opposite of the current system
104+
/// brightness. When in Light or Dark mode, switches back to System mode.
105+
/// The selected mode is persisted via [setThemeMode].
79106
80107
void toggleTheme() {
81108
switch (_themeMode) {
82109
case ThemeMode.system:
83110
// Detect current system brightness and switch to the opposite mode.
84-
85111
final systemBrightness =
86112
SchedulerBinding.instance.platformDispatcher.platformBrightness;
87113
if (systemBrightness == Brightness.light) {
@@ -94,7 +120,6 @@ class SolidThemeNotifier extends ChangeNotifier {
94120
case ThemeMode.light:
95121
case ThemeMode.dark:
96122
// Switch back to System mode.
97-
98123
setThemeMode(ThemeMode.system);
99124
break;
100125
}
@@ -127,6 +152,20 @@ class SolidThemeNotifier extends ChangeNotifier {
127152
''';
128153
}
129154
}
155+
156+
// ── Serialisation helpers ─────────────────────────────────────────────────
157+
158+
static String _themeModeToString(ThemeMode mode) => switch (mode) {
159+
ThemeMode.light => 'light',
160+
ThemeMode.dark => 'dark',
161+
ThemeMode.system => 'system',
162+
};
163+
164+
static ThemeMode _themeModeFromString(String? value) => switch (value) {
165+
'light' => ThemeMode.light,
166+
'dark' => ThemeMode.dark,
167+
_ => ThemeMode.system, // default for null or unrecognised values
168+
};
130169
}
131170

132171
/// Global instance of the theme notifier.

pubspec.yaml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
name: solidui
22
description: 'A UI library for building Solid applications with Flutter.'
3-
version: 0.3.11
3+
version: 0.3.12
44
homepage: https://github.com/anusii/solidui
55

66
environment:

0 commit comments

Comments
 (0)