Skip to content

Commit c1af837

Browse files
committed
Update settings logic
1 parent 9bff8e1 commit c1af837

File tree

13 files changed

+158
-225
lines changed

13 files changed

+158
-225
lines changed

app/lib/src/widget/material_context.dart

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -15,8 +15,8 @@ class MaterialContext extends StatelessWidget {
1515
Widget build(BuildContext context) {
1616
return SettingsBuilder(
1717
builder: (context, settings) {
18-
final themeMode = settings.theme.themeMode;
19-
final seedColor = settings.theme.seedColor;
18+
final themeMode = settings.general.themeMode;
19+
final seedColor = settings.general.seedColor;
2020
final locale = settings.general.locale;
2121

2222
final materialThemeMode = switch (themeMode) {

core/common/lib/common.dart

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3,3 +3,4 @@ export 'src/extensions/string_extension.dart';
33
export 'src/mutex/mutext.dart';
44
export 'src/persisted_column/persisted_column.dart';
55
export 'src/persisted_column/shared_preferences_column.dart';
6+
export 'src/utils/jsonmap_codec.dart';
Lines changed: 37 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,37 @@
1+
import 'dart:convert';
2+
3+
/// {@template json_map_codec}
4+
/// A codec for converting between a [T] and a [Map<String, Object?>].
5+
/// {@endtemplate}
6+
abstract class JsonMapCodec<T> extends Codec<T, Map<String, Object?>> {
7+
/// {@macro json_map_codec}
8+
const JsonMapCodec();
9+
10+
({T? decoded, Object? error, StackTrace? stackTrace}) tryDecode(Map<String, Object?> input) {
11+
try {
12+
return (decoded: $decode(input), error: null, stackTrace: null);
13+
} catch (e, stackTrace) {
14+
return (decoded: null, error: e, stackTrace: stackTrace);
15+
}
16+
}
17+
18+
T $decode(Map<String, Object?> input);
19+
Map<String, Object?> $encode(T input);
20+
21+
@override
22+
Converter<Map<String, Object?>, T> get decoder =>
23+
_FuncConverter<Map<String, Object?>, T>($decode);
24+
25+
@override
26+
Converter<T, Map<String, Object?>> get encoder =>
27+
_FuncConverter<T, Map<String, Object?>>($encode);
28+
}
29+
30+
class _FuncConverter<S, T> extends Converter<S, T> {
31+
const _FuncConverter(this._onConvert);
32+
33+
final T Function(S) _onConvert;
34+
35+
@override
36+
T convert(S input) => _onConvert(input);
37+
}

feature/home/lib/src/presentation/widget/home_screen.dart

Lines changed: 13 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -9,12 +9,10 @@ class HomeScreen extends StatefulWidget {
99
}
1010

1111
class _HomeScreenState extends State<HomeScreen> {
12-
Widget _buildColorItem(int index, Color? seedColor) {
13-
final itemColor = Colors.accents[index];
14-
12+
Widget _buildColorItem(Color color, bool isSelected) {
1513
return _ColorItem(
16-
color: itemColor,
17-
seedColor: seedColor,
14+
color: color,
15+
isSelected: isSelected,
1816
onTap: _onSeedColorChanged,
1917
);
2018
}
@@ -23,7 +21,7 @@ class _HomeScreenState extends State<HomeScreen> {
2321
SettingsScope.of(context).settingsBloc.add(
2422
SettingsEventUpdate(
2523
onUpdate: (settings) => settings.copyWith(
26-
theme: settings.theme.copyWith(seedColor: color),
24+
general: settings.general.copyWith(seedColor: color),
2725
),
2826
),
2927
);
@@ -53,7 +51,12 @@ class _HomeScreenState extends State<HomeScreen> {
5351
itemCount: Colors.accents.length,
5452
scrollDirection: Axis.horizontal,
5553
itemBuilder: (context, index) {
56-
return _buildColorItem(index, data.theme.seedColor);
54+
final color = Colors.accents[index];
55+
56+
return _buildColorItem(
57+
color,
58+
data.general.seedColor.toARGB32() == color.toARGB32(),
59+
);
5760
},
5861
);
5962
},
@@ -67,10 +70,10 @@ class _HomeScreenState extends State<HomeScreen> {
6770
}
6871

6972
class _ColorItem extends StatelessWidget {
70-
const _ColorItem({required this.color, required this.seedColor, required this.onTap});
73+
const _ColorItem({required this.color, required this.isSelected, required this.onTap});
7174

7275
final ValueChanged<Color> onTap;
73-
final Color? seedColor;
76+
final bool isSelected;
7477
final Color color;
7578

7679
@override
@@ -84,7 +87,7 @@ class _ColorItem extends StatelessWidget {
8487
decoration: BoxDecoration(
8588
border: Border.all(
8689
width: 2,
87-
color: seedColor?.toARGB32() == color.toARGB32() ? Colors.black : Colors.transparent,
90+
color: isSelected ? Colors.black : Colors.transparent,
8891
),
8992
borderRadius: BorderRadius.circular(16),
9093
color: color,

feature/settings/lib/settings.dart

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
1+
export 'src/domain/model/general.dart';
12
export 'src/domain/model/settings.dart';
2-
export 'src/domain/model/theme_configuration.dart';
33
export 'src/domain/repositories/settings_repository.dart';
44
export 'src/injection.dart';
55
export 'src/presentation/bloc/settings_bloc.dart';

feature/settings/lib/src/data/mappers/general_configuration_codec.dart

Lines changed: 0 additions & 52 deletions
This file was deleted.
Lines changed: 50 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,50 @@
1+
// TODO(Michael): update sizzle_lints to remove this lint
2+
// ignore_for_file: prefer-prefixed-global-constants
3+
4+
import 'dart:ui' show Color;
5+
6+
import 'package:common/common.dart';
7+
import 'package:settings/settings.dart';
8+
9+
const generalSettingsCodec = GeneralSettingsCodec();
10+
11+
class GeneralSettingsCodec extends JsonMapCodec<GeneralSettings> {
12+
const GeneralSettingsCodec();
13+
14+
@override
15+
GeneralSettings $decode(Map<String, Object?> input) {
16+
final themeMode = input['themeMode'] as String?;
17+
final seedColor = input['seedColor'] as Map<String, Object?>?;
18+
19+
const defaults = GeneralSettings();
20+
21+
Color? seedColorValue;
22+
23+
if (seedColor case {
24+
'r': final r as double,
25+
'g': final g as double,
26+
'b': final b as double,
27+
'a': final a as double,
28+
}) {
29+
seedColorValue = Color.from(alpha: a, red: r, green: g, blue: b);
30+
}
31+
32+
return GeneralSettings(
33+
themeMode: themeMode != null ? ThemeModeVO.values.byName(themeMode) : defaults.themeMode,
34+
seedColor: seedColorValue ?? defaults.seedColor,
35+
);
36+
}
37+
38+
@override
39+
Map<String, Object?> $encode(GeneralSettings input) {
40+
return {
41+
'themeMode': input.themeMode.name,
42+
'seedColor': {
43+
'r': input.seedColor.r,
44+
'g': input.seedColor.g,
45+
'b': input.seedColor.b,
46+
'a': input.seedColor.a,
47+
},
48+
};
49+
}
50+
}
Lines changed: 12 additions & 41 deletions
Original file line numberDiff line numberDiff line change
@@ -1,54 +1,25 @@
1-
import 'dart:convert';
2-
1+
import 'package:common/common.dart';
32
import 'package:settings/settings.dart';
4-
import 'package:settings/src/data/mappers/general_configuration_codec.dart';
5-
import 'package:settings/src/data/mappers/theme_configuration_codec.dart';
6-
import 'package:settings/src/domain/model/general_configuration.dart';
3+
import 'package:settings/src/data/mappers/general_settings_codec.dart';
74

8-
class SettingsCodec extends Codec<Settings, Map<String, Object?>> {
5+
class SettingsCodec extends JsonMapCodec<Settings> {
96
const SettingsCodec();
107

118
@override
12-
Converter<Map<String, Object?>, Settings> get decoder => const _SettingsDecoder();
13-
14-
@override
15-
Converter<Settings, Map<String, Object?>> get encoder => const _SettingsEncoder();
16-
}
17-
18-
class _SettingsEncoder extends Converter<Settings, Map<String, Object?>> {
19-
const _SettingsEncoder();
20-
21-
@override
22-
Map<String, Object?> convert(Settings input) {
23-
return {
24-
'general': generalConfigurationCodec.encode(input.general),
25-
'theme': themeConfigurationCodec.encode(input.theme),
26-
};
27-
}
28-
}
29-
30-
class _SettingsDecoder extends Converter<Map<String, Object?>, Settings> {
31-
const _SettingsDecoder();
32-
33-
@override
34-
Settings convert(Map<String, Object?> input) {
9+
Settings $decode(Map<String, Object?> input) {
3510
final generalMap = input['general'] as Map<String, Object?>?;
36-
final themeMap = input['themeConfiguration'] as Map<String, Object?>?;
3711

38-
ThemeConfiguration? theme;
39-
GeneralConfiguration? general;
40-
41-
if (themeMap != null) {
42-
theme = themeConfigurationCodec.decode(themeMap);
43-
}
12+
GeneralSettings? general;
4413

4514
if (generalMap != null) {
46-
general = generalConfigurationCodec.decode(generalMap);
15+
general = generalSettingsCodec.decode(generalMap);
4716
}
4817

49-
return Settings(
50-
general: general ?? const GeneralConfiguration(),
51-
theme: theme ?? const ThemeConfiguration(),
52-
);
18+
return Settings(general: general ?? const GeneralSettings());
5319
}
20+
21+
@override
22+
Map<String, Object?> $encode(Settings input) => {
23+
'general': generalSettingsCodec.encode(input.general),
24+
};
5425
}

feature/settings/lib/src/data/mappers/theme_configuration_codec.dart

Lines changed: 0 additions & 55 deletions
This file was deleted.
Lines changed: 36 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,36 @@
1+
import 'dart:ui' show Color, Locale;
2+
3+
/// Possible theme modes for the application.
4+
enum ThemeModeVO { light, dark, system }
5+
6+
/// Class that holds values used for constructing a theme for the app.
7+
final class GeneralSettings {
8+
const GeneralSettings({
9+
this.locale = const Locale('en'),
10+
this.themeMode = ThemeModeVO.system,
11+
this.seedColor = const Color(0xFF6200EE),
12+
});
13+
14+
final ThemeModeVO themeMode;
15+
final Color seedColor;
16+
final Locale locale;
17+
18+
GeneralSettings copyWith({ThemeModeVO? themeMode, Color? seedColor, Locale? locale}) {
19+
return GeneralSettings(
20+
themeMode: themeMode ?? this.themeMode,
21+
seedColor: seedColor ?? this.seedColor,
22+
locale: locale ?? this.locale,
23+
);
24+
}
25+
26+
@override
27+
bool operator ==(Object other) =>
28+
identical(this, other) ||
29+
other is GeneralSettings &&
30+
seedColor == other.seedColor &&
31+
themeMode == other.themeMode &&
32+
locale == other.locale;
33+
34+
@override
35+
int get hashCode => Object.hash(seedColor, themeMode, locale);
36+
}

0 commit comments

Comments
 (0)