Files
PiliPlus/lib/pages/dynamics/widgets/dynamic_panel.dart
bggRGjQaUbCoE be03909fdc opt gesture
Signed-off-by: bggRGjQaUbCoE <githubaccount56556@proton.me>
2025-09-30 13:03:48 +08:00

201 lines
6.1 KiB
Dart

import 'package:PiliPlus/common/widgets/dyn/ink_well.dart';
import 'package:PiliPlus/common/widgets/image/image_save.dart';
import 'package:PiliPlus/models/dynamics/result.dart';
import 'package:PiliPlus/pages/dynamics/widgets/action_panel.dart';
import 'package:PiliPlus/pages/dynamics/widgets/author_panel.dart';
import 'package:PiliPlus/pages/dynamics/widgets/dyn_content.dart';
import 'package:PiliPlus/utils/page_utils.dart';
import 'package:PiliPlus/utils/utils.dart';
import 'package:flutter/material.dart' hide InkWell;
class DynamicPanel extends StatelessWidget {
final DynamicItemModel item;
final double maxWidth;
final bool isDetail;
final ValueChanged? onRemove;
final bool isSave;
final Function(bool isTop, dynamic dynId)? onSetTop;
final VoidCallback? onBlock;
final VoidCallback? onUnfold;
final bool isDetailPortraitW;
const DynamicPanel({
super.key,
required this.item,
required this.maxWidth,
this.isDetail = false,
this.onRemove,
this.isSave = false,
this.onSetTop,
this.onBlock,
this.onUnfold,
this.isDetailPortraitW = true,
});
@override
Widget build(BuildContext context) {
if (item.visible == false) {
return const SizedBox.shrink();
}
final theme = Theme.of(context);
final authorWidget = AuthorPanel(
item: item,
isDetail: isDetail,
onRemove: onRemove,
isSave: isSave,
onSetTop: onSetTop,
onBlock: onBlock,
);
void showMore() => _imageSaveDialog(context, authorWidget.morePanel);
final child = Material(
type: MaterialType.transparency,
child: InkWell(
onTap:
isDetail &&
!const {
'DYNAMIC_TYPE_AV',
'DYNAMIC_TYPE_UGC_SEASON',
'DYNAMIC_TYPE_PGC_UNION',
'DYNAMIC_TYPE_PGC',
'DYNAMIC_TYPE_LIVE',
'DYNAMIC_TYPE_LIVE_RCMD',
'DYNAMIC_TYPE_MEDIALIST',
'DYNAMIC_TYPE_COURSES_SEASON',
}.contains(item.type)
? null
: () => PageUtils.pushDynDetail(item),
onLongPress: showMore,
onSecondaryTap: Utils.isMobile ? null : showMore,
child: Column(
mainAxisSize: MainAxisSize.min,
crossAxisAlignment: CrossAxisAlignment.start,
children: [
Padding(
padding: const EdgeInsets.fromLTRB(12, 12, 12, 6),
child: authorWidget,
),
...dynContent(
context,
theme: theme,
isSave: isSave,
isDetail: isDetail,
item: item,
floor: 1,
maxWidth: maxWidth,
),
const SizedBox(height: 2),
if (!isDetail) ...[
ActionPanel(item: item),
if (item.modules.moduleFold case final moduleFold?) ...[
Divider(
height: 1,
color: theme.dividerColor.withValues(alpha: 0.1),
),
InkWell(
onTap: onUnfold,
child: Container(
alignment: Alignment.center,
padding: const EdgeInsets.symmetric(vertical: 10),
child: Text.rich(
textAlign: TextAlign.center,
style: TextStyle(
height: 1,
fontSize: 13,
color: theme.colorScheme.outline,
),
strutStyle: const StrutStyle(
height: 1,
leading: 0,
fontSize: 13,
),
TextSpan(
children: [
TextSpan(text: moduleFold.statement ?? '展开'),
WidgetSpan(
alignment: PlaceholderAlignment.middle,
child: Icon(
size: 19,
Icons.keyboard_arrow_down,
color: theme.colorScheme.outline,
),
),
],
),
),
),
),
],
] else if (!isSave)
const SizedBox(height: 12),
],
),
),
);
if (isSave || (isDetail && !isDetailPortraitW)) {
return child;
}
return DecoratedBox(
decoration: BoxDecoration(
border: Border(
bottom: BorderSide(
width: 8,
color: theme.dividerColor.withValues(alpha: 0.05),
),
),
),
child: Padding(
padding: const EdgeInsets.only(bottom: 8),
child: child,
),
);
}
void _imageSaveDialog(
BuildContext context,
Function(BuildContext) morePanel,
) {
String? title;
String? cover;
String? bvid;
late final major = item.modules.moduleDynamic?.major;
switch (item.type) {
case 'DYNAMIC_TYPE_AV':
title = major?.archive?.title;
cover = major?.archive?.cover;
bvid = major?.archive?.bvid;
break;
case 'DYNAMIC_TYPE_UGC_SEASON':
title = major?.ugcSeason?.title;
cover = major?.ugcSeason?.cover;
bvid = major?.ugcSeason?.bvid;
break;
case 'DYNAMIC_TYPE_PGC' || 'DYNAMIC_TYPE_PGC_UNION':
title = major?.pgc?.title;
cover = major?.pgc?.cover;
break;
case 'DYNAMIC_TYPE_LIVE_RCMD':
title = major?.liveRcmd?.title;
cover = major?.liveRcmd?.cover;
break;
case 'DYNAMIC_TYPE_LIVE':
title = major?.live?.title;
cover = major?.live?.cover;
break;
case 'DYNAMIC_TYPE_COURSES_SEASON':
title = major?.courses?.title;
cover = major?.courses?.cover;
break;
default:
morePanel(context);
return;
}
imageSaveDialog(
title: title,
cover: cover,
bvid: bvid,
);
}
}