feature: Rework responsive layout (#217)

Co-authored-by: PartyDonut <PartyDonut@users.noreply.github.com>
This commit is contained in:
PartyDonut 2025-02-07 15:55:01 +01:00 committed by GitHub
parent e07f280124
commit 8012fdcea8
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
48 changed files with 1468 additions and 1040 deletions

View file

@ -10,6 +10,8 @@ part 'home_settings_model.g.dart';
@freezed
class HomeSettingsModel with _$HomeSettingsModel {
factory HomeSettingsModel({
@Default({...LayoutMode.values}) Set<LayoutMode> screenLayouts,
@Default({...ViewSize.values}) Set<ViewSize> layoutStates,
@Default(HomeBanner.carousel) HomeBanner homeBanner,
@Default(HomeCarouselSettings.combined) HomeCarouselSettings carouselSettings,
@Default(HomeNextUp.separate) HomeNextUp nextUp,
@ -18,6 +20,48 @@ class HomeSettingsModel with _$HomeSettingsModel {
factory HomeSettingsModel.fromJson(Map<String, dynamic> json) => _$HomeSettingsModelFromJson(json);
}
T selectAvailableOrSmaller<T>(T value, Set<T> availableOptions, List<T> allOptions) {
if (availableOptions.contains(value)) {
return value;
}
int index = allOptions.indexOf(value);
for (int i = index - 1; i >= 0; i--) {
if (availableOptions.contains(allOptions[i])) {
return allOptions[i];
}
}
return availableOptions.first;
}
enum ViewSize {
phone,
tablet,
desktop;
const ViewSize();
String label(BuildContext context) => switch (this) {
ViewSize.phone => context.localized.phone,
ViewSize.tablet => context.localized.tablet,
ViewSize.desktop => context.localized.desktop,
};
}
enum LayoutMode {
single,
dual;
const LayoutMode();
String label(BuildContext context) => switch (this) {
LayoutMode.single => context.localized.layoutModeSingle,
LayoutMode.dual => context.localized.layoutModeDual,
};
}
enum HomeBanner {
hide,
carousel,

View file

@ -20,6 +20,8 @@ HomeSettingsModel _$HomeSettingsModelFromJson(Map<String, dynamic> json) {
/// @nodoc
mixin _$HomeSettingsModel {
Set<LayoutMode> get screenLayouts => throw _privateConstructorUsedError;
Set<ViewSize> get layoutStates => throw _privateConstructorUsedError;
HomeBanner get homeBanner => throw _privateConstructorUsedError;
HomeCarouselSettings get carouselSettings =>
throw _privateConstructorUsedError;
@ -42,7 +44,9 @@ abstract class $HomeSettingsModelCopyWith<$Res> {
_$HomeSettingsModelCopyWithImpl<$Res, HomeSettingsModel>;
@useResult
$Res call(
{HomeBanner homeBanner,
{Set<LayoutMode> screenLayouts,
Set<ViewSize> layoutStates,
HomeBanner homeBanner,
HomeCarouselSettings carouselSettings,
HomeNextUp nextUp});
}
@ -62,11 +66,21 @@ class _$HomeSettingsModelCopyWithImpl<$Res, $Val extends HomeSettingsModel>
@pragma('vm:prefer-inline')
@override
$Res call({
Object? screenLayouts = null,
Object? layoutStates = null,
Object? homeBanner = null,
Object? carouselSettings = null,
Object? nextUp = null,
}) {
return _then(_value.copyWith(
screenLayouts: null == screenLayouts
? _value.screenLayouts
: screenLayouts // ignore: cast_nullable_to_non_nullable
as Set<LayoutMode>,
layoutStates: null == layoutStates
? _value.layoutStates
: layoutStates // ignore: cast_nullable_to_non_nullable
as Set<ViewSize>,
homeBanner: null == homeBanner
? _value.homeBanner
: homeBanner // ignore: cast_nullable_to_non_nullable
@ -92,7 +106,9 @@ abstract class _$$HomeSettingsModelImplCopyWith<$Res>
@override
@useResult
$Res call(
{HomeBanner homeBanner,
{Set<LayoutMode> screenLayouts,
Set<ViewSize> layoutStates,
HomeBanner homeBanner,
HomeCarouselSettings carouselSettings,
HomeNextUp nextUp});
}
@ -110,11 +126,21 @@ class __$$HomeSettingsModelImplCopyWithImpl<$Res>
@pragma('vm:prefer-inline')
@override
$Res call({
Object? screenLayouts = null,
Object? layoutStates = null,
Object? homeBanner = null,
Object? carouselSettings = null,
Object? nextUp = null,
}) {
return _then(_$HomeSettingsModelImpl(
screenLayouts: null == screenLayouts
? _value._screenLayouts
: screenLayouts // ignore: cast_nullable_to_non_nullable
as Set<LayoutMode>,
layoutStates: null == layoutStates
? _value._layoutStates
: layoutStates // ignore: cast_nullable_to_non_nullable
as Set<ViewSize>,
homeBanner: null == homeBanner
? _value.homeBanner
: homeBanner // ignore: cast_nullable_to_non_nullable
@ -135,13 +161,35 @@ class __$$HomeSettingsModelImplCopyWithImpl<$Res>
@JsonSerializable()
class _$HomeSettingsModelImpl implements _HomeSettingsModel {
_$HomeSettingsModelImpl(
{this.homeBanner = HomeBanner.carousel,
{final Set<LayoutMode> screenLayouts = const {...LayoutMode.values},
final Set<ViewSize> layoutStates = const {...ViewSize.values},
this.homeBanner = HomeBanner.carousel,
this.carouselSettings = HomeCarouselSettings.combined,
this.nextUp = HomeNextUp.separate});
this.nextUp = HomeNextUp.separate})
: _screenLayouts = screenLayouts,
_layoutStates = layoutStates;
factory _$HomeSettingsModelImpl.fromJson(Map<String, dynamic> json) =>
_$$HomeSettingsModelImplFromJson(json);
final Set<LayoutMode> _screenLayouts;
@override
@JsonKey()
Set<LayoutMode> get screenLayouts {
if (_screenLayouts is EqualUnmodifiableSetView) return _screenLayouts;
// ignore: implicit_dynamic_type
return EqualUnmodifiableSetView(_screenLayouts);
}
final Set<ViewSize> _layoutStates;
@override
@JsonKey()
Set<ViewSize> get layoutStates {
if (_layoutStates is EqualUnmodifiableSetView) return _layoutStates;
// ignore: implicit_dynamic_type
return EqualUnmodifiableSetView(_layoutStates);
}
@override
@JsonKey()
final HomeBanner homeBanner;
@ -154,7 +202,7 @@ class _$HomeSettingsModelImpl implements _HomeSettingsModel {
@override
String toString() {
return 'HomeSettingsModel(homeBanner: $homeBanner, carouselSettings: $carouselSettings, nextUp: $nextUp)';
return 'HomeSettingsModel(screenLayouts: $screenLayouts, layoutStates: $layoutStates, homeBanner: $homeBanner, carouselSettings: $carouselSettings, nextUp: $nextUp)';
}
@override
@ -162,6 +210,10 @@ class _$HomeSettingsModelImpl implements _HomeSettingsModel {
return identical(this, other) ||
(other.runtimeType == runtimeType &&
other is _$HomeSettingsModelImpl &&
const DeepCollectionEquality()
.equals(other._screenLayouts, _screenLayouts) &&
const DeepCollectionEquality()
.equals(other._layoutStates, _layoutStates) &&
(identical(other.homeBanner, homeBanner) ||
other.homeBanner == homeBanner) &&
(identical(other.carouselSettings, carouselSettings) ||
@ -171,8 +223,13 @@ class _$HomeSettingsModelImpl implements _HomeSettingsModel {
@JsonKey(includeFromJson: false, includeToJson: false)
@override
int get hashCode =>
Object.hash(runtimeType, homeBanner, carouselSettings, nextUp);
int get hashCode => Object.hash(
runtimeType,
const DeepCollectionEquality().hash(_screenLayouts),
const DeepCollectionEquality().hash(_layoutStates),
homeBanner,
carouselSettings,
nextUp);
/// Create a copy of HomeSettingsModel
/// with the given fields replaced by the non-null parameter values.
@ -193,13 +250,19 @@ class _$HomeSettingsModelImpl implements _HomeSettingsModel {
abstract class _HomeSettingsModel implements HomeSettingsModel {
factory _HomeSettingsModel(
{final HomeBanner homeBanner,
{final Set<LayoutMode> screenLayouts,
final Set<ViewSize> layoutStates,
final HomeBanner homeBanner,
final HomeCarouselSettings carouselSettings,
final HomeNextUp nextUp}) = _$HomeSettingsModelImpl;
factory _HomeSettingsModel.fromJson(Map<String, dynamic> json) =
_$HomeSettingsModelImpl.fromJson;
@override
Set<LayoutMode> get screenLayouts;
@override
Set<ViewSize> get layoutStates;
@override
HomeBanner get homeBanner;
@override

View file

@ -9,6 +9,14 @@ part of 'home_settings_model.dart';
_$HomeSettingsModelImpl _$$HomeSettingsModelImplFromJson(
Map<String, dynamic> json) =>
_$HomeSettingsModelImpl(
screenLayouts: (json['screenLayouts'] as List<dynamic>?)
?.map((e) => $enumDecode(_$LayoutModeEnumMap, e))
.toSet() ??
const {...LayoutMode.values},
layoutStates: (json['layoutStates'] as List<dynamic>?)
?.map((e) => $enumDecode(_$ViewSizeEnumMap, e))
.toSet() ??
const {...ViewSize.values},
homeBanner:
$enumDecodeNullable(_$HomeBannerEnumMap, json['homeBanner']) ??
HomeBanner.carousel,
@ -22,12 +30,27 @@ _$HomeSettingsModelImpl _$$HomeSettingsModelImplFromJson(
Map<String, dynamic> _$$HomeSettingsModelImplToJson(
_$HomeSettingsModelImpl instance) =>
<String, dynamic>{
'screenLayouts':
instance.screenLayouts.map((e) => _$LayoutModeEnumMap[e]!).toList(),
'layoutStates':
instance.layoutStates.map((e) => _$ViewSizeEnumMap[e]!).toList(),
'homeBanner': _$HomeBannerEnumMap[instance.homeBanner]!,
'carouselSettings':
_$HomeCarouselSettingsEnumMap[instance.carouselSettings]!,
'nextUp': _$HomeNextUpEnumMap[instance.nextUp]!,
};
const _$LayoutModeEnumMap = {
LayoutMode.single: 'single',
LayoutMode.dual: 'dual',
};
const _$ViewSizeEnumMap = {
ViewSize.phone: 'phone',
ViewSize.tablet: 'tablet',
ViewSize.desktop: 'desktop',
};
const _$HomeBannerEnumMap = {
HomeBanner.hide: 'hide',
HomeBanner.carousel: 'carousel',