diff --git a/.vscode/settings.json b/.vscode/settings.json index ffa9f03..b4c5fa8 100644 --- a/.vscode/settings.json +++ b/.vscode/settings.json @@ -12,6 +12,7 @@ "audioplayers", "autolabeler", "Autovalidate", + "Checkmark", "deeplinking", "fullscreen", "Lerp", diff --git a/lib/settings/view/buttons.dart b/lib/settings/view/buttons.dart index 0dea11f..4a15b41 100644 --- a/lib/settings/view/buttons.dart +++ b/lib/settings/view/buttons.dart @@ -20,12 +20,16 @@ class OkButton extends StatelessWidget { class CancelButton extends StatelessWidget { const CancelButton({ super.key, + this.onPressed, }); + final void Function()? onPressed; + @override Widget build(BuildContext context) { return TextButton( onPressed: () { + onPressed?.call(); Navigator.of(context).pop(); }, child: const Text('Cancel'), diff --git a/lib/settings/view/theme_settings_page.dart b/lib/settings/view/theme_settings_page.dart index b6fe4e9..f3bb606 100644 --- a/lib/settings/view/theme_settings_page.dart +++ b/lib/settings/view/theme_settings_page.dart @@ -1,9 +1,11 @@ import 'dart:io'; import 'package:flutter/material.dart'; +import 'package:flutter_hooks/flutter_hooks.dart'; import 'package:flutter_settings_ui/flutter_settings_ui.dart'; import 'package:hooks_riverpod/hooks_riverpod.dart'; import 'package:vaani/settings/app_settings_provider.dart'; +import 'package:vaani/settings/view/buttons.dart'; import 'package:vaani/settings/view/simple_settings_page.dart'; import 'package:vaani/shared/extensions/enum.dart'; @@ -57,28 +59,8 @@ class ThemeSettingsPage extends HookConsumerWidget { final themeMode = await showDialog( context: context, builder: (context) { - return SimpleDialog( - title: const Text('Select Theme Mode'), - children: [ - SimpleDialogOption( - onPressed: () { - Navigator.pop(context, ThemeMode.system); - }, - child: const Text('System'), - ), - SimpleDialogOption( - onPressed: () { - Navigator.pop(context, ThemeMode.light); - }, - child: const Text('Light'), - ), - SimpleDialogOption( - onPressed: () { - Navigator.pop(context, ThemeMode.dark); - }, - child: const Text('Dark'), - ), - ], + return ModeSelectionDialog( + themeMode: themeSettings.themeMode, ); }, ); @@ -228,3 +210,52 @@ extension StringExtension on String { return Color(int.parse('0xff$substring(1)')); } } + +class ModeSelectionDialog extends HookConsumerWidget { + final ThemeMode themeMode; + + const ModeSelectionDialog({ + super.key, + required this.themeMode, + }); + + @override + Widget build(BuildContext context, WidgetRef ref) { + final selectedTheme = useState(themeMode); + // a wrap of chips to show the available modes with icons + return AlertDialog( + title: const Text('Select Theme Mode'), + content: Wrap( + spacing: 8.0, + runSpacing: 8.0, + children: ThemeMode.values + .map( + (mode) => ChoiceChip( + avatar: switch (mode) { + ThemeMode.system => const Icon(Icons.auto_awesome), + ThemeMode.light => const Icon(Icons.light_mode), + ThemeMode.dark => const Icon(Icons.dark_mode), + }, + showCheckmark: false, + label: Text(mode.pascalCase), + selected: mode == selectedTheme.value, + onSelected: (selected) { + if (selected) { + selectedTheme.value = mode; + } + }, + ), + ) + .toList(), + ), + actions: [ + CancelButton(), + OkButton( + onPressed: () { + Navigator.pop(context, selectedTheme.value); + }, + ), + ], + ); + } +}