diff --git a/lib/pages/article/widgets/opus_content.dart b/lib/pages/article/widgets/opus_content.dart index 9f7c2b722..3165822c4 100644 --- a/lib/pages/article/widgets/opus_content.dart +++ b/lib/pages/article/widgets/opus_content.dart @@ -81,9 +81,7 @@ class OpusContent extends StatelessWidget { // case 'RICH_TEXT_NODE_TYPE_TOPIC': default: if (rich.jumpUrl != null) { - PiliScheme.routePushFromUrl( - rich.jumpUrl!, - ); + PiliScheme.routePushFromUrl(rich.jumpUrl!); } } }, @@ -100,7 +98,7 @@ class OpusContent extends StatelessWidget { colorScheme.onSurfaceVariant, BlendMode.srcIn, ), - alignment: Alignment.centerLeft, + alignment: .centerLeft, placeholderBuilder: (_) => Text(latex), errorBuilder: (_) => Text(latex), ), @@ -281,7 +279,7 @@ class OpusContent extends StatelessWidget { children: [ const WidgetSpan( child: Icon(MdiIcons.circleMedium), - alignment: PlaceholderAlignment.middle, + alignment: .middle, ), ...entry.$2.nodes!.map((item) { if (item.word != null) { @@ -318,18 +316,272 @@ class OpusContent extends StatelessWidget { ), ); case 6: + final type = element.linkCard!.card!.type; + Widget child; + switch (type) { + case 'LINK_CARD_TYPE_UGC': + final ugc = element.linkCard!.card!.ugc!; + child = Row( + spacing: 10, + children: [ + NetworkImgLayer( + width: 104, + height: 65, + src: ugc.cover, + borderRadius: const .all(.circular(6)), + ), + Expanded( + child: Column( + crossAxisAlignment: .start, + children: [ + Text(ugc.title!), + Text( + ugc.descSecond!, + style: TextStyle( + fontSize: 13, + color: colorScheme.outline, + ), + ), + ], + ), + ), + ], + ); + case 'LINK_CARD_TYPE_ITEM_NULL': + final itemNull = element.linkCard?.card?.itemNull; + child = Text( + ' ${itemNull?.text}: ${element.linkCard?.card?.oid}', + ); + case 'LINK_CARD_TYPE_COMMON': + final common = element.linkCard!.card!.common!; + child = Row( + spacing: 10, + children: [ + NetworkImgLayer( + width: 104, + height: 65, + src: common.cover, + borderRadius: const .all(.circular(6)), + ), + Expanded( + child: Column( + crossAxisAlignment: .start, + children: [ + Text(common.title!), + if (common.desc1 != null) + Text( + common.desc1!, + style: TextStyle( + fontSize: 13, + color: colorScheme.outline, + ), + ), + if (common.desc2 != null) + Text( + common.desc2!, + style: TextStyle( + fontSize: 13, + color: colorScheme.outline, + ), + ), + ], + ), + ), + ], + ); + case 'LINK_CARD_TYPE_LIVE': + final live = element.linkCard!.card!.live!; + child = Row( + spacing: 10, + children: [ + NetworkImgLayer( + width: 104, + height: 65, + src: live.cover, + borderRadius: const .all(.circular(6)), + ), + Expanded( + child: Column( + crossAxisAlignment: .start, + children: [ + Text(live.title!), + if (live.descFirst != null) + Text( + live.descFirst!, + style: TextStyle( + fontSize: 13, + color: colorScheme.outline, + ), + ), + if (live.descSecond != null) + Text( + live.descSecond!, + style: TextStyle( + fontSize: 13, + color: colorScheme.outline, + ), + ), + ], + ), + ), + ], + ); + case 'LINK_CARD_TYPE_OPUS': + final opus = element.linkCard!.card!.opus!; + child = Row( + spacing: 10, + children: [ + NetworkImgLayer( + width: 104, + height: 65, + src: opus.cover, + borderRadius: const .all(.circular(6)), + ), + Expanded( + child: Column( + crossAxisAlignment: .start, + children: [ + Text(opus.title!), + Text( + '${opus.authorName} · ${opus.statView ?? 0}阅读', + style: TextStyle( + fontSize: 13, + color: colorScheme.outline, + ), + ), + ], + ), + ), + ], + ); + case 'LINK_CARD_TYPE_VOTE': + final vote = element.linkCard!.card!.vote!; + child = Row( + spacing: 10, + children: [ + Container( + decoration: BoxDecoration( + borderRadius: const .all(.circular(6)), + color: colorScheme.secondaryContainer, + ), + width: 70, + height: 50, + alignment: .center, + child: Icon( + Icons.bar_chart_rounded, + color: colorScheme.onSurfaceVariant, + ), + ), + Expanded( + child: Column( + crossAxisAlignment: .start, + children: [ + Text(vote.desc!), + Text( + '${vote.joinNum}人参与', + style: TextStyle( + fontSize: 13, + color: colorScheme.outline, + ), + ), + ], + ), + ), + ], + ); + case 'LINK_CARD_TYPE_MUSIC': + final music = element.linkCard!.card!.music!; + child = Row( + spacing: 10, + children: [ + NetworkImgLayer( + width: 104, + height: 65, + src: music.cover, + borderRadius: const .all(.circular(6)), + ), + Expanded( + child: Column( + crossAxisAlignment: .start, + children: [ + Text(music.title!), + if (music.label != null) + Text( + music.label!, + style: TextStyle( + fontSize: 13, + color: colorScheme.outline, + ), + ), + ], + ), + ), + ], + ); + case 'LINK_CARD_TYPE_GOODS': + final goods = element.linkCard!.card!.goods!; + child = Column( + children: goods.items!.map((e) { + return GestureDetector( + onTap: () { + if (e.jumpUrl?.isNotEmpty == true) { + PiliScheme.routePushFromUrl(e.jumpUrl!); + } + }, + child: Row( + spacing: 10, + children: [ + NetworkImgLayer( + width: 104, + height: 65, + src: e.cover, + borderRadius: const .all(.circular(6)), + ), + Expanded( + child: Column( + crossAxisAlignment: .start, + children: [ + Text(e.name!), + if (e.brief?.isNotEmpty == true) + Text( + e.brief!, + style: TextStyle( + fontSize: 13, + color: colorScheme.outline, + ), + ), + if (e.price?.isNotEmpty == true) + Text( + '${e.price!}起', + style: TextStyle( + fontSize: 13, + color: colorScheme.outline, + ), + ), + ], + ), + ), + ], + ), + ); + }).toList(), + ); + default: + throw UnimplementedError( + '\nparaType: ${element.paraType},\ncard type: $type', + ); + } return Material( shape: const RoundedRectangleBorder( - borderRadius: BorderRadius.all(Radius.circular(8)), + borderRadius: .all(.circular(8)), ), color: colorScheme.onInverseSurface, child: InkWell( - onTap: element.linkCard!.card!.type == 'LINK_CARD_TYPE_GOODS' + onTap: type == 'LINK_CARD_TYPE_GOODS' ? null : () { try { - if (element.linkCard!.card!.type == - 'LINK_CARD_TYPE_VOTE') { + if (type == 'LINK_CARD_TYPE_VOTE') { showVoteDialog( context, element.linkCard!.card!.vote?.voteId ?? @@ -337,296 +589,42 @@ class OpusContent extends StatelessWidget { ); return; } - String? url = - switch (element.linkCard!.card!.type) { - 'LINK_CARD_TYPE_UGC' => - element.linkCard!.card!.ugc!.jumpUrl, - 'LINK_CARD_TYPE_COMMON' => - element.linkCard!.card!.common!.jumpUrl, - 'LINK_CARD_TYPE_LIVE' => - element.linkCard!.card!.live!.jumpUrl, - 'LINK_CARD_TYPE_OPUS' => - element.linkCard!.card!.opus!.jumpUrl, - 'LINK_CARD_TYPE_MUSIC' => - element.linkCard!.card!.music!.jumpUrl, - _ => null, - }; + if (type == 'LINK_CARD_TYPE_ITEM_NULL') { + switch (element.linkCard?.card?.itemNull?.text) { + case '视频': + PiliScheme.videoPush( + int.parse(element.linkCard!.card!.oid!), + null, + ); + default: + PageUtils.pushDynFromId( + id: element.linkCard!.card!.oid!, + ); + } + return; + } + String? url = switch (type) { + 'LINK_CARD_TYPE_UGC' => + element.linkCard!.card!.ugc!.jumpUrl, + 'LINK_CARD_TYPE_COMMON' => + element.linkCard!.card!.common!.jumpUrl, + 'LINK_CARD_TYPE_LIVE' => + element.linkCard!.card!.live!.jumpUrl, + 'LINK_CARD_TYPE_OPUS' => + element.linkCard!.card!.opus!.jumpUrl, + 'LINK_CARD_TYPE_MUSIC' => + element.linkCard!.card!.music!.jumpUrl, + _ => null, + }; if (url != null && url.isNotEmpty) { PiliScheme.routePushFromUrl(url); } } catch (_) {} }, - borderRadius: const BorderRadius.all(Radius.circular(8)), + borderRadius: const .all(.circular(8)), child: Padding( - padding: const EdgeInsets.all(8), - child: switch (element.linkCard?.card?.type) { - 'LINK_CARD_TYPE_UGC' => Row( - spacing: 10, - children: [ - NetworkImgLayer( - width: 104, - height: 65, - src: element.linkCard!.card!.ugc!.cover, - borderRadius: const BorderRadius.all( - Radius.circular(6), - ), - ), - Expanded( - child: Column( - crossAxisAlignment: CrossAxisAlignment.start, - children: [ - Text(element.linkCard!.card!.ugc!.title!), - Text( - element.linkCard!.card!.ugc!.descSecond!, - style: TextStyle( - fontSize: 13, - color: colorScheme.outline, - ), - ), - ], - ), - ), - ], - ), - 'LINK_CARD_TYPE_ITEM_NULL' => Row( - children: [ - if (element - .linkCard - ?.card - ?.itemNull - ?.icon - ?.isNullOrEmpty == - true) - const Icon(Icons.info, size: 20), - Text(' ${element.linkCard?.card?.itemNull?.text}'), - ], - ), - 'LINK_CARD_TYPE_COMMON' => Row( - spacing: 10, - children: [ - NetworkImgLayer( - width: 104, - height: 65, - src: element.linkCard!.card!.common!.cover, - borderRadius: const BorderRadius.all( - Radius.circular(6), - ), - ), - Expanded( - child: Column( - crossAxisAlignment: CrossAxisAlignment.start, - children: [ - Text(element.linkCard!.card!.common!.title!), - if (element.linkCard!.card!.common!.desc1 != - null) - Text( - element.linkCard!.card!.common!.desc1!, - style: TextStyle( - fontSize: 13, - color: colorScheme.outline, - ), - ), - if (element.linkCard!.card!.common!.desc2 != - null) - Text( - element.linkCard!.card!.common!.desc2!, - style: TextStyle( - fontSize: 13, - color: colorScheme.outline, - ), - ), - ], - ), - ), - ], - ), - 'LINK_CARD_TYPE_LIVE' => Row( - spacing: 10, - children: [ - NetworkImgLayer( - width: 104, - height: 65, - src: element.linkCard!.card!.live!.cover, - borderRadius: const BorderRadius.all( - Radius.circular(6), - ), - ), - Expanded( - child: Column( - crossAxisAlignment: CrossAxisAlignment.start, - children: [ - Text(element.linkCard!.card!.live!.title!), - if (element.linkCard!.card!.live!.descFirst != - null) - Text( - element.linkCard!.card!.live!.descFirst!, - style: TextStyle( - fontSize: 13, - color: colorScheme.outline, - ), - ), - if (element.linkCard!.card!.live!.descSecond != - null) - Text( - element.linkCard!.card!.live!.descSecond!, - style: TextStyle( - fontSize: 13, - color: colorScheme.outline, - ), - ), - ], - ), - ), - ], - ), - 'LINK_CARD_TYPE_OPUS' => Row( - spacing: 10, - children: [ - NetworkImgLayer( - width: 104, - height: 65, - src: element.linkCard!.card!.opus!.cover, - borderRadius: const BorderRadius.all( - Radius.circular(6), - ), - ), - Expanded( - child: Column( - crossAxisAlignment: CrossAxisAlignment.start, - children: [ - Text(element.linkCard!.card!.opus!.title!), - Text( - '${element.linkCard!.card!.opus!.authorName} · ${element.linkCard!.card!.opus!.statView ?? 0}阅读', - style: TextStyle( - fontSize: 13, - color: colorScheme.outline, - ), - ), - ], - ), - ), - ], - ), - 'LINK_CARD_TYPE_VOTE' => Row( - spacing: 10, - children: [ - Container( - decoration: BoxDecoration( - borderRadius: const BorderRadius.all( - Radius.circular(6), - ), - color: colorScheme.secondaryContainer, - ), - width: 70, - height: 50, - alignment: Alignment.center, - child: Icon( - Icons.bar_chart_rounded, - color: colorScheme.onSurfaceVariant, - ), - ), - Expanded( - child: Column( - crossAxisAlignment: CrossAxisAlignment.start, - children: [ - Text(element.linkCard!.card!.vote!.desc!), - Text( - '${element.linkCard!.card!.vote!.joinNum}人参与', - style: TextStyle( - fontSize: 13, - color: colorScheme.outline, - ), - ), - ], - ), - ), - ], - ), - 'LINK_CARD_TYPE_MUSIC' => Row( - spacing: 10, - children: [ - NetworkImgLayer( - width: 104, - height: 65, - src: element.linkCard!.card!.music!.cover, - borderRadius: const BorderRadius.all( - Radius.circular(6), - ), - ), - Expanded( - child: Column( - crossAxisAlignment: CrossAxisAlignment.start, - children: [ - Text(element.linkCard!.card!.music!.title!), - if (element.linkCard!.card!.music!.label != - null) - Text( - element.linkCard!.card!.music!.label!, - style: TextStyle( - fontSize: 13, - color: colorScheme.outline, - ), - ), - ], - ), - ), - ], - ), - 'LINK_CARD_TYPE_GOODS' => Column( - children: element.linkCard!.card!.goods!.items!.map(( - e, - ) { - return GestureDetector( - onTap: () { - if (e.jumpUrl?.isNotEmpty == true) { - PiliScheme.routePushFromUrl(e.jumpUrl!); - } - }, - child: Row( - spacing: 10, - children: [ - NetworkImgLayer( - width: 104, - height: 65, - src: e.cover, - borderRadius: const BorderRadius.all( - Radius.circular(6), - ), - ), - Expanded( - child: Column( - crossAxisAlignment: - CrossAxisAlignment.start, - children: [ - Text(e.name!), - if (e.brief?.isNotEmpty == true) - Text( - e.brief!, - style: TextStyle( - fontSize: 13, - color: colorScheme.outline, - ), - ), - if (e.price?.isNotEmpty == true) - Text( - '${e.price!}起', - style: TextStyle( - fontSize: 13, - color: colorScheme.outline, - ), - ), - ], - ), - ), - ], - ), - ); - }).toList(), - ), - _ => throw UnimplementedError( - '\nparaType: ${element.paraType},\ncard type: ${element.linkCard?.card?.type}', - ), - }, + padding: const .all(8), + child: child, ), ), ); @@ -648,12 +646,12 @@ class OpusContent extends StatelessWidget { ) .render(renderer); return Container( - padding: const EdgeInsets.all(12), + padding: const .all(12), decoration: BoxDecoration( - borderRadius: const BorderRadius.all(Radius.circular(8)), + borderRadius: const .all(.circular(8)), color: colorScheme.onInverseSurface, ), - width: double.infinity, + width: .infinity, child: SelectableText.rich(renderer.span!), ); case 8 when (element.heading?.nodes?.isNotEmpty == true): @@ -691,7 +689,7 @@ class OpusContent extends StatelessWidget { return SelectableText( '不支持的类型 (${element.paraType})', style: const TextStyle( - fontWeight: FontWeight.bold, + fontWeight: .bold, color: Colors.red, ), ); @@ -700,7 +698,7 @@ class OpusContent extends StatelessWidget { return SelectableText( '错误的类型 $e', style: const TextStyle( - fontWeight: FontWeight.bold, + fontWeight: .bold, color: Colors.red, ), ); @@ -723,7 +721,7 @@ Widget moduleBlockedItem( ? null : BoxDecoration( image: DecorationImage( - fit: BoxFit.fill, + fit: .fill, image: ResizeImage( CachedNetworkImageProvider( ImageUtils.thumbnailUrl( @@ -759,7 +757,7 @@ Widget moduleBlockedItem( return FilledButton.tonal( style: FilledButton.styleFrom( padding: padding, - tapTargetSize: MaterialTapTargetSize.shrinkWrap, + tapTargetSize: .shrinkWrap, visualDensity: visualDensity, backgroundColor: theme.colorScheme.btnColor, foregroundColor: Colors.white, @@ -771,7 +769,7 @@ Widget moduleBlockedItem( } }, child: Row( - mainAxisSize: MainAxisSize.min, + mainAxisSize: .min, children: [ if (moduleBlocked.button!.icon?.isNotEmpty == true) CachedNetworkImage( @@ -798,9 +796,9 @@ Widget moduleBlockedItem( width: maxWidth, height: maxWidth, decoration: bgImg(maxWidth), - padding: const EdgeInsets.all(12), + padding: const .all(12), child: Column( - mainAxisAlignment: MainAxisAlignment.center, + mainAxisAlignment: .center, children: [ if (moduleBlocked.icon != null) icon(math.max(40, maxWidth / 7)), @@ -830,16 +828,16 @@ Widget moduleBlockedItem( builder: (context, constraints) { return Container( decoration: bgImg(constraints.maxWidth), - padding: const EdgeInsets.all(12), + padding: const .all(12), child: Row( spacing: 8, children: [ if (moduleBlocked.icon != null) icon(42), Expanded( child: Column( - crossAxisAlignment: CrossAxisAlignment.start, - mainAxisSize: MainAxisSize.min, spacing: 2, + mainAxisSize: .min, + crossAxisAlignment: .start, children: [ if (moduleBlocked.title?.isNotEmpty == true) Text(moduleBlocked.title!), @@ -862,9 +860,9 @@ Widget moduleBlockedItem( horizontal: -4, ), shape: const RoundedRectangleBorder( - borderRadius: BorderRadius.all(Radius.circular(6)), + borderRadius: .all(.circular(6)), ), - padding: const EdgeInsets.symmetric(horizontal: 10), + padding: const .symmetric(horizontal: 10), ), ], ), @@ -891,15 +889,15 @@ Widget opusCollection(ThemeData theme, ModuleCollection item) { children: [ Expanded( child: Column( - mainAxisSize: MainAxisSize.min, - crossAxisAlignment: CrossAxisAlignment.start, + mainAxisSize: .min, + crossAxisAlignment: .start, children: [ Text(item.title!), Text.rich( TextSpan( children: [ WidgetSpan( - alignment: PlaceholderAlignment.middle, + alignment: .middle, child: Icon( size: 18, Icons.article_outlined,