148 lines
4.5 KiB
Dart
Executable File
148 lines
4.5 KiB
Dart
Executable File
import 'package:flutter/material.dart';
|
|
import 'package:get/get.dart';
|
|
import 'package:flutter_html/flutter_html.dart';
|
|
import 'package:flutter_markdown/flutter_markdown.dart';
|
|
import 'package:flutter_screenutil/flutter_screenutil.dart';
|
|
|
|
import '../model/response/kr_message_list.dart';
|
|
import 'api_service/kr_api.user.dart';
|
|
import '../utils/kr_common_util.dart';
|
|
import '../widgets/dialogs/kr_dialog.dart';
|
|
import '../localization/app_translations.dart';
|
|
|
|
class KRAnnouncementService {
|
|
static final KRAnnouncementService _instance = KRAnnouncementService._internal();
|
|
final KRUserApi _kr_userApi = KRUserApi();
|
|
bool _kr_hasShownAnnouncement = false;
|
|
|
|
factory KRAnnouncementService() {
|
|
return _instance;
|
|
}
|
|
|
|
KRAnnouncementService._internal();
|
|
|
|
// 检查是否需要显示公告弹窗
|
|
Future<void> kr_checkAnnouncement() async {
|
|
if (_kr_hasShownAnnouncement) {
|
|
return;
|
|
}
|
|
|
|
final either = await _kr_userApi.kr_getMessageList(1, 1, popup: true);
|
|
either.fold(
|
|
(error) {
|
|
KRCommonUtil.kr_showToast(error.msg);
|
|
},
|
|
(list) {
|
|
if (list.announcements.isNotEmpty) {
|
|
// 按创建时间降序排序,获取最新的公告
|
|
final sortedAnnouncements = list.announcements;
|
|
|
|
final latestAnnouncement = sortedAnnouncements.first;
|
|
|
|
// 如果需要弹窗显示
|
|
if (latestAnnouncement.popup) {
|
|
_kr_hasShownAnnouncement = true;
|
|
KRDialog.show(
|
|
title: latestAnnouncement.title,
|
|
message: null,
|
|
confirmText: AppTranslations.kr_dialog.kr_iKnow,
|
|
onConfirm: () {
|
|
// Navigator.of(Get.context!).pop();
|
|
},
|
|
customMessageWidget: _kr_buildMessageContent(latestAnnouncement.content, Get.context!),
|
|
);
|
|
}
|
|
}
|
|
},
|
|
);
|
|
}
|
|
|
|
// 构建消息内容
|
|
Widget _kr_buildMessageContent(String content, BuildContext context) {
|
|
// 判断内容类型
|
|
final bool kr_isHtml = content.contains('<') && content.contains('>');
|
|
final bool kr_isMarkdown = content.contains('**') ||
|
|
content.contains('*') ||
|
|
content.contains('#') ||
|
|
content.contains('- ') ||
|
|
content.contains('[');
|
|
|
|
final textStyle = TextStyle(
|
|
fontSize: 14.sp,
|
|
color: Theme.of(context).textTheme.bodySmall?.color,
|
|
fontFamily: 'AlibabaPuHuiTi-Regular',
|
|
height: 1.4,
|
|
);
|
|
|
|
if (kr_isHtml) {
|
|
// 使用 flutter_html 处理 HTML 内容
|
|
return Html(
|
|
data: content,
|
|
style: {
|
|
'body': Style(
|
|
margin: Margins.all(0),
|
|
padding: HtmlPaddings.all(0),
|
|
fontSize: FontSize(14.sp),
|
|
color: Theme.of(context).textTheme.bodySmall?.color,
|
|
fontFamily: 'AlibabaPuHuiTi-Regular',
|
|
lineHeight: LineHeight(1.4),
|
|
),
|
|
'p': Style(
|
|
margin: Margins.only(bottom: 8.h),
|
|
),
|
|
'b': Style(
|
|
fontWeight: FontWeight.bold,
|
|
),
|
|
'i': Style(
|
|
fontStyle: FontStyle.italic,
|
|
),
|
|
'a': Style(
|
|
color: Colors.blue,
|
|
textDecoration: TextDecoration.underline,
|
|
),
|
|
},
|
|
shrinkWrap: true,
|
|
);
|
|
} else if (kr_isMarkdown) {
|
|
// 使用 flutter_markdown 处理 Markdown 内容
|
|
return MarkdownBody(
|
|
data: content,
|
|
styleSheet: MarkdownStyleSheet(
|
|
p: TextStyle(
|
|
fontSize: 14.sp,
|
|
color: Theme.of(context).textTheme.bodySmall?.color,
|
|
fontFamily: 'AlibabaPuHuiTi-Regular',
|
|
height: 1.4,
|
|
),
|
|
strong: TextStyle(
|
|
fontSize: 14.sp,
|
|
fontWeight: FontWeight.bold,
|
|
color: Theme.of(context).textTheme.bodySmall?.color,
|
|
fontFamily: 'AlibabaPuHuiTi-Regular',
|
|
height: 1.4,
|
|
),
|
|
em: TextStyle(
|
|
fontSize: 14.sp,
|
|
fontStyle: FontStyle.italic,
|
|
color: Theme.of(context).textTheme.bodySmall?.color,
|
|
fontFamily: 'AlibabaPuHuiTi-Regular',
|
|
height: 1.4,
|
|
),
|
|
a: TextStyle(
|
|
fontSize: 14.sp,
|
|
color: Colors.blue,
|
|
decoration: TextDecoration.underline,
|
|
fontFamily: 'AlibabaPuHuiTi-Regular',
|
|
height: 1.4,
|
|
),
|
|
),
|
|
);
|
|
} else {
|
|
// 普通文本
|
|
return Text(
|
|
content,
|
|
style: textStyle,
|
|
);
|
|
}
|
|
}
|
|
} |