mirror of
https://github.com/HChaZZY/PiliPlus.git
synced 2025-12-06 09:13:48 +08:00
mod: opus: show itemnull, moduleblocked
Signed-off-by: bggRGjQaUbCoE <githubaccount56556@proton.me>
This commit is contained in:
@@ -173,11 +173,28 @@ class Card {
|
|||||||
String? oid;
|
String? oid;
|
||||||
String? type;
|
String? type;
|
||||||
Ugc? ugc;
|
Ugc? ugc;
|
||||||
|
ItemNull? itemNull;
|
||||||
|
|
||||||
Card.fromJson(Map<String, dynamic> json) {
|
Card.fromJson(Map<String, dynamic> json) {
|
||||||
oid = json['oid'];
|
oid = json['oid'];
|
||||||
type = json['type'];
|
type = json['type'];
|
||||||
ugc = json['ugc'] == null ? null : Ugc.fromJson(json['ugc']);
|
ugc = json['ugc'] == null ? null : Ugc.fromJson(json['ugc']);
|
||||||
|
itemNull =
|
||||||
|
json['item_null'] == null ? null : ItemNull.fromJson(json['item_null']);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
class ItemNull {
|
||||||
|
ItemNull({
|
||||||
|
this.icon,
|
||||||
|
this.text,
|
||||||
|
});
|
||||||
|
String? icon;
|
||||||
|
String? text;
|
||||||
|
|
||||||
|
ItemNull.fromJson(Map<String, dynamic> json) {
|
||||||
|
icon = json['icon'];
|
||||||
|
text = json['text'];
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -100,6 +100,7 @@ class ItemModulesModel {
|
|||||||
// 专栏
|
// 专栏
|
||||||
List<ModuleTag>? moduleExtend; // opus的tag
|
List<ModuleTag>? moduleExtend; // opus的tag
|
||||||
List<ArticleContentModel>? moduleContent;
|
List<ArticleContentModel>? moduleContent;
|
||||||
|
ModuleBlocked? moduleBlocked;
|
||||||
|
|
||||||
// moduleBottom
|
// moduleBottom
|
||||||
|
|
||||||
@@ -137,6 +138,11 @@ class ItemModulesModel {
|
|||||||
?.map((i) => ArticleContentModel.fromJson(i))
|
?.map((i) => ArticleContentModel.fromJson(i))
|
||||||
.toList();
|
.toList();
|
||||||
break;
|
break;
|
||||||
|
case 'MODULE_TYPE_BLOCKED':
|
||||||
|
moduleBlocked = i['module_blocked'] == null
|
||||||
|
? null
|
||||||
|
: ModuleBlocked.fromJson(i['module_blocked']);
|
||||||
|
break;
|
||||||
case 'MODULE_TYPE_EXTEND':
|
case 'MODULE_TYPE_EXTEND':
|
||||||
moduleExtend = (i['module_extend']['items'] as List?)
|
moduleExtend = (i['module_extend']['items'] as List?)
|
||||||
?.map((i) => ModuleTag.fromJson(i))
|
?.map((i) => ModuleTag.fromJson(i))
|
||||||
@@ -156,6 +162,46 @@ class ItemModulesModel {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
class ModuleBlocked {
|
||||||
|
BgImg? bgImg;
|
||||||
|
int? blockedType;
|
||||||
|
Button? button;
|
||||||
|
String? hintMessage;
|
||||||
|
BgImg? icon;
|
||||||
|
|
||||||
|
ModuleBlocked.fromJson(Map<String, dynamic> json) {
|
||||||
|
bgImg = json['bg_img'] == null ? null : BgImg.fromJson(json['bg_img']);
|
||||||
|
blockedType = json['blocked_type'];
|
||||||
|
button = json['button'] == null ? null : Button.fromJson(json['button']);
|
||||||
|
hintMessage = json['hint_message'];
|
||||||
|
icon = json['icon'] == null ? null : BgImg.fromJson(json['icon']);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
class Button {
|
||||||
|
int? handleType;
|
||||||
|
String? icon;
|
||||||
|
String? jumpUrl;
|
||||||
|
String? text;
|
||||||
|
|
||||||
|
Button.fromJson(Map<String, dynamic> json) {
|
||||||
|
handleType = json['handle_type'];
|
||||||
|
icon = json['icon'];
|
||||||
|
jumpUrl = json['jump_url'];
|
||||||
|
text = json['text'];
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
class BgImg {
|
||||||
|
String? imgDark;
|
||||||
|
String? imgDay;
|
||||||
|
|
||||||
|
BgImg.fromJson(Map<String, dynamic> json) {
|
||||||
|
imgDark = json['img_dark'];
|
||||||
|
imgDay = json['img_day'];
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
class Basic {
|
class Basic {
|
||||||
String? commentIdStr;
|
String? commentIdStr;
|
||||||
int? commentType;
|
int? commentType;
|
||||||
|
|||||||
@@ -119,7 +119,7 @@ class ArticleController extends ReplyController<MainListReply> {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// stats
|
// stats
|
||||||
Future<bool> getArticleInfo() async {
|
Future<bool> getArticleInfo([bool isGetCover = false]) async {
|
||||||
final res = await DynamicsHttp.articleInfo(cvId: commentId);
|
final res = await DynamicsHttp.articleInfo(cvId: commentId);
|
||||||
if (res['status']) {
|
if (res['status']) {
|
||||||
summary
|
summary
|
||||||
@@ -140,6 +140,9 @@ class ArticleController extends ReplyController<MainListReply> {
|
|||||||
);
|
);
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
if (isGetCover) {
|
||||||
|
SmartDialog.showToast(res['msg']);
|
||||||
|
}
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -338,29 +338,48 @@ class _ArticlePageState extends State<ArticlePage>
|
|||||||
() {
|
() {
|
||||||
if (_articleCtr.isLoaded.value) {
|
if (_articleCtr.isLoaded.value) {
|
||||||
late Widget content;
|
late Widget content;
|
||||||
if (_articleCtr.opus == null) {
|
if (_articleCtr.opus != null) {
|
||||||
debugPrint('html page');
|
|
||||||
final res = parser.parse(_articleCtr.articleData!.content!);
|
|
||||||
content = SliverList.separated(
|
|
||||||
itemCount: res.body!.children.length,
|
|
||||||
itemBuilder: (context, index) {
|
|
||||||
return htmlRender(
|
|
||||||
context: context,
|
|
||||||
element: res.body!.children[index],
|
|
||||||
maxWidth: maxWidth,
|
|
||||||
callback: _getImageCallback,
|
|
||||||
);
|
|
||||||
},
|
|
||||||
separatorBuilder: (context, index) =>
|
|
||||||
const SizedBox(height: 10),
|
|
||||||
);
|
|
||||||
} else {
|
|
||||||
debugPrint('json page');
|
debugPrint('json page');
|
||||||
content = OpusContent(
|
content = OpusContent(
|
||||||
opus: _articleCtr.opus!,
|
opus: _articleCtr.opus!,
|
||||||
callback: _getImageCallback,
|
callback: _getImageCallback,
|
||||||
maxWidth: maxWidth,
|
maxWidth: maxWidth,
|
||||||
);
|
);
|
||||||
|
} else if (_articleCtr.opusData?.modules.moduleBlocked != null) {
|
||||||
|
debugPrint('moduleBlocked');
|
||||||
|
final moduleBlocked =
|
||||||
|
_articleCtr.opusData!.modules.moduleBlocked!;
|
||||||
|
final width = maxWidth * 0.8;
|
||||||
|
content = moduleBlockedItem(moduleBlocked, width);
|
||||||
|
} else if (_articleCtr.articleData?.content != null) {
|
||||||
|
debugPrint('html page');
|
||||||
|
final res = parser.parse(_articleCtr.articleData!.content!);
|
||||||
|
if (res.body!.children.isEmpty) {
|
||||||
|
content = SliverToBoxAdapter(
|
||||||
|
child: htmlRender(
|
||||||
|
context: context,
|
||||||
|
html: _articleCtr.articleData!.content!,
|
||||||
|
maxWidth: maxWidth,
|
||||||
|
callback: _getImageCallback,
|
||||||
|
),
|
||||||
|
);
|
||||||
|
} else {
|
||||||
|
content = SliverList.separated(
|
||||||
|
itemCount: res.body!.children.length,
|
||||||
|
itemBuilder: (context, index) {
|
||||||
|
return htmlRender(
|
||||||
|
context: context,
|
||||||
|
element: res.body!.children[index],
|
||||||
|
maxWidth: maxWidth,
|
||||||
|
callback: _getImageCallback,
|
||||||
|
);
|
||||||
|
},
|
||||||
|
separatorBuilder: (context, index) =>
|
||||||
|
const SizedBox(height: 10),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
content = SliverToBoxAdapter(child: Text('NULL'));
|
||||||
}
|
}
|
||||||
|
|
||||||
int? pubTime =
|
int? pubTime =
|
||||||
@@ -615,12 +634,13 @@ class _ArticlePageState extends State<ArticlePage>
|
|||||||
),
|
),
|
||||||
),
|
),
|
||||||
if (_articleCtr.commentType == 12 &&
|
if (_articleCtr.commentType == 12 &&
|
||||||
_articleCtr.stats.value != null)
|
_articleCtr.stats.value != null &&
|
||||||
|
_articleCtr.opusData?.modules.moduleBlocked == null)
|
||||||
PopupMenuItem(
|
PopupMenuItem(
|
||||||
onTap: () async {
|
onTap: () async {
|
||||||
try {
|
try {
|
||||||
if (_articleCtr.summary.cover == null) {
|
if (_articleCtr.summary.cover == null) {
|
||||||
if (!await _articleCtr.getArticleInfo()) {
|
if (!await _articleCtr.getArticleInfo(true)) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -10,120 +10,129 @@ import 'package:html/dom.dart' as dom;
|
|||||||
|
|
||||||
Widget htmlRender({
|
Widget htmlRender({
|
||||||
required BuildContext context,
|
required BuildContext context,
|
||||||
required dom.Element element,
|
dom.Element? element,
|
||||||
|
String? html,
|
||||||
int? imgCount,
|
int? imgCount,
|
||||||
List<String>? imgList,
|
List<String>? imgList,
|
||||||
required double maxWidth,
|
required double maxWidth,
|
||||||
Function(List<String>, int)? callback,
|
Function(List<String>, int)? callback,
|
||||||
}) {
|
}) {
|
||||||
debugPrint('htmlRender');
|
debugPrint('htmlRender');
|
||||||
return SelectionArea(
|
final extensions = [
|
||||||
child: Html.fromElement(
|
TagExtension(
|
||||||
documentElement: element,
|
tagsToExtend: <String>{'img'},
|
||||||
onLinkTap: (String? url, Map<String, String> buildContext, attributes) {},
|
builder: (ExtensionContext extensionContext) {
|
||||||
extensions: [
|
try {
|
||||||
TagExtension(
|
final Map<String, dynamic> attributes = extensionContext.attributes;
|
||||||
tagsToExtend: <String>{'img'},
|
final List<dynamic> key = attributes.keys.toList();
|
||||||
builder: (ExtensionContext extensionContext) {
|
String imgUrl = key.contains('src')
|
||||||
try {
|
? attributes['src'] as String
|
||||||
final Map<String, dynamic> attributes = extensionContext.attributes;
|
: attributes['data-src'] as String;
|
||||||
final List<dynamic> key = attributes.keys.toList();
|
imgUrl = imgUrl.contains('@') ? imgUrl.split('@').first : imgUrl;
|
||||||
String imgUrl = key.contains('src')
|
final bool isEmote = imgUrl.contains('/emote/');
|
||||||
? attributes['src'] as String
|
final bool isMall = imgUrl.contains('/mall/');
|
||||||
: attributes['data-src'] as String;
|
if (isMall) {
|
||||||
imgUrl = imgUrl.contains('@') ? imgUrl.split('@').first : imgUrl;
|
|
||||||
final bool isEmote = imgUrl.contains('/emote/');
|
|
||||||
final bool isMall = imgUrl.contains('/mall/');
|
|
||||||
if (isMall) {
|
|
||||||
return const SizedBox.shrink();
|
|
||||||
}
|
|
||||||
|
|
||||||
String? clazz = attributes['class'];
|
|
||||||
String? height = RegExp(r'max-height:(\d+)px')
|
|
||||||
.firstMatch('${attributes['style']}')
|
|
||||||
?.group(1);
|
|
||||||
if (clazz?.contains('cut-off') == true || height != null) {
|
|
||||||
return CachedNetworkImage(
|
|
||||||
width: maxWidth,
|
|
||||||
height: height != null ? double.parse(height) : null,
|
|
||||||
imageUrl: Utils.thumbnailImgUrl(imgUrl),
|
|
||||||
fit: BoxFit.contain,
|
|
||||||
);
|
|
||||||
}
|
|
||||||
return Hero(
|
|
||||||
tag: imgUrl,
|
|
||||||
child: GestureDetector(
|
|
||||||
onTap: () {
|
|
||||||
if (callback != null) {
|
|
||||||
callback([imgUrl], 0);
|
|
||||||
} else {
|
|
||||||
context.imageView(
|
|
||||||
imgList: [SourceModel(url: imgUrl)],
|
|
||||||
);
|
|
||||||
}
|
|
||||||
},
|
|
||||||
child: NetworkImgLayer(
|
|
||||||
width: isEmote ? 22 : maxWidth,
|
|
||||||
height: isEmote ? 22 : null,
|
|
||||||
src: imgUrl,
|
|
||||||
),
|
|
||||||
),
|
|
||||||
);
|
|
||||||
} catch (err) {
|
|
||||||
debugPrint('错误的HTML: $element');
|
|
||||||
return const SizedBox.shrink();
|
return const SizedBox.shrink();
|
||||||
}
|
}
|
||||||
},
|
|
||||||
),
|
String? clazz = attributes['class'];
|
||||||
],
|
String? height = RegExp(r'max-height:(\d+)px')
|
||||||
style: {
|
.firstMatch('${attributes['style']}')
|
||||||
'html': Style(
|
?.group(1);
|
||||||
fontSize: FontSize(16),
|
if (clazz?.contains('cut-off') == true || height != null) {
|
||||||
lineHeight: LineHeight.percent(160),
|
return CachedNetworkImage(
|
||||||
letterSpacing: 0.3,
|
width: maxWidth,
|
||||||
),
|
height: height != null ? double.parse(height) : null,
|
||||||
'body': Style(margin: Margins.zero, padding: HtmlPaddings.zero),
|
imageUrl: Utils.thumbnailImgUrl(imgUrl),
|
||||||
'a': Style(
|
fit: BoxFit.contain,
|
||||||
color: Theme.of(context).colorScheme.primary,
|
);
|
||||||
textDecoration: TextDecoration.none,
|
}
|
||||||
),
|
return Hero(
|
||||||
'br': Style(
|
tag: imgUrl,
|
||||||
lineHeight: LineHeight.percent(-1),
|
child: GestureDetector(
|
||||||
),
|
onTap: () {
|
||||||
'p': Style(
|
if (callback != null) {
|
||||||
margin: Margins.only(bottom: 4),
|
callback([imgUrl], 0);
|
||||||
),
|
} else {
|
||||||
'span': Style(
|
context.imageView(
|
||||||
fontSize: FontSize.large,
|
imgList: [SourceModel(url: imgUrl)],
|
||||||
height: Height(1.8),
|
);
|
||||||
),
|
}
|
||||||
'div': Style(height: Height.auto()),
|
},
|
||||||
'li > p': Style(
|
child: NetworkImgLayer(
|
||||||
display: Display.inline,
|
width: isEmote ? 22 : maxWidth,
|
||||||
),
|
height: isEmote ? 22 : null,
|
||||||
'li': Style(
|
src: imgUrl,
|
||||||
padding: HtmlPaddings.only(bottom: 4),
|
),
|
||||||
textAlign: TextAlign.justify,
|
),
|
||||||
),
|
);
|
||||||
'img': Style(margin: Margins.only(top: 4, bottom: 4)),
|
} catch (err) {
|
||||||
'h1,h2': Style(
|
debugPrint('错误的HTML: $element');
|
||||||
fontSize: FontSize.xLarge,
|
return const SizedBox.shrink();
|
||||||
fontWeight: FontWeight.bold,
|
}
|
||||||
margin: Margins.only(bottom: 8),
|
},
|
||||||
),
|
),
|
||||||
'h3,h4,h5': Style(
|
];
|
||||||
fontSize: FontSize(16),
|
final style = {
|
||||||
fontWeight: FontWeight.bold,
|
'html': Style(
|
||||||
margin: Margins.only(bottom: 4),
|
fontSize: FontSize(16),
|
||||||
),
|
lineHeight: LineHeight.percent(160),
|
||||||
'figcaption': Style(
|
letterSpacing: 0.3,
|
||||||
fontSize: FontSize.large,
|
),
|
||||||
textAlign: TextAlign.center,
|
'body': Style(margin: Margins.zero, padding: HtmlPaddings.zero),
|
||||||
),
|
'a': Style(
|
||||||
'strong': Style(fontWeight: FontWeight.bold),
|
color: Theme.of(context).colorScheme.primary,
|
||||||
'figure': Style(
|
textDecoration: TextDecoration.none,
|
||||||
margin: Margins.zero,
|
),
|
||||||
),
|
'br': Style(
|
||||||
},
|
lineHeight: LineHeight.percent(-1),
|
||||||
));
|
),
|
||||||
|
'p': Style(
|
||||||
|
margin: Margins.only(bottom: 4),
|
||||||
|
),
|
||||||
|
'span': Style(
|
||||||
|
fontSize: FontSize.large,
|
||||||
|
height: Height(1.8),
|
||||||
|
),
|
||||||
|
'div': Style(height: Height.auto()),
|
||||||
|
'li > p': Style(
|
||||||
|
display: Display.inline,
|
||||||
|
),
|
||||||
|
'li': Style(
|
||||||
|
padding: HtmlPaddings.only(bottom: 4),
|
||||||
|
textAlign: TextAlign.justify,
|
||||||
|
),
|
||||||
|
'img': Style(margin: Margins.only(top: 4, bottom: 4)),
|
||||||
|
'h1,h2': Style(
|
||||||
|
fontSize: FontSize.xLarge,
|
||||||
|
fontWeight: FontWeight.bold,
|
||||||
|
margin: Margins.only(bottom: 8),
|
||||||
|
),
|
||||||
|
'h3,h4,h5': Style(
|
||||||
|
fontSize: FontSize(16),
|
||||||
|
fontWeight: FontWeight.bold,
|
||||||
|
margin: Margins.only(bottom: 4),
|
||||||
|
),
|
||||||
|
'figcaption': Style(
|
||||||
|
fontSize: FontSize.large,
|
||||||
|
textAlign: TextAlign.center,
|
||||||
|
),
|
||||||
|
'strong': Style(fontWeight: FontWeight.bold),
|
||||||
|
'figure': Style(
|
||||||
|
margin: Margins.zero,
|
||||||
|
),
|
||||||
|
};
|
||||||
|
return SelectionArea(
|
||||||
|
child: element != null
|
||||||
|
? Html.fromElement(
|
||||||
|
documentElement: element,
|
||||||
|
extensions: extensions,
|
||||||
|
style: style,
|
||||||
|
)
|
||||||
|
: Html(
|
||||||
|
data: html,
|
||||||
|
extensions: extensions,
|
||||||
|
style: style,
|
||||||
|
),
|
||||||
|
);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -4,12 +4,14 @@ import 'package:PiliPlus/common/widgets/interactiveviewer_gallery/interactivevie
|
|||||||
import 'package:PiliPlus/common/widgets/network_img_layer.dart';
|
import 'package:PiliPlus/common/widgets/network_img_layer.dart';
|
||||||
import 'package:PiliPlus/models/dynamics/article_content_model.dart'
|
import 'package:PiliPlus/models/dynamics/article_content_model.dart'
|
||||||
show ArticleContentModel, Style, Word;
|
show ArticleContentModel, Style, Word;
|
||||||
|
import 'package:PiliPlus/models/dynamics/result.dart';
|
||||||
import 'package:PiliPlus/utils/app_scheme.dart';
|
import 'package:PiliPlus/utils/app_scheme.dart';
|
||||||
import 'package:PiliPlus/utils/extension.dart';
|
import 'package:PiliPlus/utils/extension.dart';
|
||||||
import 'package:PiliPlus/utils/utils.dart';
|
import 'package:PiliPlus/utils/utils.dart';
|
||||||
import 'package:cached_network_image/cached_network_image.dart';
|
import 'package:cached_network_image/cached_network_image.dart';
|
||||||
import 'package:flutter/gestures.dart';
|
import 'package:flutter/gestures.dart';
|
||||||
import 'package:flutter/material.dart';
|
import 'package:flutter/material.dart';
|
||||||
|
import 'package:get/get.dart';
|
||||||
import 'package:material_design_icons_flutter/material_design_icons_flutter.dart';
|
import 'package:material_design_icons_flutter/material_design_icons_flutter.dart';
|
||||||
import 'package:re_highlight/languages/all.dart';
|
import 'package:re_highlight/languages/all.dart';
|
||||||
import 'package:re_highlight/re_highlight.dart';
|
import 'package:re_highlight/re_highlight.dart';
|
||||||
@@ -168,7 +170,7 @@ class OpusContent extends StatelessWidget {
|
|||||||
}).toList(),
|
}).toList(),
|
||||||
),
|
),
|
||||||
);
|
);
|
||||||
case 6 when (element.linkCard?.card?.ugc != null):
|
case 6:
|
||||||
return Material(
|
return Material(
|
||||||
shape: const RoundedRectangleBorder(
|
shape: const RoundedRectangleBorder(
|
||||||
borderRadius: BorderRadius.all(Radius.circular(8)),
|
borderRadius: BorderRadius.all(Radius.circular(8)),
|
||||||
@@ -186,32 +188,46 @@ class OpusContent extends StatelessWidget {
|
|||||||
borderRadius: const BorderRadius.all(Radius.circular(8)),
|
borderRadius: const BorderRadius.all(Radius.circular(8)),
|
||||||
child: Padding(
|
child: Padding(
|
||||||
padding: const EdgeInsets.all(8),
|
padding: const EdgeInsets.all(8),
|
||||||
child: Row(
|
child: switch (element.linkCard?.card?.type) {
|
||||||
children: [
|
'LINK_CARD_TYPE_UGC' => Row(
|
||||||
NetworkImgLayer(
|
children: [
|
||||||
radius: 6,
|
NetworkImgLayer(
|
||||||
width: 65 * StyleString.aspectRatio,
|
radius: 6,
|
||||||
height: 65,
|
width: 65 * StyleString.aspectRatio,
|
||||||
src: element.linkCard!.card!.ugc!.cover,
|
height: 65,
|
||||||
),
|
src: element.linkCard!.card!.ugc!.cover,
|
||||||
const SizedBox(width: 10),
|
),
|
||||||
Expanded(
|
const SizedBox(width: 10),
|
||||||
child: Column(
|
Expanded(
|
||||||
crossAxisAlignment: CrossAxisAlignment.start,
|
child: Column(
|
||||||
children: [
|
crossAxisAlignment: CrossAxisAlignment.start,
|
||||||
Text(element.linkCard!.card!.ugc!.title!),
|
children: [
|
||||||
Text(
|
Text(element.linkCard!.card!.ugc!.title!),
|
||||||
element.linkCard!.card!.ugc!.descSecond!,
|
Text(
|
||||||
style: TextStyle(
|
element.linkCard!.card!.ugc!.descSecond!,
|
||||||
fontSize: 13,
|
style: TextStyle(
|
||||||
color: colorScheme.outline,
|
fontSize: 13,
|
||||||
),
|
color: colorScheme.outline,
|
||||||
|
),
|
||||||
|
),
|
||||||
|
],
|
||||||
),
|
),
|
||||||
],
|
),
|
||||||
),
|
],
|
||||||
),
|
),
|
||||||
],
|
'LINK_CARD_TYPE_ITEM_NULL' => Row(
|
||||||
),
|
children: [
|
||||||
|
if (element.linkCard?.card?.itemNull?.icon
|
||||||
|
?.isNullOrEmpty ==
|
||||||
|
true)
|
||||||
|
Icon(Icons.info, size: 20),
|
||||||
|
Text(' ${element.linkCard?.card?.itemNull?.text}'),
|
||||||
|
],
|
||||||
|
),
|
||||||
|
_ => throw UnimplementedError(
|
||||||
|
'\nparaType: ${element.paraType},\ncard type: ${element.linkCard?.card?.type}',
|
||||||
|
),
|
||||||
|
},
|
||||||
),
|
),
|
||||||
),
|
),
|
||||||
);
|
);
|
||||||
@@ -269,3 +285,80 @@ class OpusContent extends StatelessWidget {
|
|||||||
);
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Widget moduleBlockedItem(ModuleBlocked moduleBlocked, double width) {
|
||||||
|
return SliverToBoxAdapter(
|
||||||
|
child: Stack(
|
||||||
|
clipBehavior: Clip.none,
|
||||||
|
children: [
|
||||||
|
if (moduleBlocked.bgImg != null)
|
||||||
|
CachedNetworkImage(
|
||||||
|
width: width,
|
||||||
|
fit: BoxFit.cover,
|
||||||
|
imageUrl: Utils.thumbnailImgUrl(
|
||||||
|
Get.isDarkMode
|
||||||
|
? moduleBlocked.bgImg!.imgDark
|
||||||
|
: moduleBlocked.bgImg!.imgDay,
|
||||||
|
),
|
||||||
|
),
|
||||||
|
Container(
|
||||||
|
width: width,
|
||||||
|
height: width,
|
||||||
|
padding: const EdgeInsets.all(12),
|
||||||
|
child: Column(
|
||||||
|
mainAxisAlignment: MainAxisAlignment.center,
|
||||||
|
children: [
|
||||||
|
if (moduleBlocked.icon != null)
|
||||||
|
CachedNetworkImage(
|
||||||
|
width: width / 7,
|
||||||
|
fit: BoxFit.contain,
|
||||||
|
imageUrl: Utils.thumbnailImgUrl(
|
||||||
|
Get.isDarkMode
|
||||||
|
? moduleBlocked.icon!.imgDark
|
||||||
|
: moduleBlocked.icon!.imgDay,
|
||||||
|
),
|
||||||
|
),
|
||||||
|
if (moduleBlocked.hintMessage != null) ...[
|
||||||
|
const SizedBox(height: 5),
|
||||||
|
Text(
|
||||||
|
moduleBlocked.hintMessage!,
|
||||||
|
textAlign: TextAlign.center,
|
||||||
|
),
|
||||||
|
],
|
||||||
|
if (moduleBlocked.button != null) ...[
|
||||||
|
const SizedBox(height: 5),
|
||||||
|
FilledButton.tonal(
|
||||||
|
style: FilledButton.styleFrom(
|
||||||
|
visualDensity: const VisualDensity(vertical: -2.5),
|
||||||
|
backgroundColor: Get.isDarkMode
|
||||||
|
? const Color(0xFF8F0030)
|
||||||
|
: const Color(0xFFFF6699),
|
||||||
|
foregroundColor: Colors.white,
|
||||||
|
),
|
||||||
|
onPressed: () {
|
||||||
|
if (moduleBlocked.button!.jumpUrl != null) {
|
||||||
|
PiliScheme.routePushFromUrl(
|
||||||
|
moduleBlocked.button!.jumpUrl!);
|
||||||
|
}
|
||||||
|
},
|
||||||
|
child: Row(
|
||||||
|
mainAxisSize: MainAxisSize.min,
|
||||||
|
children: [
|
||||||
|
if (moduleBlocked.button!.icon != null)
|
||||||
|
CachedNetworkImage(
|
||||||
|
height: 16,
|
||||||
|
color: Colors.white,
|
||||||
|
imageUrl: moduleBlocked.button!.icon!,
|
||||||
|
),
|
||||||
|
Text(moduleBlocked.button!.text ?? ''),
|
||||||
|
],
|
||||||
|
),
|
||||||
|
),
|
||||||
|
],
|
||||||
|
],
|
||||||
|
),
|
||||||
|
),
|
||||||
|
],
|
||||||
|
),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user