格式化代码

This commit is contained in:
rang 2025-10-25 10:38:56 +08:00
parent a28547685b
commit b3a9d76c78
24 changed files with 611 additions and 451 deletions

View file

@ -26,8 +26,8 @@ class ExplorePage extends HookConsumerWidget {
@override
Widget build(BuildContext context, WidgetRef ref) {
// hooks for the dark mode
final settings = ref.watch(appSettingsProvider);
final api = ref.watch(authenticatedApiProvider);
ref.watch(appSettingsProvider);
// final api = ref.watch(authenticatedApiProvider);
return Scaffold(
appBar: AppBar(
title: Text(S.of(context).explore),
@ -62,8 +62,8 @@ class MySearchBar extends HookConsumerWidget {
currentQuery = query;
// In a real application, there should be some error handling here.
final options =
await api.libraries.search(libraryId: settings.activeLibraryId!, query: query, limit: 3);
final options = await api.libraries
.search(libraryId: settings.activeLibraryId!, query: query, limit: 3);
// If another search happened after this one, throw away these options.
if (currentQuery != query) {
@ -98,7 +98,10 @@ class MySearchBar extends HookConsumerWidget {
// opacity: 0.5 for the hint text
hintStyle: WidgetStatePropertyAll(
Theme.of(context).textTheme.bodyMedium!.copyWith(
color: Theme.of(context).colorScheme.onSurface.withValues(alpha: 0.5),
color: Theme.of(context)
.colorScheme
.onSurface
.withValues(alpha: 0.5),
),
),
textInputAction: TextInputAction.search,
@ -231,8 +234,9 @@ class BookSearchResultMini extends HookConsumerWidget {
@override
Widget build(BuildContext context, WidgetRef ref) {
final item = ref.watch(libraryItemProvider(book.libraryItemId)).valueOrNull;
final image =
item == null ? const AsyncValue.loading() : ref.watch(coverImageProvider(item.id));
final image = item == null
? const AsyncValue.loading()
: ref.watch(coverImageProvider(item.id));
return ListTile(
leading: SizedBox(
width: 50,

View file

@ -77,9 +77,11 @@ class LibraryItemActions extends HookConsumerWidget {
IconButton(
onPressed: () {
appLogger.fine('Sharing');
var currentServerUrl = apiSettings.activeServer!.serverUrl;
var currentServerUrl =
apiSettings.activeServer!.serverUrl;
if (!currentServerUrl.hasScheme) {
currentServerUrl = Uri.https(currentServerUrl.toString());
currentServerUrl =
Uri.https(currentServerUrl.toString());
}
handleLaunchUrl(
Uri.parse(
@ -138,7 +140,8 @@ class LibraryItemActions extends HookConsumerWidget {
FileDownloader()
.database
.deleteRecordWithId(
record.task.taskId,
record
.task.taskId,
);
Navigator.pop(context);
},
@ -157,7 +160,8 @@ class LibraryItemActions extends HookConsumerWidget {
},
onTap: () async {
// open the file location
final didOpen = await FileDownloader().openFile(
final didOpen =
await FileDownloader().openFile(
task: record.task,
);
@ -226,7 +230,9 @@ class LibItemDownloadButton extends HookConsumerWidget {
onPressed: () {
appLogger.fine('Pressed download button');
ref.read(downloadManagerProvider.notifier).queueAudioBookDownload(item);
ref
.read(downloadManagerProvider.notifier)
.queueAudioBookDownload(item);
},
icon: const Icon(
Icons.download_rounded,
@ -245,7 +251,10 @@ class ItemCurrentlyInDownloadQueue extends HookConsumerWidget {
@override
Widget build(BuildContext context, WidgetRef ref) {
final progress = ref.watch(itemDownloadProgressProvider(item.id)).valueOrNull?.clamp(0.05, 1.0);
final progress = ref
.watch(itemDownloadProgressProvider(item.id))
.valueOrNull
?.clamp(0.05, 1.0);
if (progress == 1) {
return AlreadyItemDownloadedButton(item: item);
@ -333,7 +342,7 @@ class DownloadSheet extends HookConsumerWidget {
@override
Widget build(BuildContext context, WidgetRef ref) {
final manager = ref.watch(downloadManagerProvider);
// final manager = ref.watch(downloadManagerProvider);
return Column(
mainAxisSize: MainAxisSize.min,
@ -377,7 +386,9 @@ class DownloadSheet extends HookConsumerWidget {
TextButton(
onPressed: () {
// delete the file
ref.read(downloadManagerProvider.notifier).deleteDownloadedItem(
ref
.read(downloadManagerProvider.notifier)
.deleteDownloadedItem(
item,
);
GoRouter.of(context).pop(true);
@ -396,7 +407,8 @@ class DownloadSheet extends HookConsumerWidget {
);
if (wasDeleted ?? false) {
appLogger.fine(S.of(context).deleted(item.media.metadata.title ?? ''));
appLogger
.fine(S.of(context).deleted(item.media.metadata.title ?? ''));
GoRouter.of(context).pop();
ScaffoldMessenger.of(context).showSnackBar(
SnackBar(
@ -520,7 +532,8 @@ Future<void> libraryItemPlayButtonOnPressed({
appLogger.info('Setting the book ${book.libraryItemId}');
appLogger.info('Initial position: ${userMediaProgress?.currentTime}');
final downloadManager = ref.watch(simpleDownloadManagerProvider);
final libItem = await ref.read(libraryItemProvider(book.libraryItemId).future);
final libItem =
await ref.read(libraryItemProvider(book.libraryItemId).future);
final downloadedUris = await downloadManager.getDownloadedFilesUri(libItem);
setSourceFuture = player.setSourceAudiobook(
book,
@ -536,23 +549,27 @@ Future<void> libraryItemPlayButtonOnPressed({
}
}
// set the volume as this is the first time playing and dismissing causes the volume to go to 0
var bookPlayerSettings = ref.read(bookSettingsProvider(book.libraryItemId)).playerSettings;
var bookPlayerSettings =
ref.read(bookSettingsProvider(book.libraryItemId)).playerSettings;
var appPlayerSettings = ref.read(appSettingsProvider).playerSettings;
var configurePlayerForEveryBook = appPlayerSettings.configurePlayerForEveryBook;
var configurePlayerForEveryBook =
appPlayerSettings.configurePlayerForEveryBook;
await Future.wait([
setSourceFuture ?? Future.value(),
// set the volume
player.setVolume(
configurePlayerForEveryBook
? bookPlayerSettings.preferredDefaultVolume ?? appPlayerSettings.preferredDefaultVolume
? bookPlayerSettings.preferredDefaultVolume ??
appPlayerSettings.preferredDefaultVolume
: appPlayerSettings.preferredDefaultVolume,
),
// set the speed
player.setSpeed(
configurePlayerForEveryBook
? bookPlayerSettings.preferredDefaultSpeed ?? appPlayerSettings.preferredDefaultSpeed
? bookPlayerSettings.preferredDefaultSpeed ??
appPlayerSettings.preferredDefaultSpeed
: appPlayerSettings.preferredDefaultSpeed,
),
]);

View file

@ -25,8 +25,9 @@ class LibraryItemMetadata extends HookConsumerWidget {
if (book == null) {
return null;
}
final duration =
book.audioFiles.map((e) => e.duration).reduce((value, element) => value + element);
final duration = book.audioFiles
.map((e) => e.duration)
.reduce((value, element) => value + element);
final hours = duration.inHours;
final minutes = duration.inMinutes.remainder(60);
return '${hours}h ${minutes}m';
@ -41,8 +42,9 @@ class LibraryItemMetadata extends HookConsumerWidget {
if (book == null) {
return null;
}
final size =
book.audioFiles.map((e) => e.metadata.size).reduce((value, element) => value + element);
final size = book.audioFiles
.map((e) => e.metadata.size)
.reduce((value, element) => value + element);
if (size / 1024 / 1024 < 1024) {
return '${(size / 1024 / 1024).toStringAsFixed(2)} MB';
}
@ -98,7 +100,10 @@ class LibraryItemMetadata extends HookConsumerWidget {
return VerticalDivider(
indent: 6,
endIndent: 6,
color: Theme.of(context).colorScheme.onSurface.withValues(alpha: 0.6),
color: Theme.of(context)
.colorScheme
.onSurface
.withValues(alpha: 0.6),
);
},
),

View file

@ -28,7 +28,8 @@ class LibraryItemPage extends HookConsumerWidget {
static const double _showFabThreshold = 300.0;
@override
Widget build(BuildContext context, WidgetRef ref) {
final additionalItemData = extra is LibraryItemExtras ? extra as LibraryItemExtras : null;
final additionalItemData =
extra is LibraryItemExtras ? extra as LibraryItemExtras : null;
final scrollController = useScrollController();
final showFab = useState(false);
@ -151,7 +152,8 @@ class LibraryItemDescription extends HookConsumerWidget {
}
return ExpandableDescription(
title: S.of(context).bookAbout,
content: item.media.metadata.description ?? S.of(context).bookAboutDefault,
content:
item.media.metadata.description ?? S.of(context).bookAboutDefault,
readMoreText: S.of(context).readMore,
readLessText: S.of(context).readLess,
);
@ -168,8 +170,10 @@ double calculateWidth(
/// height ratio of the cover image to the available height
double maxHeightToUse = 0.25,
}) {
final availHeight = min(constraints.maxHeight, MediaQuery.of(context).size.height);
final availWidth = min(constraints.maxWidth, MediaQuery.of(context).size.width);
final availHeight =
min(constraints.maxHeight, MediaQuery.of(context).size.height);
final availWidth =
min(constraints.maxWidth, MediaQuery.of(context).size.width);
// make the width widthRatio of the available width
var width = availWidth * widthRatio;

View file

@ -2,11 +2,13 @@ import 'package:flutter/material.dart';
import 'package:go_router/go_router.dart';
import 'package:hooks_riverpod/hooks_riverpod.dart';
import 'package:vaani/api/library_provider.dart' show currentLibraryProvider;
import 'package:vaani/features/you/view/widgets/library_switch_chip.dart' show showLibrarySwitcher;
import 'package:vaani/features/you/view/widgets/library_switch_chip.dart'
show showLibrarySwitcher;
import 'package:vaani/generated/l10n.dart';
import 'package:vaani/router/router.dart' show Routes;
import 'package:vaani/shared/icons/abs_icons.dart' show AbsIcons;
import 'package:vaani/shared/widgets/not_implemented.dart' show showNotImplementedToast;
import 'package:vaani/shared/widgets/not_implemented.dart'
show showNotImplementedToast;
class LibraryBrowserPage extends HookConsumerWidget {
const LibraryBrowserPage({super.key});
@ -32,7 +34,9 @@ class LibraryBrowserPage extends HookConsumerWidget {
// true, // Optional: uncomment if you want snapping behavior (usually with floating: true)
leading: IconButton(
icon: Icon(libraryIconData),
tooltip: S.of(context).librarySwitchTooltip, // Helpful tooltip for users
tooltip: S
.of(context)
.librarySwitchTooltip, // Helpful tooltip for users
onPressed: () {
showLibrarySwitcher(context, ref);
},

View file

@ -1,7 +1,8 @@
import 'package:logging/logging.dart';
import 'package:riverpod_annotation/riverpod_annotation.dart';
import 'package:vaani/db/available_boxes.dart';
import 'package:vaani/features/per_book_settings/models/book_settings.dart' as model;
import 'package:vaani/features/per_book_settings/models/book_settings.dart'
as model;
import 'package:vaani/features/per_book_settings/models/nullable_player_settings.dart';
part 'book_settings_provider.g.dart';

View file

@ -122,9 +122,11 @@ class AudiobookPlayer extends AudioPlayer {
final trackToPlay = getTrackToPlay(book, initialPosition ?? Duration.zero);
final initialIndex = book.tracks.indexOf(trackToPlay);
final initialPositionInTrack =
initialPosition != null ? initialPosition - trackToPlay.startOffset : null;
await setAudioSourceTrack(initialIndex, initialPosition: initialPositionInTrack);
final initialPositionInTrack = initialPosition != null
? initialPosition - trackToPlay.startOffset
: null;
await setAudioSourceTrack(initialIndex,
initialPosition: initialPositionInTrack);
// _logger.finer('Setting audioSource');
// await setAudioSource(
// preload: preload,
@ -158,7 +160,8 @@ class AudiobookPlayer extends AudioPlayer {
// });
}
Future<void> setAudioSourceTrack(int index, {Duration? initialPosition}) async {
Future<void> setAudioSourceTrack(int index,
{Duration? initialPosition}) async {
if (_book == null) {
return stop();
}
@ -168,9 +171,11 @@ class AudiobookPlayer extends AudioPlayer {
_currentIndex = index;
AudioTrack track = _book!.tracks[index];
final appSettings = loadOrCreateAppSettings();
final playerSettings = readFromBoxOrCreate(_book!.libraryItemId).playerSettings;
final playerSettings =
readFromBoxOrCreate(_book!.libraryItemId).playerSettings;
final retrievedUri = _getUri(track, _downloadedUris, baseUrl: baseUrl, token: token);
final retrievedUri =
_getUri(track, _downloadedUris, baseUrl: baseUrl, token: token);
await setAudioSource(
initialPosition: initialPosition == null || initialPosition <= Duration()
@ -185,8 +190,10 @@ class AudiobookPlayer extends AudioPlayer {
// Specify a unique ID for each media item:
id: '${book?.libraryItemId}${track.index}',
// Metadata to display in the notification:
title: appSettings.notificationSettings.primaryTitle.formatNotificationTitle(book!),
album: appSettings.notificationSettings.secondaryTitle.formatNotificationTitle(book!),
title: appSettings.notificationSettings.primaryTitle
.formatNotificationTitle(book!),
album: appSettings.notificationSettings.secondaryTitle
.formatNotificationTitle(book!),
artUri: Uri.parse(
'$baseUrl/api/items/${book?.libraryItemId}/cover?token=$token&width=800',
),
@ -392,7 +399,8 @@ Uri _getUri(
},
);
return uri ?? Uri.parse('${baseUrl.toString()}${track.contentUrl}?token=$token');
return uri ??
Uri.parse('${baseUrl.toString()}${track.contentUrl}?token=$token');
}
extension FormatNotificationTitle on String {

View file

@ -31,7 +31,8 @@ class AudiobookPlayer extends HookConsumerWidget {
if (currentBook == null) {
return const SizedBox.shrink();
}
final itemBeingPlayed = ref.watch(libraryItemProvider(currentBook.libraryItemId));
final itemBeingPlayed =
ref.watch(libraryItemProvider(currentBook.libraryItemId));
final player = ref.watch(audiobookPlayerProvider);
final imageOfItemBeingPlayed = itemBeingPlayed.valueOrNull != null
? ref.watch(
@ -64,7 +65,8 @@ class AudiobookPlayer extends HookConsumerWidget {
themeOfLibraryItemProvider(
itemBeingPlayed.valueOrNull?.id,
brightness: Theme.of(context).brightness,
highContrast: appSettings.themeSettings.highContrast || MediaQuery.of(context).highContrast,
highContrast: appSettings.themeSettings.highContrast ||
MediaQuery.of(context).highContrast,
),
);
@ -86,7 +88,8 @@ class AudiobookPlayer extends HookConsumerWidget {
onDragDown: (percentage) async {
// preferred volume
// set volume to 0 when dragging down
await player.setVolume(preferredVolume * (1 - percentage.clamp(0, .75)));
await player
.setVolume(preferredVolume * (1 - percentage.clamp(0, .75)));
},
minHeight: playerMinHeight,
// subtract the height of notches and other system UI
@ -106,8 +109,10 @@ class AudiobookPlayer extends HookConsumerWidget {
// at what point should the player switch from miniplayer to expanded player
// also at this point the image should be at its max size and in the center of the player
final miniplayerPercentageDeclaration =
(maxImgSize - playerMinHeight) / (playerMaxHeight - playerMinHeight);
final bool isFormMiniplayer = percentage < miniplayerPercentageDeclaration;
(maxImgSize - playerMinHeight) /
(playerMaxHeight - playerMinHeight);
final bool isFormMiniplayer =
percentage < miniplayerPercentageDeclaration;
if (!isFormMiniplayer) {
// this calculation needs a refactor
@ -207,14 +212,17 @@ class AudiobookChapterProgressBar extends HookConsumerWidget {
// now find the chapter that corresponds to the current time
// and calculate the progress of the current chapter
final currentChapterProgress =
currentChapter == null ? null : (player.positionInBook - currentChapter.start);
final currentChapterProgress = currentChapter == null
? null
: (player.positionInBook - currentChapter.start);
final currentChapterBuffered =
currentChapter == null ? null : (player.bufferedPositionInBook - currentChapter.start);
final currentChapterBuffered = currentChapter == null
? null
: (player.bufferedPositionInBook - currentChapter.start);
return ProgressBar(
progress: currentChapterProgress ?? position.data ?? const Duration(seconds: 0),
progress:
currentChapterProgress ?? position.data ?? const Duration(seconds: 0),
total: currentChapter == null
? player.book?.duration ?? const Duration(seconds: 0)
: currentChapter.end - currentChapter.start,
@ -226,7 +234,8 @@ class AudiobookChapterProgressBar extends HookConsumerWidget {
player.seek(duration);
},
thumbRadius: 8,
buffered: currentChapterBuffered ?? buffered.data ?? const Duration(seconds: 0),
buffered:
currentChapterBuffered ?? buffered.data ?? const Duration(seconds: 0),
bufferedBarColor: Theme.of(context).colorScheme.secondary,
timeLabelType: TimeLabelType.remainingTime,
timeLabelLocation: TimeLabelLocation.below,

View file

@ -105,7 +105,10 @@ class PlayerWhenExpanded extends HookConsumerWidget {
decoration: BoxDecoration(
boxShadow: [
BoxShadow(
color: Theme.of(context).colorScheme.primary.withValues(alpha: 0.1),
color: Theme.of(context)
.colorScheme
.primary
.withValues(alpha: 0.1),
blurRadius: 32 * earlyPercentage,
spreadRadius: 8 * earlyPercentage,
// offset: Offset(0, 16 * earlyPercentage),
@ -171,7 +174,10 @@ class PlayerWhenExpanded extends HookConsumerWidget {
currentBookMetadata?.authorName ?? '',
].join(' - '),
style: Theme.of(context).textTheme.titleMedium?.copyWith(
color: Theme.of(context).colorScheme.onSurface.withValues(alpha: 0.7),
color: Theme.of(context)
.colorScheme
.onSurface
.withValues(alpha: 0.7),
),
maxLines: 1,
overflow: TextOverflow.ellipsis,

View file

@ -34,7 +34,8 @@ class PlayerWhenMinimized extends HookConsumerWidget {
final currentChapter = ref.watch(currentPlayingChapterProvider);
final vanishingPercentage = 1 - percentageMiniplayer;
final progress = useStream(player.slowPositionStreamInBook, initialData: Duration.zero);
final progress =
useStream(player.slowPositionStreamInBook, initialData: Duration.zero);
final bookMetaExpanded = ref.watch(currentBookMetadataProvider);
@ -56,7 +57,8 @@ class PlayerWhenMinimized extends HookConsumerWidget {
context.pushNamed(
Routes.libraryItem.name,
pathParameters: {
Routes.libraryItem.pathParamName!: player.book!.libraryItemId,
Routes.libraryItem.pathParamName!:
player.book!.libraryItemId,
},
);
},
@ -90,7 +92,10 @@ class PlayerWhenMinimized extends HookConsumerWidget {
maxLines: 1,
overflow: TextOverflow.ellipsis,
style: Theme.of(context).textTheme.bodyMedium!.copyWith(
color: Theme.of(context).colorScheme.onSurface.withValues(alpha: 0.7),
color: Theme.of(context)
.colorScheme
.onSurface
.withValues(alpha: 0.7),
),
),
],
@ -134,7 +139,8 @@ class PlayerWhenMinimized extends HookConsumerWidget {
SizedBox(
height: barHeight,
child: LinearProgressIndicator(
value: (progress.data ?? Duration.zero).inSeconds / player.book!.duration.inSeconds,
value: (progress.data ?? Duration.zero).inSeconds /
player.book!.duration.inSeconds,
color: Theme.of(context).colorScheme.onPrimaryContainer,
backgroundColor: Theme.of(context).colorScheme.primaryContainer,
),

View file

@ -1,14 +1,17 @@
import 'package:flutter/material.dart';
import 'package:flutter_animate/flutter_animate.dart';
import 'package:hooks_riverpod/hooks_riverpod.dart';
import 'package:vaani/features/player/providers/audiobook_player.dart' show audiobookPlayerProvider;
import 'package:vaani/features/player/providers/audiobook_player.dart'
show audiobookPlayerProvider;
import 'package:vaani/features/player/providers/currently_playing_provider.dart'
show currentPlayingChapterProvider, currentlyPlayingBookProvider;
import 'package:vaani/features/player/view/player_when_expanded.dart' show pendingPlayerModals;
import 'package:vaani/features/player/view/player_when_expanded.dart'
show pendingPlayerModals;
import 'package:vaani/features/player/view/widgets/playing_indicator_icon.dart';
import 'package:vaani/main.dart' show appLogger;
import 'package:vaani/shared/extensions/chapter.dart' show ChapterDuration;
import 'package:vaani/shared/extensions/duration_format.dart' show DurationFormat;
import 'package:vaani/shared/extensions/duration_format.dart'
show DurationFormat;
import 'package:vaani/shared/hooks.dart' show useTimer;
class ChapterSelectionButton extends HookConsumerWidget {
@ -88,11 +91,13 @@ class ChapterSelectionModal extends HookConsumerWidget {
children: currentBook!.chapters.map(
(chapter) {
final isCurrent = currentChapterIndex == chapter.id;
final isPlayed =
currentChapterIndex != null && chapter.id < currentChapterIndex;
final isPlayed = currentChapterIndex != null &&
chapter.id < currentChapterIndex;
return ListTile(
autofocus: isCurrent,
iconColor: isPlayed && !isCurrent ? theme.disabledColor : null,
iconColor: isPlayed && !isCurrent
? theme.disabledColor
: null,
title: Text(
chapter.title,
style: isPlayed && !isCurrent

View file

@ -50,7 +50,8 @@ class PlayerSkipChapterStartEnd extends HookConsumerWidget {
body: Column(
children: [
ListTile(
title: Text('跳过片头 ${bookSettings.playerSettings.skipChapterStart.inSeconds}s'),
title: Text(
'跳过片头 ${bookSettings.playerSettings.skipChapterStart.inSeconds}s'),
),
Expanded(
child: TimeIntervalSlider(
@ -65,14 +66,16 @@ class PlayerSkipChapterStartEnd extends HookConsumerWidget {
bookSettingsProvider(bookId).notifier,
)
.update(
bookSettings.copyWith.playerSettings(skipChapterStart: interval),
bookSettings.copyWith
.playerSettings(skipChapterStart: interval),
);
ref.read(audiobookPlayerProvider).setClip(start: interval);
},
),
),
ListTile(
title: Text('跳过片尾 ${bookSettings.playerSettings.skipChapterEnd.inSeconds}s'),
title: Text(
'跳过片尾 ${bookSettings.playerSettings.skipChapterEnd.inSeconds}s'),
),
Expanded(
child: TimeIntervalSlider(
@ -87,7 +90,8 @@ class PlayerSkipChapterStartEnd extends HookConsumerWidget {
bookSettingsProvider(bookId).notifier,
)
.update(
bookSettings.copyWith.playerSettings(skipChapterEnd: interval),
bookSettings.copyWith
.playerSettings(skipChapterEnd: interval),
);
},
),

View file

@ -3,7 +3,8 @@ import 'package:hooks_riverpod/hooks_riverpod.dart';
import 'package:shelfsdk/audiobookshelf_api.dart' show Library;
import 'package:vaani/api/library_provider.dart';
import 'package:vaani/generated/l10n.dart';
import 'package:vaani/settings/api_settings_provider.dart' show apiSettingsProvider;
import 'package:vaani/settings/api_settings_provider.dart'
show apiSettingsProvider;
import 'package:vaani/shared/icons/abs_icons.dart';
import 'dart:io' show Platform;
@ -99,7 +100,8 @@ void showLibrarySwitcher(
// Make it scrollable and control height
isScrollControlled: true,
constraints: BoxConstraints(
maxHeight: MediaQuery.of(context).size.height * 0.6, // Max 60% of screen
maxHeight:
MediaQuery.of(context).size.height * 0.6, // Max 60% of screen
),
builder: (sheetContext) => Padding(
// Add padding within the bottom sheet

View file

@ -68,7 +68,8 @@ class YouPage extends HookConsumerWidget {
},
),
librariesAsyncValue.when(
data: (libraries) => LibrarySwitchChip(libraries: libraries),
data: (libraries) =>
LibrarySwitchChip(libraries: libraries),
loading: () => const ActionChip(
avatar: SizedBox(
width: 18,
@ -88,7 +89,8 @@ class YouPage extends HookConsumerWidget {
// Maybe show error details or allow retry
ScaffoldMessenger.of(context).showSnackBar(
SnackBar(
content: Text('Failed to load libraries: $error'),
content:
Text('Failed to load libraries: $error'),
),
);
},
@ -141,7 +143,8 @@ class YouPage extends HookConsumerWidget {
icon: const Icon(Icons.info),
applicationName: AppMetadata.appName,
applicationVersion: AppMetadata.version,
applicationLegalese: 'Made with ❤️ by ${AppMetadata.author}',
applicationLegalese:
'Made with ❤️ by ${AppMetadata.author}',
aboutBoxChildren: [
// link to github repo
ListTile(
@ -216,7 +219,8 @@ class UserBar extends HookConsumerWidget {
Text(
api.baseUrl.toString(),
style: textTheme.bodyMedium?.copyWith(
color: themeData.colorScheme.onSurface.withValues(alpha: 0.6),
color:
themeData.colorScheme.onSurface.withValues(alpha: 0.6),
),
),
],