mirror of
https://github.com/bggRGjQaUbCoE/PiliPlus.git
synced 2026-08-05 18:20:10 +08:00
@@ -82,8 +82,9 @@ class WhisperDetailController extends CommonListController<RspSessionMsg, Msg> {
|
||||
var result = await ImGrpc.sendMsg(
|
||||
senderUid: accountService.mid,
|
||||
receiverId: mid!,
|
||||
content:
|
||||
msgType == 5 ? message! : jsonEncode(picMsg ?? {"content": message!}),
|
||||
content: msgType == 5
|
||||
? message!
|
||||
: jsonEncode(picMsg ?? {"content": message!}),
|
||||
msgType: MsgType.values[msgType ?? (picMsg != null ? 2 : 1)],
|
||||
);
|
||||
SmartDialog.dismiss();
|
||||
|
||||
@@ -88,8 +88,11 @@ class _WhisperDetailPageState
|
||||
maxLines: 1,
|
||||
overflow: TextOverflow.ellipsis,
|
||||
style: const TextStyle(height: 1, fontSize: 16),
|
||||
strutStyle:
|
||||
const StrutStyle(leading: 0, height: 1, fontSize: 16),
|
||||
strutStyle: const StrutStyle(
|
||||
leading: 0,
|
||||
height: 1,
|
||||
fontSize: 16,
|
||||
),
|
||||
),
|
||||
),
|
||||
if (_whisperDetailController.isLive) ...[
|
||||
@@ -105,9 +108,11 @@ class _WhisperDetailPageState
|
||||
),
|
||||
actions: [
|
||||
IconButton(
|
||||
onPressed: () => Get.to(WhisperLinkSettingPage(
|
||||
talkerUid: _whisperDetailController.talkerId,
|
||||
)),
|
||||
onPressed: () => Get.to(
|
||||
WhisperLinkSettingPage(
|
||||
talkerUid: _whisperDetailController.talkerId,
|
||||
),
|
||||
),
|
||||
icon: Icon(
|
||||
size: 20,
|
||||
Icons.settings,
|
||||
@@ -130,8 +135,10 @@ class _WhisperDetailPageState
|
||||
behavior: HitTestBehavior.opaque,
|
||||
child: refreshIndicator(
|
||||
onRefresh: _whisperDetailController.onRefresh,
|
||||
child: Obx(() =>
|
||||
_buildBody(_whisperDetailController.loadingState.value)),
|
||||
child: Obx(
|
||||
() =>
|
||||
_buildBody(_whisperDetailController.loadingState.value),
|
||||
),
|
||||
),
|
||||
),
|
||||
),
|
||||
@@ -149,39 +156,42 @@ class _WhisperDetailPageState
|
||||
Widget _buildBody(LoadingState<List<Msg>?> loadingState) {
|
||||
return switch (loadingState) {
|
||||
Loading() => loadingWidget,
|
||||
Success(:var response) => response?.isNotEmpty == true
|
||||
? ListView.separated(
|
||||
shrinkWrap: true,
|
||||
reverse: true,
|
||||
itemCount: response!.length,
|
||||
padding: const EdgeInsets.all(14),
|
||||
physics: const AlwaysScrollableScrollPhysics(
|
||||
parent: ClampingScrollPhysics(),
|
||||
Success(:var response) =>
|
||||
response?.isNotEmpty == true
|
||||
? ListView.separated(
|
||||
shrinkWrap: true,
|
||||
reverse: true,
|
||||
itemCount: response!.length,
|
||||
padding: const EdgeInsets.all(14),
|
||||
physics: const AlwaysScrollableScrollPhysics(
|
||||
parent: ClampingScrollPhysics(),
|
||||
),
|
||||
controller: _whisperDetailController.scrollController,
|
||||
itemBuilder: (context, int index) {
|
||||
if (index == response.length - 1) {
|
||||
_whisperDetailController.onLoadMore();
|
||||
}
|
||||
final item = response[index];
|
||||
return ChatItem(
|
||||
item: item,
|
||||
eInfos: _whisperDetailController.eInfos,
|
||||
onLongPress:
|
||||
item.senderUid.toInt() ==
|
||||
_whisperDetailController.accountService.mid
|
||||
? () => onLongPress(index, item)
|
||||
: null,
|
||||
);
|
||||
},
|
||||
separatorBuilder: (context, index) =>
|
||||
const SizedBox(height: 12),
|
||||
)
|
||||
: scrollErrorWidget(
|
||||
onReload: _whisperDetailController.onReload,
|
||||
),
|
||||
controller: _whisperDetailController.scrollController,
|
||||
itemBuilder: (context, int index) {
|
||||
if (index == response.length - 1) {
|
||||
_whisperDetailController.onLoadMore();
|
||||
}
|
||||
final item = response[index];
|
||||
return ChatItem(
|
||||
item: item,
|
||||
eInfos: _whisperDetailController.eInfos,
|
||||
onLongPress: item.senderUid.toInt() ==
|
||||
_whisperDetailController.accountService.mid
|
||||
? () => onLongPress(index, item)
|
||||
: null,
|
||||
);
|
||||
},
|
||||
separatorBuilder: (context, index) => const SizedBox(height: 12),
|
||||
)
|
||||
: scrollErrorWidget(
|
||||
onReload: _whisperDetailController.onReload,
|
||||
),
|
||||
Error(:var errMsg) => scrollErrorWidget(
|
||||
errMsg: errMsg,
|
||||
onReload: _whisperDetailController.onReload,
|
||||
),
|
||||
errMsg: errMsg,
|
||||
onReload: _whisperDetailController.onReload,
|
||||
),
|
||||
};
|
||||
}
|
||||
|
||||
@@ -297,9 +307,10 @@ class _WhisperDetailPageState
|
||||
biz: 'im',
|
||||
);
|
||||
if (result['status']) {
|
||||
String mimeType = lookupMimeType(pickedFile.path)
|
||||
?.split('/')
|
||||
.getOrNull(1) ??
|
||||
String mimeType =
|
||||
lookupMimeType(
|
||||
pickedFile.path,
|
||||
)?.split('/').getOrNull(1) ??
|
||||
'jpg';
|
||||
UploadBfsResData data = result['data'];
|
||||
Map picMsg = {
|
||||
@@ -326,9 +337,11 @@ class _WhisperDetailPageState
|
||||
}
|
||||
}
|
||||
},
|
||||
icon: Icon(enablePublish
|
||||
? Icons.send
|
||||
: Icons.add_photo_alternate_outlined),
|
||||
icon: Icon(
|
||||
enablePublish
|
||||
? Icons.send
|
||||
: Icons.add_photo_alternate_outlined,
|
||||
),
|
||||
tooltip: enablePublish ? '发送' : '图片',
|
||||
);
|
||||
},
|
||||
|
||||
@@ -52,7 +52,8 @@ class ChatItem extends StatelessWidget {
|
||||
Widget build(BuildContext context) {
|
||||
bool isPic = item.msgType == MsgType.EN_MSG_TYPE_PIC.value; // 图片
|
||||
bool isRevoke = item.msgType == MsgType.EN_MSG_TYPE_DRAW_BACK.value; // 撤回消息
|
||||
bool isSystem = item.msgType == MsgType.EN_MSG_TYPE_VIDEO_CARD.value ||
|
||||
bool isSystem =
|
||||
item.msgType == MsgType.EN_MSG_TYPE_VIDEO_CARD.value ||
|
||||
item.msgType == MsgType.EN_MSG_TYPE_TIP_MESSAGE.value ||
|
||||
item.msgType == MsgType.EN_MSG_TYPE_NOTIFY_MSG.value ||
|
||||
item.msgType == MsgType.EN_MSG_TYPE_PICTURE_CARD.value ||
|
||||
@@ -138,17 +139,18 @@ class ChatItem extends StatelessWidget {
|
||||
Divider(
|
||||
height: 10,
|
||||
thickness: 1,
|
||||
color: theme.colorScheme.outline
|
||||
.withValues(alpha: 0.2),
|
||||
color: theme.colorScheme.outline.withValues(
|
||||
alpha: 0.2,
|
||||
),
|
||||
),
|
||||
Text(
|
||||
'此条消息为自动回复',
|
||||
style:
|
||||
theme.textTheme.labelMedium!.copyWith(
|
||||
color: theme.colorScheme.outline,
|
||||
),
|
||||
style: theme.textTheme.labelMedium!
|
||||
.copyWith(
|
||||
color: theme.colorScheme.outline,
|
||||
),
|
||||
),
|
||||
]
|
||||
],
|
||||
],
|
||||
),
|
||||
),
|
||||
@@ -313,8 +315,9 @@ class ChatItem extends StatelessWidget {
|
||||
for (var i in content['sub_cards'])
|
||||
GestureDetector(
|
||||
onTap: () async {
|
||||
String? bvid =
|
||||
IdUtils.bvRegex.firstMatch(i['jump_url'])?.group(0);
|
||||
String? bvid = IdUtils.bvRegex
|
||||
.firstMatch(i['jump_url'])
|
||||
?.group(0);
|
||||
if (bvid != null) {
|
||||
try {
|
||||
SmartDialog.showLoading();
|
||||
@@ -442,12 +445,14 @@ class ChatItem extends StatelessWidget {
|
||||
text: content['times'] == 0
|
||||
? '--:--'
|
||||
: DurationUtil.formatDuration(content['times']),
|
||||
)
|
||||
),
|
||||
],
|
||||
),
|
||||
Padding(
|
||||
padding:
|
||||
const EdgeInsets.symmetric(horizontal: 12, vertical: 8),
|
||||
padding: const EdgeInsets.symmetric(
|
||||
horizontal: 12,
|
||||
vertical: 8,
|
||||
),
|
||||
child: Text(
|
||||
content['times'] == 0 ? '内容已失效' : content['title'],
|
||||
style: TextStyle(
|
||||
@@ -509,12 +514,12 @@ class ChatItem extends StatelessWidget {
|
||||
case 6:
|
||||
type = '专栏';
|
||||
onTap = () => Get.toNamed(
|
||||
'/articlePage',
|
||||
parameters: {
|
||||
'id': '${content['id']}',
|
||||
'type': 'read',
|
||||
},
|
||||
);
|
||||
'/articlePage',
|
||||
parameters: {
|
||||
'id': '${content['id']}',
|
||||
'type': 'read',
|
||||
},
|
||||
);
|
||||
break;
|
||||
|
||||
// dynamic
|
||||
@@ -530,7 +535,8 @@ class ChatItem extends StatelessWidget {
|
||||
|
||||
default:
|
||||
onTap = () => SmartDialog.showToast(
|
||||
'unsupported source type: ${content['source']}');
|
||||
'unsupported source type: ${content['source']}',
|
||||
);
|
||||
}
|
||||
return Column(
|
||||
crossAxisAlignment: CrossAxisAlignment.start,
|
||||
@@ -698,15 +704,21 @@ class ChatItem extends StatelessWidget {
|
||||
Text.rich(
|
||||
TextSpan(
|
||||
children: modules!.indexed
|
||||
.map((e) => TextSpan(children: [
|
||||
.map(
|
||||
(e) => TextSpan(
|
||||
children: [
|
||||
TextSpan(
|
||||
text: e.$2['title'],
|
||||
style: TextStyle(
|
||||
color: theme.colorScheme.outline)),
|
||||
text: e.$2['title'],
|
||||
style: TextStyle(
|
||||
color: theme.colorScheme.outline,
|
||||
),
|
||||
),
|
||||
TextSpan(text: ' ${e.$2['detail']}'),
|
||||
if (e.$1 != modules.length - 1)
|
||||
const TextSpan(text: '\n'),
|
||||
]))
|
||||
],
|
||||
),
|
||||
)
|
||||
.toList(),
|
||||
),
|
||||
),
|
||||
|
||||
Reference in New Issue
Block a user