feat(flutter): 压缩首页剧卡并把播放次数上封面

This commit is contained in:
Zhou Weidong committed 2026-10-20 13:03:19 +08:00
1 parent 8e2cd5c838
commit 124ba75ab8
3 files changed
+104 -58

No files matched your search

+50 -48
View File
@@ -3,6 +3,7 @@
import 'package:flutter/material.dart';
import '../../../core/data/models/drama.dart';
import '../../../core/formatting/count_format.dart';
import '../../../core/theme/app_colors.dart';
import '../../../core/theme/app_dimens.dart';
import '../../../core/theme/app_theme.dart';
@@ -12,9 +13,12 @@ import '../../../l10n/app_localizations.dart';
const int _columns = 2;
const double _columnGap = 10;
const double _cardGap = 10;
const double _coverAspectRatio = 3 / 4;
const double _addSize = 28;
const double _addIconSize = 18;
const double _coverAspectRatio = 5 / 6;
const double _cardPadding = 8;
const double _coverTitleGap = 6;
const double _lineGap = 2;
const double _viewsIconSize = 10;
const double _viewsFontSize = 9;
/// 首页浏览态使用的双列剧目网格。
class HomeDramaGrid extends StatelessWidget {
@@ -89,16 +93,16 @@ class HomeDramaCard extends StatelessWidget {
key: Key('home-drama-card-${drama.id}'),
onTap: onTap,
child: Padding(
padding: const EdgeInsets.all(AppDimens.spaceSm),
padding: const EdgeInsets.all(_cardPadding),
child: Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: [
_cover(),
const SizedBox(height: AppDimens.spaceSm),
const SizedBox(height: _coverTitleGap),
_title(),
const SizedBox(height: AppDimens.spaceXs),
const SizedBox(height: _lineGap),
_genre(),
const SizedBox(height: AppDimens.spaceXs),
const SizedBox(height: _lineGap),
_metadata(),
],
),
@@ -124,6 +128,7 @@ class HomeDramaCard extends StatelessWidget {
Positioned(top: 8, left: 8, child: _tagBadge()),
if (_lockedCount > 0)
Positioned(top: 8, right: 8, child: _lockedBadge()),
Positioned(left: 8, bottom: 8, child: _viewsBadge()),
Positioned(right: 8, bottom: 8, child: _episodeBadge()),
],
),
@@ -210,6 +215,37 @@ class HomeDramaCard extends StatelessWidget {
);
}
/// 播放次数角标:深色半透明胶囊 + 白色小播放图标。
Widget _viewsBadge() {
return Container(
key: Key('home-drama-views-${drama.id}'),
padding: const EdgeInsets.symmetric(horizontal: 6, vertical: 2),
decoration: BoxDecoration(
color: AppColors.playerOverlayPill,
borderRadius: BorderRadius.circular(AppDimens.pillRadius),
),
child: Row(
mainAxisSize: MainAxisSize.min,
children: [
const Icon(
Icons.play_arrow_rounded,
color: AppColors.onPrimary,
size: _viewsIconSize,
),
const SizedBox(width: 2),
Text(
formatInteractionCount(drama.viewCount),
style: const TextStyle(
color: AppColors.onPrimary,
fontSize: _viewsFontSize,
fontWeight: FontWeight.w700,
),
),
],
),
);
}
Widget _title() {
return Text(
drama.title,
@@ -239,47 +275,13 @@ class HomeDramaCard extends StatelessWidget {
}
Widget _metadata() {
return Row(
children: [
Expanded(
child: Wrap(
spacing: AppDimens.spaceSm,
runSpacing: AppDimens.spaceXs,
children: [
Text(
l10n.episodeCount(drama.episodeCount),
key: Key('home-drama-episode-count-${drama.id}'),
style: const TextStyle(
color: AppColors.subtle,
fontSize: AppDimens.cardViews,
),
),
Text(
l10n.viewCountLabel(drama.viewCount),
key: Key('home-drama-views-${drama.id}'),
style: const TextStyle(
color: AppColors.subtle,
fontSize: AppDimens.cardViews,
),
),
],
),
),
Container(
key: Key('home-drama-add-${drama.id}'),
width: _addSize,
height: _addSize,
decoration: const BoxDecoration(
color: AppColors.blue,
shape: BoxShape.circle,
),
child: const Icon(
Icons.add_rounded,
color: AppColors.onPrimary,
size: _addIconSize,
),
),
],
return Text(
l10n.episodeCount(drama.episodeCount),
key: Key('home-drama-episode-count-${drama.id}'),
style: const TextStyle(
color: AppColors.subtle,
fontSize: AppDimens.cardViews,
),
);
}
}