♻️ Update event calander loading
This commit is contained in:
parent
1822142df5
commit
d678cc571a
@ -2,6 +2,7 @@ import 'package:auto_route/auto_route.dart';
|
||||
import 'package:easy_localization/easy_localization.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter_hooks/flutter_hooks.dart';
|
||||
import 'package:freezed_annotation/freezed_annotation.dart';
|
||||
import 'package:gap/gap.dart';
|
||||
import 'package:hooks_riverpod/hooks_riverpod.dart';
|
||||
import 'package:island/models/activity.dart';
|
||||
@ -13,11 +14,24 @@ import 'package:styled_widget/styled_widget.dart';
|
||||
import 'package:table_calendar/table_calendar.dart';
|
||||
|
||||
part 'event_calendar.g.dart';
|
||||
part 'event_calendar.freezed.dart';
|
||||
|
||||
@freezed
|
||||
abstract class EventCalendarQuery with _$EventCalendarQuery {
|
||||
const factory EventCalendarQuery({
|
||||
required String? uname,
|
||||
required int year,
|
||||
required int month,
|
||||
}) = _EventCalendarQuery;
|
||||
}
|
||||
|
||||
@riverpod
|
||||
Future<List<SnEventCalendarEntry>> myselfAccountEventCalendar(Ref ref) async {
|
||||
Future<List<SnEventCalendarEntry>> accountEventCalendar(
|
||||
Ref ref,
|
||||
EventCalendarQuery query,
|
||||
) async {
|
||||
final client = ref.watch(apiClientProvider);
|
||||
final resp = await client.get('/accounts/me/calendar');
|
||||
final resp = await client.get('/accounts/${query.uname ?? 'me'}/calendar');
|
||||
return resp.data
|
||||
.map((e) => SnEventCalendarEntry.fromJson(e))
|
||||
.cast<SnEventCalendarEntry>()
|
||||
@ -30,10 +44,21 @@ class MyselfEventCalendarScreen extends HookConsumerWidget {
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context, WidgetRef ref) {
|
||||
final events = ref.watch(myselfAccountEventCalendarProvider);
|
||||
final selectedMonth = useState(DateTime.now().month);
|
||||
final selectedYear = useState(DateTime.now().year);
|
||||
|
||||
final selectedDay = useState(DateTime.now());
|
||||
|
||||
final events = ref.watch(
|
||||
accountEventCalendarProvider(
|
||||
EventCalendarQuery(
|
||||
uname: 'me',
|
||||
year: selectedYear.value,
|
||||
month: selectedMonth.value,
|
||||
),
|
||||
),
|
||||
);
|
||||
|
||||
return AppScaffold(
|
||||
appBar: AppBar(
|
||||
leading: const PageBackButton(),
|
||||
@ -41,64 +66,62 @@ class MyselfEventCalendarScreen extends HookConsumerWidget {
|
||||
),
|
||||
body: Column(
|
||||
children: [
|
||||
SizedBox(
|
||||
height: 340,
|
||||
child: events.when(
|
||||
data: (events) {
|
||||
return TableCalendar(
|
||||
locale: EasyLocalization.of(context)!.locale.toString(),
|
||||
firstDay: DateTime.utc(2010, 10, 16),
|
||||
lastDay: DateTime.utc(2030, 3, 14),
|
||||
focusedDay: DateTime.now(),
|
||||
calendarFormat: CalendarFormat.month,
|
||||
selectedDayPredicate: (day) {
|
||||
return isSameDay(selectedDay.value, day);
|
||||
},
|
||||
onDaySelected: (value, _) {
|
||||
selectedDay.value = value;
|
||||
},
|
||||
eventLoader: (day) {
|
||||
return events
|
||||
.where((e) => isSameDay(e.date, day))
|
||||
.expand((e) => [...e.statuses, e.checkInResult])
|
||||
.where((e) => e != null)
|
||||
.toList();
|
||||
},
|
||||
calendarBuilders: CalendarBuilders(
|
||||
dowBuilder: (context, day) {
|
||||
final text = DateFormat.EEEEE().format(day);
|
||||
return Center(child: Text(text));
|
||||
},
|
||||
markerBuilder: (context, day, events) {
|
||||
var checkInResult =
|
||||
events.whereType<SnCheckInResult>().firstOrNull;
|
||||
if (checkInResult != null) {
|
||||
return Positioned(
|
||||
top: 32,
|
||||
child: Text(
|
||||
['大凶', '凶', '中平', '吉', '大吉'][checkInResult.level],
|
||||
style: TextStyle(
|
||||
fontSize: 9,
|
||||
color:
|
||||
isSameDay(selectedDay.value, day)
|
||||
? Theme.of(context).colorScheme.onPrimary
|
||||
: Theme.of(context).colorScheme.onSurface,
|
||||
),
|
||||
),
|
||||
);
|
||||
}
|
||||
return null;
|
||||
},
|
||||
),
|
||||
);
|
||||
TableCalendar(
|
||||
locale: EasyLocalization.of(context)!.locale.toString(),
|
||||
firstDay: DateTime.now().add(Duration(days: -3650)),
|
||||
lastDay: DateTime.now().add(Duration(days: 3650)),
|
||||
focusedDay: DateTime.utc(
|
||||
selectedYear.value,
|
||||
selectedMonth.value,
|
||||
DateTime.now().day,
|
||||
),
|
||||
calendarFormat: CalendarFormat.month,
|
||||
selectedDayPredicate: (day) {
|
||||
return isSameDay(selectedDay.value, day);
|
||||
},
|
||||
onDaySelected: (value, _) {
|
||||
selectedDay.value = value;
|
||||
},
|
||||
onPageChanged: (focusedDay) {
|
||||
selectedMonth.value = focusedDay.month;
|
||||
selectedYear.value = focusedDay.year;
|
||||
},
|
||||
eventLoader: (day) {
|
||||
return events.value
|
||||
?.where((e) => isSameDay(e.date, day))
|
||||
.expand((e) => [...e.statuses, e.checkInResult])
|
||||
.where((e) => e != null)
|
||||
.toList() ??
|
||||
[];
|
||||
},
|
||||
calendarBuilders: CalendarBuilders(
|
||||
dowBuilder: (context, day) {
|
||||
final text = DateFormat.EEEEE().format(day);
|
||||
return Center(child: Text(text));
|
||||
},
|
||||
markerBuilder: (context, day, events) {
|
||||
var checkInResult =
|
||||
events.whereType<SnCheckInResult>().firstOrNull;
|
||||
if (checkInResult != null) {
|
||||
return Positioned(
|
||||
top: 32,
|
||||
child: Text(
|
||||
['大凶', '凶', '中平', '吉', '大吉'][checkInResult.level],
|
||||
style: TextStyle(
|
||||
fontSize: 9,
|
||||
color:
|
||||
isSameDay(selectedDay.value, day)
|
||||
? Theme.of(context).colorScheme.onPrimary
|
||||
: Theme.of(context).colorScheme.onSurface,
|
||||
),
|
||||
),
|
||||
);
|
||||
}
|
||||
return null;
|
||||
},
|
||||
loading: () => const Center(child: CircularProgressIndicator()),
|
||||
error:
|
||||
(error, stack) =>
|
||||
Center(child: Text('Error loading calendar: $error')),
|
||||
),
|
||||
),
|
||||
const Divider(height: 1),
|
||||
const Divider(height: 1).padding(top: 8),
|
||||
AnimatedSwitcher(
|
||||
duration: const Duration(milliseconds: 300),
|
||||
child: Builder(
|
||||
@ -107,30 +130,27 @@ class MyselfEventCalendarScreen extends HookConsumerWidget {
|
||||
events.value
|
||||
?.where((e) => isSameDay(e.date, selectedDay.value))
|
||||
.firstOrNull;
|
||||
if (event == null) {
|
||||
return Center(child: Text('eventCalanderEmpty').tr());
|
||||
}
|
||||
return Column(
|
||||
crossAxisAlignment: CrossAxisAlignment.stretch,
|
||||
children: [
|
||||
Text(DateFormat.EEEE().format(event.date))
|
||||
Text(DateFormat.EEEE().format(selectedDay.value))
|
||||
.fontSize(16)
|
||||
.bold()
|
||||
.textColor(
|
||||
Theme.of(context).colorScheme.onSecondaryContainer,
|
||||
),
|
||||
Text(DateFormat.yMd().format(event.date))
|
||||
Text(DateFormat.yMd().format(selectedDay.value))
|
||||
.fontSize(12)
|
||||
.textColor(
|
||||
Theme.of(context).colorScheme.onSecondaryContainer,
|
||||
),
|
||||
const Gap(16),
|
||||
if (event.checkInResult != null)
|
||||
if (event?.checkInResult != null)
|
||||
Column(
|
||||
crossAxisAlignment: CrossAxisAlignment.stretch,
|
||||
children: [
|
||||
Text(
|
||||
'checkInResultLevel${event.checkInResult!.level}',
|
||||
'checkInResultLevel${event!.checkInResult!.level}',
|
||||
).tr().fontSize(16).bold(),
|
||||
for (final tip in event.checkInResult!.tips)
|
||||
Row(
|
||||
@ -156,7 +176,8 @@ class MyselfEventCalendarScreen extends HookConsumerWidget {
|
||||
).padding(top: 8),
|
||||
],
|
||||
),
|
||||
if (event.checkInResult == null && event.statuses.isEmpty)
|
||||
if (event?.checkInResult == null &&
|
||||
(event?.statuses.isEmpty ?? true))
|
||||
Text('eventCalanderEmpty').tr(),
|
||||
],
|
||||
).padding(vertical: 24, horizontal: 24);
|
||||
|
148
lib/screens/account/me/event_calendar.freezed.dart
Normal file
148
lib/screens/account/me/event_calendar.freezed.dart
Normal file
@ -0,0 +1,148 @@
|
||||
// dart format width=80
|
||||
// coverage:ignore-file
|
||||
// GENERATED CODE - DO NOT MODIFY BY HAND
|
||||
// ignore_for_file: type=lint
|
||||
// ignore_for_file: unused_element, deprecated_member_use, deprecated_member_use_from_same_package, use_function_type_syntax_for_parameters, unnecessary_const, avoid_init_to_null, invalid_override_different_default_values_named, prefer_expression_function_bodies, annotate_overrides, invalid_annotation_target, unnecessary_question_mark
|
||||
|
||||
part of 'event_calendar.dart';
|
||||
|
||||
// **************************************************************************
|
||||
// FreezedGenerator
|
||||
// **************************************************************************
|
||||
|
||||
// dart format off
|
||||
T _$identity<T>(T value) => value;
|
||||
/// @nodoc
|
||||
mixin _$EventCalendarQuery {
|
||||
|
||||
String? get uname; int get year; int get month;
|
||||
/// Create a copy of EventCalendarQuery
|
||||
/// with the given fields replaced by the non-null parameter values.
|
||||
@JsonKey(includeFromJson: false, includeToJson: false)
|
||||
@pragma('vm:prefer-inline')
|
||||
$EventCalendarQueryCopyWith<EventCalendarQuery> get copyWith => _$EventCalendarQueryCopyWithImpl<EventCalendarQuery>(this as EventCalendarQuery, _$identity);
|
||||
|
||||
|
||||
|
||||
@override
|
||||
bool operator ==(Object other) {
|
||||
return identical(this, other) || (other.runtimeType == runtimeType&&other is EventCalendarQuery&&(identical(other.uname, uname) || other.uname == uname)&&(identical(other.year, year) || other.year == year)&&(identical(other.month, month) || other.month == month));
|
||||
}
|
||||
|
||||
|
||||
@override
|
||||
int get hashCode => Object.hash(runtimeType,uname,year,month);
|
||||
|
||||
@override
|
||||
String toString() {
|
||||
return 'EventCalendarQuery(uname: $uname, year: $year, month: $month)';
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
/// @nodoc
|
||||
abstract mixin class $EventCalendarQueryCopyWith<$Res> {
|
||||
factory $EventCalendarQueryCopyWith(EventCalendarQuery value, $Res Function(EventCalendarQuery) _then) = _$EventCalendarQueryCopyWithImpl;
|
||||
@useResult
|
||||
$Res call({
|
||||
String? uname, int year, int month
|
||||
});
|
||||
|
||||
|
||||
|
||||
|
||||
}
|
||||
/// @nodoc
|
||||
class _$EventCalendarQueryCopyWithImpl<$Res>
|
||||
implements $EventCalendarQueryCopyWith<$Res> {
|
||||
_$EventCalendarQueryCopyWithImpl(this._self, this._then);
|
||||
|
||||
final EventCalendarQuery _self;
|
||||
final $Res Function(EventCalendarQuery) _then;
|
||||
|
||||
/// Create a copy of EventCalendarQuery
|
||||
/// with the given fields replaced by the non-null parameter values.
|
||||
@pragma('vm:prefer-inline') @override $Res call({Object? uname = freezed,Object? year = null,Object? month = null,}) {
|
||||
return _then(_self.copyWith(
|
||||
uname: freezed == uname ? _self.uname : uname // ignore: cast_nullable_to_non_nullable
|
||||
as String?,year: null == year ? _self.year : year // ignore: cast_nullable_to_non_nullable
|
||||
as int,month: null == month ? _self.month : month // ignore: cast_nullable_to_non_nullable
|
||||
as int,
|
||||
));
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
/// @nodoc
|
||||
|
||||
|
||||
class _EventCalendarQuery implements EventCalendarQuery {
|
||||
const _EventCalendarQuery({required this.uname, required this.year, required this.month});
|
||||
|
||||
|
||||
@override final String? uname;
|
||||
@override final int year;
|
||||
@override final int month;
|
||||
|
||||
/// Create a copy of EventCalendarQuery
|
||||
/// with the given fields replaced by the non-null parameter values.
|
||||
@override @JsonKey(includeFromJson: false, includeToJson: false)
|
||||
@pragma('vm:prefer-inline')
|
||||
_$EventCalendarQueryCopyWith<_EventCalendarQuery> get copyWith => __$EventCalendarQueryCopyWithImpl<_EventCalendarQuery>(this, _$identity);
|
||||
|
||||
|
||||
|
||||
@override
|
||||
bool operator ==(Object other) {
|
||||
return identical(this, other) || (other.runtimeType == runtimeType&&other is _EventCalendarQuery&&(identical(other.uname, uname) || other.uname == uname)&&(identical(other.year, year) || other.year == year)&&(identical(other.month, month) || other.month == month));
|
||||
}
|
||||
|
||||
|
||||
@override
|
||||
int get hashCode => Object.hash(runtimeType,uname,year,month);
|
||||
|
||||
@override
|
||||
String toString() {
|
||||
return 'EventCalendarQuery(uname: $uname, year: $year, month: $month)';
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
/// @nodoc
|
||||
abstract mixin class _$EventCalendarQueryCopyWith<$Res> implements $EventCalendarQueryCopyWith<$Res> {
|
||||
factory _$EventCalendarQueryCopyWith(_EventCalendarQuery value, $Res Function(_EventCalendarQuery) _then) = __$EventCalendarQueryCopyWithImpl;
|
||||
@override @useResult
|
||||
$Res call({
|
||||
String? uname, int year, int month
|
||||
});
|
||||
|
||||
|
||||
|
||||
|
||||
}
|
||||
/// @nodoc
|
||||
class __$EventCalendarQueryCopyWithImpl<$Res>
|
||||
implements _$EventCalendarQueryCopyWith<$Res> {
|
||||
__$EventCalendarQueryCopyWithImpl(this._self, this._then);
|
||||
|
||||
final _EventCalendarQuery _self;
|
||||
final $Res Function(_EventCalendarQuery) _then;
|
||||
|
||||
/// Create a copy of EventCalendarQuery
|
||||
/// with the given fields replaced by the non-null parameter values.
|
||||
@override @pragma('vm:prefer-inline') $Res call({Object? uname = freezed,Object? year = null,Object? month = null,}) {
|
||||
return _then(_EventCalendarQuery(
|
||||
uname: freezed == uname ? _self.uname : uname // ignore: cast_nullable_to_non_nullable
|
||||
as String?,year: null == year ? _self.year : year // ignore: cast_nullable_to_non_nullable
|
||||
as int,month: null == month ? _self.month : month // ignore: cast_nullable_to_non_nullable
|
||||
as int,
|
||||
));
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
// dart format on
|
@ -6,26 +6,155 @@ part of 'event_calendar.dart';
|
||||
// RiverpodGenerator
|
||||
// **************************************************************************
|
||||
|
||||
String _$myselfAccountEventCalendarHash() =>
|
||||
r'd3faad342d5104e87ff6597ab459e65cb5f4ef97';
|
||||
String _$accountEventCalendarHash() =>
|
||||
r'57405caaf53a83d121b6bb4b70540134fb581525';
|
||||
|
||||
/// See also [myselfAccountEventCalendar].
|
||||
@ProviderFor(myselfAccountEventCalendar)
|
||||
final myselfAccountEventCalendarProvider =
|
||||
AutoDisposeFutureProvider<List<SnEventCalendarEntry>>.internal(
|
||||
myselfAccountEventCalendar,
|
||||
name: r'myselfAccountEventCalendarProvider',
|
||||
debugGetCreateSourceHash:
|
||||
const bool.fromEnvironment('dart.vm.product')
|
||||
? null
|
||||
: _$myselfAccountEventCalendarHash,
|
||||
dependencies: null,
|
||||
allTransitiveDependencies: null,
|
||||
/// Copied from Dart SDK
|
||||
class _SystemHash {
|
||||
_SystemHash._();
|
||||
|
||||
static int combine(int hash, int value) {
|
||||
// ignore: parameter_assignments
|
||||
hash = 0x1fffffff & (hash + value);
|
||||
// ignore: parameter_assignments
|
||||
hash = 0x1fffffff & (hash + ((0x0007ffff & hash) << 10));
|
||||
return hash ^ (hash >> 6);
|
||||
}
|
||||
|
||||
static int finish(int hash) {
|
||||
// ignore: parameter_assignments
|
||||
hash = 0x1fffffff & (hash + ((0x03ffffff & hash) << 3));
|
||||
// ignore: parameter_assignments
|
||||
hash = hash ^ (hash >> 11);
|
||||
return 0x1fffffff & (hash + ((0x00003fff & hash) << 15));
|
||||
}
|
||||
}
|
||||
|
||||
/// See also [accountEventCalendar].
|
||||
@ProviderFor(accountEventCalendar)
|
||||
const accountEventCalendarProvider = AccountEventCalendarFamily();
|
||||
|
||||
/// See also [accountEventCalendar].
|
||||
class AccountEventCalendarFamily
|
||||
extends Family<AsyncValue<List<SnEventCalendarEntry>>> {
|
||||
/// See also [accountEventCalendar].
|
||||
const AccountEventCalendarFamily();
|
||||
|
||||
/// See also [accountEventCalendar].
|
||||
AccountEventCalendarProvider call(EventCalendarQuery query) {
|
||||
return AccountEventCalendarProvider(query);
|
||||
}
|
||||
|
||||
@override
|
||||
AccountEventCalendarProvider getProviderOverride(
|
||||
covariant AccountEventCalendarProvider provider,
|
||||
) {
|
||||
return call(provider.query);
|
||||
}
|
||||
|
||||
static const Iterable<ProviderOrFamily>? _dependencies = null;
|
||||
|
||||
@override
|
||||
Iterable<ProviderOrFamily>? get dependencies => _dependencies;
|
||||
|
||||
static const Iterable<ProviderOrFamily>? _allTransitiveDependencies = null;
|
||||
|
||||
@override
|
||||
Iterable<ProviderOrFamily>? get allTransitiveDependencies =>
|
||||
_allTransitiveDependencies;
|
||||
|
||||
@override
|
||||
String? get name => r'accountEventCalendarProvider';
|
||||
}
|
||||
|
||||
/// See also [accountEventCalendar].
|
||||
class AccountEventCalendarProvider
|
||||
extends AutoDisposeFutureProvider<List<SnEventCalendarEntry>> {
|
||||
/// See also [accountEventCalendar].
|
||||
AccountEventCalendarProvider(EventCalendarQuery query)
|
||||
: this._internal(
|
||||
(ref) => accountEventCalendar(ref as AccountEventCalendarRef, query),
|
||||
from: accountEventCalendarProvider,
|
||||
name: r'accountEventCalendarProvider',
|
||||
debugGetCreateSourceHash:
|
||||
const bool.fromEnvironment('dart.vm.product')
|
||||
? null
|
||||
: _$accountEventCalendarHash,
|
||||
dependencies: AccountEventCalendarFamily._dependencies,
|
||||
allTransitiveDependencies:
|
||||
AccountEventCalendarFamily._allTransitiveDependencies,
|
||||
query: query,
|
||||
);
|
||||
|
||||
AccountEventCalendarProvider._internal(
|
||||
super._createNotifier, {
|
||||
required super.name,
|
||||
required super.dependencies,
|
||||
required super.allTransitiveDependencies,
|
||||
required super.debugGetCreateSourceHash,
|
||||
required super.from,
|
||||
required this.query,
|
||||
}) : super.internal();
|
||||
|
||||
final EventCalendarQuery query;
|
||||
|
||||
@override
|
||||
Override overrideWith(
|
||||
FutureOr<List<SnEventCalendarEntry>> Function(
|
||||
AccountEventCalendarRef provider,
|
||||
)
|
||||
create,
|
||||
) {
|
||||
return ProviderOverride(
|
||||
origin: this,
|
||||
override: AccountEventCalendarProvider._internal(
|
||||
(ref) => create(ref as AccountEventCalendarRef),
|
||||
from: from,
|
||||
name: null,
|
||||
dependencies: null,
|
||||
allTransitiveDependencies: null,
|
||||
debugGetCreateSourceHash: null,
|
||||
query: query,
|
||||
),
|
||||
);
|
||||
}
|
||||
|
||||
@override
|
||||
AutoDisposeFutureProviderElement<List<SnEventCalendarEntry>> createElement() {
|
||||
return _AccountEventCalendarProviderElement(this);
|
||||
}
|
||||
|
||||
@override
|
||||
bool operator ==(Object other) {
|
||||
return other is AccountEventCalendarProvider && other.query == query;
|
||||
}
|
||||
|
||||
@override
|
||||
int get hashCode {
|
||||
var hash = _SystemHash.combine(0, runtimeType.hashCode);
|
||||
hash = _SystemHash.combine(hash, query.hashCode);
|
||||
|
||||
return _SystemHash.finish(hash);
|
||||
}
|
||||
}
|
||||
|
||||
@Deprecated('Will be removed in 3.0. Use Ref instead')
|
||||
// ignore: unused_element
|
||||
typedef MyselfAccountEventCalendarRef =
|
||||
AutoDisposeFutureProviderRef<List<SnEventCalendarEntry>>;
|
||||
mixin AccountEventCalendarRef
|
||||
on AutoDisposeFutureProviderRef<List<SnEventCalendarEntry>> {
|
||||
/// The parameter `query` of this provider.
|
||||
EventCalendarQuery get query;
|
||||
}
|
||||
|
||||
class _AccountEventCalendarProviderElement
|
||||
extends AutoDisposeFutureProviderElement<List<SnEventCalendarEntry>>
|
||||
with AccountEventCalendarRef {
|
||||
_AccountEventCalendarProviderElement(super.provider);
|
||||
|
||||
@override
|
||||
EventCalendarQuery get query =>
|
||||
(origin as AccountEventCalendarProvider).query;
|
||||
}
|
||||
|
||||
// ignore_for_file: type=lint
|
||||
// ignore_for_file: subtype_of_sealed_class, invalid_use_of_internal_member, invalid_use_of_visible_for_testing_member, deprecated_member_use_from_same_package
|
||||
|
Loading…
x
Reference in New Issue
Block a user