feat(ui): 更新品牌启动页与选集交互

This commit is contained in:
Zhou Weidong committed 2026-10-19 09:28:16 +08:00
1 parent 4778ce2c75
commit c1cb7d1c11
87 files changed
+919 -552

No files matched your search

+105 -47
View File
@@ -136,7 +136,7 @@ class _PlayerPageState extends State<PlayerPage> with WidgetsBindingObserver {
data: AppTheme.dark(),
child: widget.embedded
? content
: Scaffold(backgroundColor: Colors.black, body: content),
: Scaffold(backgroundColor: AppColors.ink, body: content),
),
);
}
@@ -183,7 +183,7 @@ class _PlayerPageState extends State<PlayerPage> with WidgetsBindingObserver {
return Stack(
fit: StackFit.expand,
children: [
const ColoredBox(color: Colors.black),
const ColoredBox(color: AppColors.ink),
?video,
if (!logic.chromeHidden)
const IgnorePointer(
@@ -304,7 +304,7 @@ class _PlayerPageState extends State<PlayerPage> with WidgetsBindingObserver {
child: IgnorePointer(
child: DecoratedBox(
decoration: BoxDecoration(
color: Color(0x73000000),
color: AppColors.blue,
shape: BoxShape.circle,
),
child: Padding(
@@ -494,31 +494,91 @@ class _BlockedNotice extends StatelessWidget {
: l10n.noMediaNotice;
return Center(
child: Padding(
padding: const EdgeInsets.symmetric(horizontal: 36),
padding: const EdgeInsets.symmetric(horizontal: 28),
child: _UnlockCard(
locked: needsUnlock,
title: title,
coinLabel: needsUnlock && unlockCoin > 0
? '$unlockCoin ${l10n.coins}'
: null,
footnote: needsUnlock ? l10n.unlockComingSoon : null,
),
),
);
}
}
/// Coin lock presented as a reward card: gold chip, chili only on the icon.
class _UnlockCard extends StatelessWidget {
const _UnlockCard({
required this.locked,
required this.title,
required this.coinLabel,
required this.footnote,
});
final bool locked;
final String title;
final String? coinLabel;
final String? footnote;
@override
Widget build(BuildContext context) {
return DecoratedBox(
decoration: BoxDecoration(
color: AppColors.card,
borderRadius: BorderRadius.circular(20),
border: Border.all(color: AppColors.gold.withValues(alpha: 0.55)),
),
child: Padding(
padding: const EdgeInsets.fromLTRB(20, 22, 20, 18),
child: Column(
mainAxisSize: MainAxisSize.min,
children: [
Icon(
needsUnlock
? Icons.lock_outline_rounded
: Icons.movie_filter_outlined,
color: Colors.white70,
size: 36,
locked ? Icons.lock_outline_rounded : Icons.movie_filter_outlined,
color: locked ? AppColors.gold : AppColors.cream,
size: 32,
),
const SizedBox(height: 12),
Text(
title,
textAlign: TextAlign.center,
style: const TextStyle(color: Colors.white70),
style: const TextStyle(
color: AppColors.cream,
fontSize: 16,
fontWeight: FontWeight.w700,
),
),
if (needsUnlock) ...[
const SizedBox(height: 6),
if (coinLabel != null) ...[
const SizedBox(height: 12),
DecoratedBox(
decoration: BoxDecoration(
color: AppColors.gold,
borderRadius: BorderRadius.circular(20),
),
child: Padding(
padding: const EdgeInsets.symmetric(
horizontal: 12,
vertical: 6,
),
child: Text(
coinLabel!,
style: const TextStyle(
color: AppColors.onGold,
fontSize: 13,
fontWeight: FontWeight.w800,
),
),
),
),
],
if (footnote != null) ...[
const SizedBox(height: 8),
Text(
unlockCoin > 0
? '${l10n.unlockComingSoon} · $unlockCoin ${l10n.coins}'
: l10n.unlockComingSoon,
footnote!,
textAlign: TextAlign.center,
style: const TextStyle(color: Colors.white38, fontSize: 12),
style: const TextStyle(color: AppColors.muted, fontSize: 12),
),
],
],
@@ -674,14 +734,14 @@ class _PlaybackOverlay extends StatelessWidget {
children: [
_RailAction(
key: const Key('rail-like'),
icon: liked ? Icons.favorite_rounded : Icons.favorite_border_rounded,
icon: Icons.favorite_border,
label: l10n.like,
selected: liked,
onTap: onLike,
),
_RailAction(
key: const Key('rail-save'),
icon: saved ? Icons.bookmark_rounded : Icons.bookmark_border_rounded,
icon: Icons.bookmark_border,
label: l10n.save,
selected: saved,
onTap: onSave,
@@ -693,19 +753,19 @@ class _PlaybackOverlay extends StatelessWidget {
onTap: onDownload,
),
_RailAction(
icon: Icons.grid_view_rounded,
icon: Icons.grid_view_outlined,
label: l10n.episodes,
onTap: onEpisodes,
),
_RailAction(
key: const Key('rail-comments'),
icon: Icons.mode_comment_outlined,
icon: Icons.chat_bubble_outline,
label: l10n.comments,
onTap: onComments,
),
_RailAction(
key: const Key('rail-share'),
icon: Icons.share_rounded,
icon: Icons.share_outlined,
label: l10n.share,
onTap: onShare,
),
@@ -713,10 +773,16 @@ class _PlaybackOverlay extends StatelessWidget {
IconButton(
tooltip: l10n.pictureInPicture,
onPressed: onPip,
visualDensity: VisualDensity.compact,
iconSize: 20,
color: Colors.white,
icon: const Icon(Icons.picture_in_picture_alt_outlined),
padding: EdgeInsets.zero,
constraints: const BoxConstraints.tightFor(
width: _railTapSize,
height: _railTapSize,
),
color: AppColors.cream,
icon: const Icon(
Icons.picture_in_picture_alt_outlined,
size: _railIconSize,
),
),
],
);
@@ -748,6 +814,10 @@ class _PlaybackOverlay extends StatelessWidget {
);
}
const double _railIconSize = 28;
const double _railIconWeight = 300;
const double _railTapSize = 44;
class _RailAction extends StatelessWidget {
const _RailAction({
super.key,
@@ -762,28 +832,16 @@ class _RailAction extends StatelessWidget {
final bool selected;
@override
Widget build(BuildContext context) => Column(
mainAxisSize: MainAxisSize.min,
children: [
IconButton(
tooltip: label,
onPressed: onTap,
visualDensity: VisualDensity.compact,
padding: EdgeInsets.zero,
constraints: const BoxConstraints.tightFor(width: 42, height: 36),
color: selected ? AppColors.blueSoft : Colors.white,
icon: Icon(icon, size: 24),
),
Text(
label,
style: const TextStyle(
color: Colors.white,
fontSize: 11,
fontWeight: FontWeight.w600,
shadows: [Shadow(blurRadius: 8, color: Colors.black)],
),
),
],
Widget build(BuildContext context) => IconButton(
tooltip: label,
onPressed: onTap,
padding: EdgeInsets.zero,
constraints: const BoxConstraints.tightFor(
width: _railTapSize,
height: _railTapSize,
),
color: selected ? AppColors.blueSoft : AppColors.cream,
icon: Icon(icon, size: _railIconSize, weight: _railIconWeight, fill: 0),
);
}