Files
please-pay-me/mobile/lib/theme/theme_controller.dart
T
2026-09-21 04:06:43 +03:00

82 lines
2.0 KiB
Dart

import 'package:flutter/cupertino.dart';
import 'package:shared_preferences/shared_preferences.dart';
enum ThemePreference {
system,
light,
dark;
static ThemePreference parse(String? raw) {
return switch (raw) {
'light' => ThemePreference.light,
'dark' => ThemePreference.dark,
_ => ThemePreference.system,
};
}
Brightness resolve(Brightness platform) => switch (this) {
ThemePreference.system => platform,
ThemePreference.light => Brightness.light,
ThemePreference.dark => Brightness.dark,
};
}
abstract interface class ThemePreferenceStore {
Future<String?> read();
Future<void> write(String value);
}
class PrefsThemeStore implements ThemePreferenceStore {
const PrefsThemeStore();
static const key = 'ppm_theme_preference';
@override
Future<String?> read() async {
final prefs = await SharedPreferences.getInstance();
return prefs.getString(key);
}
@override
Future<void> write(String value) async {
final prefs = await SharedPreferences.getInstance();
await prefs.setString(key, value);
}
}
class MemoryThemeStore implements ThemePreferenceStore {
MemoryThemeStore([this.value]);
String? value;
@override
Future<String?> read() async => value;
@override
Future<void> write(String next) async => value = next;
}
/// Survives logout: appearance is a device preference, not a session one.
class ThemeController extends ChangeNotifier {
ThemeController({ThemePreferenceStore? store}) : _store = store ?? const PrefsThemeStore();
final ThemePreferenceStore _store;
ThemePreference _preference = ThemePreference.system;
ThemePreference get preference => _preference;
Brightness resolve(Brightness platform) => _preference.resolve(platform);
Future<void> restore() async {
_preference = ThemePreference.parse(await _store.read());
notifyListeners();
}
Future<void> setPreference(ThemePreference value) async {
if (_preference == value) return;
_preference = value;
notifyListeners();
await _store.write(value.name);
}
}