This commit is contained in:
Forrest 2026-07-29 16:22:00 -04:00
parent fc22d11df1
commit 27a8a62475
32 changed files with 354 additions and 335 deletions

View file

@ -29,14 +29,14 @@ class HomeScreen extends ConsumerWidget {
return ListView(
padding: const EdgeInsets.fromLTRB(
RatuneSpacing.lg,
RatuneSpacing.xl,
RatuneSpacing.lg,
RatuneSpacing.lg,
TimbreSpacing.lg,
TimbreSpacing.xl,
TimbreSpacing.lg,
TimbreSpacing.lg,
),
children: [
const _HeroCard(),
const SizedBox(height: RatuneSpacing.xl),
const SizedBox(height: TimbreSpacing.xl),
// Recently Played — from local history.
if (recentAlbums.isNotEmpty)
@ -93,10 +93,10 @@ class HomeScreen extends ConsumerWidget {
if (recentAlbums.isEmpty && client == null)
const Padding(
padding: EdgeInsets.only(top: RatuneSpacing.xl),
padding: EdgeInsets.only(top: TimbreSpacing.xl),
child: Text(
'Connect to a server and start listening — your home fills in as you play.',
style: TextStyle(color: RatuneColors.dimmed),
style: TextStyle(color: TimbreColors.dimmed),
),
),
],
@ -143,11 +143,11 @@ class _HeroCard extends ConsumerWidget {
child: const Row(
children: [
Icon(Icons.library_music_outlined,
color: RatuneColors.dimmed, size: 40),
SizedBox(width: RatuneSpacing.lg),
color: TimbreColors.dimmed, size: 40),
SizedBox(width: TimbreSpacing.lg),
Expanded(
child: Text('Browse your library to start listening',
style: TextStyle(color: RatuneColors.foreground)),
style: TextStyle(color: TimbreColors.foreground)),
),
],
),
@ -170,19 +170,19 @@ class _HeroCard extends ConsumerWidget {
width: 64,
height: 64,
child: ColoredBox(
color: RatuneColors.surface,
color: TimbreColors.surface,
child: artUri != null
? Image.network(artUri,
key: ValueKey(artUri),
fit: BoxFit.cover,
gaplessPlayback: true,
errorBuilder: (_, _, _) => const Icon(
Icons.album_outlined, color: RatuneColors.dimmed))
Icons.album_outlined, color: TimbreColors.dimmed))
: const Icon(Icons.album_outlined,
color: RatuneColors.dimmed),
color: TimbreColors.dimmed),
),
),
const SizedBox(width: RatuneSpacing.lg),
const SizedBox(width: TimbreSpacing.lg),
Expanded(
child: Column(
crossAxisAlignment: CrossAxisAlignment.start,
@ -192,7 +192,7 @@ class _HeroCard extends ConsumerWidget {
children: [
Icon(hasCurrent ? Icons.play_arrow : Icons.history,
size: 14, color: accent),
const SizedBox(width: RatuneSpacing.xs),
const SizedBox(width: TimbreSpacing.xs),
Text(hasCurrent ? 'NOW PLAYING' : 'RESUME',
style: TextStyle(
color: accent,
@ -201,20 +201,20 @@ class _HeroCard extends ConsumerWidget {
fontWeight: FontWeight.w700)),
],
),
const SizedBox(height: RatuneSpacing.xs),
const SizedBox(height: TimbreSpacing.xs),
Text(title,
maxLines: 1,
overflow: TextOverflow.ellipsis,
style: const TextStyle(
color: RatuneColors.foreground,
color: TimbreColors.foreground,
fontWeight: FontWeight.w700)),
if (subtitle != null)
Text(subtitle,
maxLines: 1,
overflow: TextOverflow.ellipsis,
style: const TextStyle(color: RatuneColors.dimmed)),
style: const TextStyle(color: TimbreColors.dimmed)),
if (hasCurrent) ...[
const SizedBox(height: RatuneSpacing.md),
const SizedBox(height: TimbreSpacing.md),
BlockProgressBar(progress: progress, cells: 32, height: 6),
],
],
@ -239,10 +239,10 @@ class _HeroShell extends StatelessWidget {
return InkWell(
onTap: onTap,
child: Container(
padding: const EdgeInsets.all(RatuneSpacing.lg),
padding: const EdgeInsets.all(TimbreSpacing.lg),
decoration: BoxDecoration(
color: RatuneColors.surface,
border: Border.all(color: RatuneColors.borderActive),
color: TimbreColors.surface,
border: Border.all(color: TimbreColors.borderActive),
),
child: child,
),
@ -263,19 +263,19 @@ class _Shelf extends StatelessWidget {
Widget build(BuildContext context) {
if (cards.isEmpty) return const SizedBox.shrink();
return Padding(
padding: const EdgeInsets.only(bottom: RatuneSpacing.xl),
padding: const EdgeInsets.only(bottom: TimbreSpacing.xl),
child: Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: [
_ShelfHeader(title: title, onShuffle: onShuffle),
const SizedBox(height: RatuneSpacing.md),
const SizedBox(height: TimbreSpacing.md),
SizedBox(
height: 182,
child: ListView.separated(
scrollDirection: Axis.horizontal,
itemCount: cards.length,
separatorBuilder: (_, _) =>
const SizedBox(width: RatuneSpacing.md),
const SizedBox(width: TimbreSpacing.md),
itemBuilder: (_, i) => cards[i],
),
),
@ -297,7 +297,7 @@ class _ShelfHeader extends StatelessWidget {
children: [
Text(title,
style: const TextStyle(
color: RatuneColors.foreground,
color: TimbreColors.foreground,
fontWeight: FontWeight.w700,
letterSpacing: 0.5)),
const Spacer(),
@ -306,9 +306,9 @@ class _ShelfHeader extends StatelessWidget {
onTap: onShuffle,
customBorder: const CircleBorder(),
child: const SizedBox(
width: RatuneSpacing.minTouchTarget,
width: TimbreSpacing.minTouchTarget,
height: 28,
child: Icon(Icons.shuffle, size: 18, color: RatuneColors.dimmed),
child: Icon(Icons.shuffle, size: 18, color: TimbreColors.dimmed),
),
),
],
@ -392,29 +392,29 @@ class _ArtCard extends StatelessWidget {
width: _size,
height: _size,
child: ColoredBox(
color: RatuneColors.surface,
color: TimbreColors.surface,
child: artUri != null
? Image.network(artUri!,
key: ValueKey(artUri),
fit: BoxFit.cover,
gaplessPlayback: true,
errorBuilder: (_, _, _) =>
Icon(fallbackIcon, color: RatuneColors.dimmed))
: Icon(fallbackIcon, color: RatuneColors.dimmed),
Icon(fallbackIcon, color: TimbreColors.dimmed))
: Icon(fallbackIcon, color: TimbreColors.dimmed),
),
),
),
const SizedBox(height: RatuneSpacing.sm),
const SizedBox(height: TimbreSpacing.sm),
Text(title,
maxLines: 1,
overflow: TextOverflow.ellipsis,
style: const TextStyle(color: RatuneColors.foreground)),
style: const TextStyle(color: TimbreColors.foreground)),
if (subtitle != null)
Text(subtitle!,
maxLines: 1,
overflow: TextOverflow.ellipsis,
style:
const TextStyle(color: RatuneColors.dimmed, fontSize: 12)),
const TextStyle(color: TimbreColors.dimmed, fontSize: 12)),
],
),
),
@ -434,7 +434,7 @@ class _ArtCardSkeleton extends StatelessWidget {
child: const SizedBox(
width: _ArtCard._size,
height: _ArtCard._size,
child: ColoredBox(color: RatuneColors.surface),
child: ColoredBox(color: TimbreColors.surface),
),
),
);