import 'dart:convert'; import 'dart:typed_data'; import 'package:agora_rtm/agora_rtm.dart'; import 'package:dating_touchme_app/controller/global.dart'; import 'package:dating_touchme_app/model/live/live_chat_message.dart'; import 'package:dating_touchme_app/rtc/rtc_manager.dart'; import 'package:dating_touchme_app/rtc/rtm_manager.dart'; import 'package:flutter_smart_dialog/flutter_smart_dialog.dart'; import 'package:get_storage/get_storage.dart'; /// 直播间聊天消息服务 /// 负责消息的发送、接收、解析和管理 class LiveChatMessageService { // 单例模式 static final LiveChatMessageService _instance = LiveChatMessageService._internal(); factory LiveChatMessageService() => _instance; static LiveChatMessageService get instance => _instance; final GetStorage _storage = GetStorage(); bool _isListenerRegistered = false; // 消息监听回调 Function(LiveChatMessage message)? onMessageReceived; Function(String error)? onMessageError; LiveChatMessageService._internal(); /// 注册消息监听器 void registerMessageListener({ Function(LiveChatMessage message)? onMessageReceived, Function(String error)? onMessageError, }) { if (_isListenerRegistered) { print('⚠️ 消息监听器已注册,跳过重复注册'); return; } this.onMessageReceived = onMessageReceived; this.onMessageError = onMessageError; RTMManager.instance.onMessageEvent = (MessageEvent event) { _handleIncomingMessage(event); }; _isListenerRegistered = true; print('✅ 消息监听器注册完成'); } /// 移除消息监听器 void unregisterMessageListener() { RTMManager.instance.onMessageEvent = null; _isListenerRegistered = false; onMessageReceived = null; onMessageError = null; print('✅ 消息监听器已移除'); } /// 处理接收到的消息 void _handleIncomingMessage(MessageEvent event) { try { // 解析消息内容 final messageText = _parseMessageContent(event.message); final messageData = json.decode(messageText) as Map; // 只处理聊天消息类型 if (messageData['type'] == 'chat_message') { final chatMessage = LiveChatMessage.fromJson(messageData); onMessageReceived?.call(chatMessage); } } catch (e, stackTrace) { final error = '解析RTM消息失败: $e'; print('❌ $error'); print('❌ 堆栈信息: $stackTrace'); onMessageError?.call(error); } } /// 解析消息内容(支持 String 和 Uint8List) String _parseMessageContent(dynamic message) { if (message is String) { return message; } else if (message is Uint8List) { return utf8.decode(message); } else { return message.toString(); } } /// 构建消息数据 Map _buildMessageData(String content) { final userId = _storage.read('userId') ?? GlobalData().userId ?? ''; final userData = GlobalData().userData; final userName = userData?.nickName ?? '用户'; final avatar = userData?.profilePhoto; return { 'type': 'chat_message', 'userId': userId, 'userName': userName, 'avatar': avatar, 'content': content.trim(), 'timestamp': DateTime.now().millisecondsSinceEpoch, }; } /// 验证消息内容 String? _validateMessage(String content) { final trimmed = content.trim(); if (trimmed.isEmpty) { return '消息内容不能为空'; } if (trimmed.length > 500) { return '消息内容不能超过500个字符'; } return null; } /// 检查发送前置条件 String? _checkSendPreconditions(String channelName) { if (!RTMManager.instance.isInitialized) { return 'RTM 未初始化,无法发送消息'; } if (!RTMManager.instance.isLoggedIn) { return 'RTM 未登录,无法发送消息'; } if (channelName.isEmpty) { return '未加入频道,无法发送消息'; } return null; } /// 发送聊天消息 /// /// [content] 消息内容 /// [channelName] 频道名称,如果为空则从 RTCManager 获取 /// [showToast] 是否显示 Toast 提示,默认为 true /// /// 返回发送结果,true 表示成功,false 表示失败 Future sendMessage({ required String content, String? channelName, bool showToast = true, }) async { // 验证消息内容 final validationError = _validateMessage(content); if (validationError != null) { if (showToast) { SmartDialog.showToast(validationError); } return MessageSendResult.failure(validationError); } // 获取频道名称 final targetChannelName = channelName ?? RTCManager.instance.currentChannelId ?? ''; // 检查前置条件 final preconditionError = _checkSendPreconditions(targetChannelName); if (preconditionError != null) { print('❌ $preconditionError'); if (showToast) { SmartDialog.showToast(preconditionError); } return MessageSendResult.failure(preconditionError); } try { // 构建消息数据 final messageData = _buildMessageData(content); final messageJson = json.encode(messageData); print('📤 发送消息到频道: $targetChannelName'); print('📤 消息内容: $messageJson'); // 通过 RTM 发送消息 final success = await RTMManager.instance.publishChannelMessage( channelName: targetChannelName, message: messageJson, ); if (success) { print('✅ 消息发送成功'); // 创建消息对象(用于立即显示) final chatMessage = LiveChatMessage( userId: messageData['userId'] as String, userName: messageData['userName'] as String, avatar: messageData['avatar'] as String?, content: messageData['content'] as String, timestamp: messageData['timestamp'] as int, ); return MessageSendResult.success(chatMessage); } else { final error = '消息发送失败,请重试'; print('❌ $error'); if (showToast) { SmartDialog.showToast(error); } return MessageSendResult.failure(error); } } catch (e, stackTrace) { final error = '发送消息异常: $e'; print('❌ $error'); print('❌ 堆栈信息: $stackTrace'); if (showToast) { SmartDialog.showToast(error); } return MessageSendResult.failure(error); } } /// 创建消息对象(用于本地显示) LiveChatMessage createLocalMessage(String content) { final messageData = _buildMessageData(content); return LiveChatMessage( userId: messageData['userId'] as String, userName: messageData['userName'] as String, avatar: messageData['avatar'] as String?, content: messageData['content'] as String, timestamp: messageData['timestamp'] as int, ); } } /// 消息发送结果 class MessageSendResult { final bool success; final LiveChatMessage? message; final String? error; MessageSendResult._({ required this.success, this.message, this.error, }); factory MessageSendResult.success(LiveChatMessage message) { return MessageSendResult._( success: true, message: message, ); } factory MessageSendResult.failure(String error) { return MessageSendResult._( success: false, error: error, ); } }