feat: Android TV support (#503)

Co-authored-by: PartyDonut <PartyDonut@users.noreply.github.com>
This commit is contained in:
PartyDonut 2025-09-28 21:07:49 +02:00 committed by GitHub
parent 7ab8c015b9
commit c299492d6d
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
168 changed files with 12019 additions and 3073 deletions

View file

@ -4,6 +4,7 @@ import 'package:flutter_riverpod/flutter_riverpod.dart';
import 'package:fladder/providers/user_provider.dart';
import 'package:fladder/routes/auto_router.gr.dart';
import 'package:fladder/screens/login/lock_screen.dart';
import 'package:fladder/widgets/navigation_scaffold/components/navigation_body.dart';
const settingsPageRoute = "settings";
@ -53,18 +54,22 @@ final List<AutoRoute> homeRoutes = [
page: DashboardRoute.page,
initial: true,
path: 'dashboard',
maintainState: false,
),
AutoRoute(
page: FavouritesRoute.page,
path: 'favourites',
maintainState: false,
),
AutoRoute(
page: SyncedRoute.page,
path: 'synced',
maintainState: false,
),
AutoRoute(
page: LibraryRoute.page,
path: 'libraries',
maintainState: false,
),
];
@ -76,7 +81,7 @@ final List<AutoRoute> detailsRoutes = [
final List<AutoRoute> _defaultRoutes = [
AutoRoute(page: SplashRoute.page, path: '/splash'),
AutoRoute(page: LoginRoute.page, path: '/login'),
AutoRoute(page: LoginRoute.page, path: '/login', maintainState: false),
];
final List<AutoRoute> _settingsChildren = [
@ -117,6 +122,8 @@ class AuthGuard extends AutoRouteGuard {
if (ref.read(userProvider) != null ||
resolver.routeName == const LoginRoute().routeName ||
resolver.routeName == SplashRoute().routeName) {
// We assume the last main focus is no longer active after navigating
lastMainFocus = null;
return resolver.next(true);
}
@ -127,5 +134,9 @@ class AuthGuard extends AutoRouteGuard {
router.replace(const LoginRoute());
}
}));
// We assume the last main focus is no longer active after navigating
lastMainFocus = null;
return;
}
}

View file

@ -93,11 +93,12 @@ class DetailsRoute extends _i18.PageRouteInfo<DetailsRouteArgs> {
DetailsRoute({
String id = '',
_i19.ItemBaseModel? item,
Object? tag,
_i20.Key? key,
List<_i18.PageRouteInfo>? children,
}) : super(
DetailsRoute.name,
args: DetailsRouteArgs(id: id, item: item, key: key),
args: DetailsRouteArgs(id: id, item: item, tag: tag, key: key),
rawQueryParams: {'id': id},
initialChildren: children,
);
@ -111,34 +112,44 @@ class DetailsRoute extends _i18.PageRouteInfo<DetailsRouteArgs> {
final args = data.argsAs<DetailsRouteArgs>(
orElse: () => DetailsRouteArgs(id: queryParams.getString('id', '')),
);
return _i4.DetailsScreen(id: args.id, item: args.item, key: args.key);
return _i4.DetailsScreen(
id: args.id,
item: args.item,
tag: args.tag,
key: args.key,
);
},
);
}
class DetailsRouteArgs {
const DetailsRouteArgs({this.id = '', this.item, this.key});
const DetailsRouteArgs({this.id = '', this.item, this.tag, this.key});
final String id;
final _i19.ItemBaseModel? item;
final Object? tag;
final _i20.Key? key;
@override
String toString() {
return 'DetailsRouteArgs{id: $id, item: $item, key: $key}';
return 'DetailsRouteArgs{id: $id, item: $item, tag: $tag, key: $key}';
}
@override
bool operator ==(Object other) {
if (identical(this, other)) return true;
if (other is! DetailsRouteArgs) return false;
return id == other.id && item == other.item && key == other.key;
return id == other.id &&
item == other.item &&
tag == other.tag &&
key == other.key;
}
@override
int get hashCode => id.hashCode ^ item.hashCode ^ key.hashCode;
int get hashCode => id.hashCode ^ item.hashCode ^ tag.hashCode ^ key.hashCode;
}
/// generated route for

View file

@ -13,7 +13,13 @@ import 'package:fladder/util/fladder_image.dart';
class DetailsScreen extends ConsumerStatefulWidget {
final String id;
final ItemBaseModel? item;
const DetailsScreen({@QueryParam() this.id = '', this.item, super.key});
final Object? tag;
const DetailsScreen({
@QueryParam() this.id = '',
this.item,
this.tag,
super.key,
});
@override
ConsumerState<ConsumerStatefulWidget> createState() => _DetailsScreenState();
@ -66,7 +72,7 @@ class _DetailsScreenState extends ConsumerState<DetailsScreen> {
key: Key(widget.id),
children: [
Hero(
tag: widget.id,
tag: widget.tag ?? UniqueKey(),
child: Container(
decoration: BoxDecoration(
color: Theme.of(context).colorScheme.surface.withValues(alpha: 1.0),