fix:增加解析模拟对讲服务的数据并显示到屏幕上、增加异常类、增加发送消息前的状态判断

This commit is contained in:
liyi 2024-12-25 18:30:10 +08:00
parent cdbd0c3d03
commit f98d1ab05c
30 changed files with 239 additions and 201 deletions

View File

@ -24,7 +24,6 @@ class StarChartLogic extends BaseGetXController {
int startTime = DateTime.now().millisecondsSinceEpoch;
@override
void onReady() {
super.onReady();
@ -51,6 +50,8 @@ class StarChartLogic extends BaseGetXController {
_cancelTimers();
stopProcessing();
state.listPhotoData.value = Uint8List(0);
//
_stopPlayG711Data();
//
Get.back();
@ -72,6 +73,10 @@ class StarChartLogic extends BaseGetXController {
case TalkData_ContentTypeE.G711:
_playG711Data(talkData.content);
break;
case TalkData_ContentTypeE.Image:
//
state.listPhotoData.value = Uint8List.fromList(talkData.content);
break;
}
});
}
@ -107,16 +112,18 @@ class StarChartLogic extends BaseGetXController {
}
void _startCallTimer() {
if (state.oneMinuteTimeTimer.isActive) return;
state.oneMinuteTimeTimer.cancel();
state.oneMinuteTimeTimer =
Timer.periodic(const Duration(seconds: 1), (Timer t) {
state.oneMinuteTime.value++;
if (state.oneMinuteTime.value >= 60) {
t.cancel();
initiateHangUpCommand();
AppLog.log('通话时间超过60秒自动挂断');
state.oneMinuteTime.value = 0;
}
// if (state.oneMinuteTime.value >= 60) {
// t.cancel();
// initiateHangUpCommand();
// AppLog.log('通话时间超过60秒自动挂断');
// state.oneMinuteTime.value = 0;
// }
});
}

View File

@ -38,7 +38,6 @@ class _StarChartPageState extends State<StarChartPage> {
super.initState();
initAsync();
// _getTVDataRefreshUIAction();
}
Future<void> initAsync() async {
@ -265,52 +264,12 @@ class _StarChartPageState extends State<StarChartPage> {
}
}
// void _getTVDataRefreshUIAction() {
// // state.getTVDataRefreshUIEvent = eventBus
// // .on<GetTVDataRefreshUI>()
// // .listen((GetTVDataRefreshUI event) async {
// // if (event.tvList.isNotEmpty && event.tvList.length > 100) {
// // final Uint8List imageData = Uint8List.fromList(event.tvList);
// // if (!listEquals(state.listPhotoData.value, imageData)) {
// // state.listPhotoData.value = imageData;
// // state.shouldUpdateUI.value = true;
// // if (state.shouldUpdateUI.value) {
// // setState(() {});
// // state.shouldUpdateUI.value = false;
// // }
// // }
// // }
// // });
// state.talkDataRepository.talkDataStream.listen((talkData) {
// final contentType = talkData.contentType;
// //
// switch (contentType) {
// case TalkData_ContentTypeE.Image:
// state.listPhotoData.value = Uint8List.fromList(talkData.content);
// if (talkData.content.isNotEmpty && talkData.content.length > 100) {
// //
// final Uint8List imageData = Uint8List.fromList(talkData.content);
// if (!listEquals(state.listPhotoData.value, imageData)) {
// //
// state.listPhotoData.value = imageData;
// // trueUI
// state.shouldUpdateUI.value = true;
// // WidgetsBinding.instance.addPostFrameCallback((_) {
// // setState方法之前检查标志true时才更新UI
// if (state.shouldUpdateUI.value) {
// setState(() {
// // UI
// });
// // UI后将标志重新设置为false
// state.shouldUpdateUI.value = false;
// }
// // });
// }
// }
// break;
// }
// });
// }
String listToHexString(List<int> intList) {
//
List<String> hexList = intList.map((num) => num.toRadixString(16)).toList();
//
return hexList.join('');
}
@override
void dispose() {
@ -324,58 +283,67 @@ class _StarChartPageState extends State<StarChartPage> {
}
Widget _buildMpeg4TalkView() {
return Stack(
children: <Widget>[
Image.memory(
state.listPhotoData.value,
gaplessPlayback: true,
width: 1.sw,
height: 1.sh,
fit: BoxFit.cover,
filterQuality: FilterQuality.high,
errorBuilder:
(BuildContext context, Object error, StackTrace? stackTrace) {
return Container(color: Colors.transparent);
},
),
Positioned(
top: ScreenUtil().statusBarHeight + 30.h,
width: 1.sw,
child: Obx(() {
final String sec =
(state.oneMinuteTime.value % 60).toString().padLeft(2, '0');
final String min =
(state.oneMinuteTime.value ~/ 60).toString().padLeft(2, '0');
return Row(
mainAxisAlignment: MainAxisAlignment.center,
children: <Widget>[
Text('$min:$sec',
style: TextStyle(fontSize: 26.sp, color: Colors.white)),
],
);
}),
),
Positioned(
bottom: 10.w,
child: Container(
width: 1.sw - 30.w * 2,
margin: EdgeInsets.all(30.w),
decoration: BoxDecoration(
color: const Color(0xC83C3F41),
borderRadius: BorderRadius.circular(20.h),
),
child: Column(
children: <Widget>[
SizedBox(height: 20.h),
buildTopButtons(),
SizedBox(height: 20.h),
buildBottomButtons(),
SizedBox(height: 20.h),
],
return Obx(
() => Stack(
children: <Widget>[
state.listPhotoData.value.isNotEmpty
? Image.memory(
state.listPhotoData.value,
gaplessPlayback: true,
width: 1.sw,
height: 1.sh,
fit: BoxFit.cover,
filterQuality: FilterQuality.high,
errorBuilder: (BuildContext context, Object error,
StackTrace? stackTrace) {
return Container(color: Colors.transparent);
},
)
: Image.asset(
'images/main/monitorBg.png',
width: 1.sw,
height: 1.sh,
fit: BoxFit.cover,
),
Positioned(
top: ScreenUtil().statusBarHeight + 30.h,
width: 1.sw,
child: Obx(() {
final String sec =
(state.oneMinuteTime.value % 60).toString().padLeft(2, '0');
final String min =
(state.oneMinuteTime.value ~/ 60).toString().padLeft(2, '0');
return Row(
mainAxisAlignment: MainAxisAlignment.center,
children: <Widget>[
Text('$min:$sec',
style: TextStyle(fontSize: 26.sp, color: Colors.white)),
],
);
}),
),
Positioned(
bottom: 10.w,
child: Container(
width: 1.sw - 30.w * 2,
margin: EdgeInsets.all(30.w),
decoration: BoxDecoration(
color: const Color(0xC83C3F41),
borderRadius: BorderRadius.circular(20.h),
),
child: Column(
children: <Widget>[
SizedBox(height: 20.h),
buildTopButtons(),
SizedBox(height: 20.h),
buildBottomButtons(),
SizedBox(height: 20.h),
],
),
),
),
),
],
],
),
);
}

View File

@ -56,6 +56,9 @@ class StarChartState {
RxInt talkStatus = 0.obs; //
// StartChartTalkStatus
StartChartTalkStatus talkStatusInstance = StartChartTalkStatus.instance;
//
final TalkDataRepository talkDataRepository = TalkDataRepository.instance;

View File

@ -0,0 +1,3 @@
class ExceptionConstant{
static const String relay = 'relay';
}

View File

@ -1,10 +1,10 @@
import 'dart:convert';
import 'dart:typed_data';
import 'package:star_lock/app_settings/app_settings.dart';
import 'package:star_lock/talk/startChart/exception/start_chart_message_exception.dart';
import 'package:star_lock/talk/startChart/handle/scp_message_handle.dart';
import 'package:star_lock/talk/startChart/handle/scp_message_handler_factory.dart';
class ScpMessage {
ScpMessage({
this.ProtocolFlag,
@ -149,12 +149,13 @@ class ScpMessage {
static ScpMessage deserialize(Uint8List bytes) {
final message = ScpMessage();
int offset = 0;
// Convert byte array to hex string with zero padding and without spaces
// String hexString =
// bytes.map((b) => b.toRadixString(16).padLeft(2, '0')).join();
//
// // Log the hex string
// _log(text: '原始字节数组: $hexString');
// // _log(text: 'result bytes hex: ${hexString}');
// _log(
// text:
// '\n result bytes hex: ${hexString} \n payload hex: ${hexString.substring(194)}');
// ProtocolFlag (4 bytes)
if (bytes.length - offset >= 4) {
@ -244,8 +245,7 @@ class ScpMessage {
// Payload
if (message.PayloadLength != null &&
bytes.length - offset >= message.PayloadLength!) {
final Uint8List sublist =
bytes.sublist(offset, offset + message.PayloadLength!);
final sublist = bytes.sublist(offset, offset + message.PayloadLength!);
offset += message.PayloadLength!;
message.Payload = _handlePayLoad(
payloadType: message.PayloadType ?? 0,
@ -268,7 +268,7 @@ class ScpMessage {
static dynamic _handlePayLoad({
required int payloadType,
required int messageType,
required Uint8List byte,
required List<int> byte,
int? offset,
int? PayloadLength,
int? spTotal,
@ -280,7 +280,7 @@ class ScpMessage {
final ScpMessageHandler handler =
ScpMessageHandlerFactory.createHandler(payloadType);
//
return handler.deserializePayload(
final payload = handler.deserializePayload(
payloadType: payloadType,
messageType: messageType,
byte: byte,
@ -290,12 +290,9 @@ class ScpMessage {
spIndex: spIndex,
messageId: messageId,
);
return payload;
} catch (e, stackTrace) {
//
_log(text: '❌反序列化udp数据时遇到错误----》$e');
//
_log(text: '堆栈跟踪:\n$stackTrace');
return '';
throw StartChartMessageException('❌反序列化udp数据时遇到错误----》$e \n$stackTrace');
}
}

View File

@ -0,0 +1,10 @@
class StartChartMessageException implements Exception {
final String message;
StartChartMessageException(this.message);
@override
String toString() {
return 'StartChartMessageException{message: $message}';
}
}

View File

@ -0,0 +1,10 @@
class StartChartTalkStatusException implements Exception {
final String message;
StartChartTalkStatusException(this.message);
@override
String toString() {
return 'StartChartTalkStatusException{message: $message}';
}
}

View File

@ -35,7 +35,7 @@ class UdpBlePassThroughHandler extends ScpMessageBaseHandle
deserializePayload(
{required int payloadType,
required int messageType,
required Uint8List byte,
required List<int> byte,
int? offset,
int? PayloadLength,
int? spTotal,

View File

@ -36,7 +36,7 @@ class UdpEchoTestHandler extends ScpMessageBaseHandle
deserializePayload(
{required int payloadType,
required int messageType,
required Uint8List byte,
required List<int> byte,
int? offset,
int? PayloadLength,
int? spTotal,

View File

@ -36,7 +36,7 @@ class UdpGateWayResetHandler extends ScpMessageBaseHandle
deserializePayload(
{required int payloadType,
required int messageType,
required Uint8List byte,
required List<int> byte,
int? offset,
int? PayloadLength,
int? spTotal,

View File

@ -39,7 +39,7 @@ class UdpGateWayTransferHandler extends ScpMessageBaseHandle
deserializePayload(
{required int payloadType,
required int messageType,
required Uint8List byte,
required List<int> byte,
int? offset,
int? PayloadLength,
int? spTotal,

View File

@ -42,7 +42,7 @@ class UdpGoOnlineHandler extends ScpMessageBaseHandle
deserializePayload(
{required int payloadType,
required int messageType,
required Uint8List byte,
required List<int> byte,
int? offset,
int? PayloadLength,
int? spTotal,

View File

@ -43,7 +43,7 @@ class UdpHeartBeatHandler extends ScpMessageBaseHandle
void handleRealTimeData(ScpMessage scpMessage) {}
@override
deserializePayload({required int payloadType, required int messageType, required Uint8List byte, int? offset, int? PayloadLength, int? spTotal, int? spIndex, int? messageId}) {
deserializePayload({required int payloadType, required int messageType, required List<int> byte, int? offset, int? PayloadLength, int? spTotal, int? spIndex, int? messageId}) {
//
HeartbeatResponse heartbeatResponse = HeartbeatResponse.fromBytes(byte);
return heartbeatResponse;

View File

@ -38,7 +38,7 @@ class UdpRemoteUnLockHandler extends ScpMessageBaseHandle implements ScpMessageH
}
@override
deserializePayload({required int payloadType, required int messageType, required Uint8List byte, int? offset, int? PayloadLength, int? spTotal, int? spIndex, int? messageId}) {
deserializePayload({required int payloadType, required int messageType, required List<int> byte, int? offset, int? PayloadLength, int? spTotal, int? spIndex, int? messageId}) {
if (messageType == MessageTypeConstant.Resp) {
final GenericResp genericResp = GenericResp();
genericResp.mergeFromBuffer(byte);

View File

@ -44,7 +44,7 @@ class UdpTalkAcceptHandler extends ScpMessageBaseHandle
stopRingtone();
//
talkStatus.setAnsweredSuccessfully();
talkStatus.setDuringCall();
talkStatus.setWaitingData();
}
}
@ -58,7 +58,7 @@ class UdpTalkAcceptHandler extends ScpMessageBaseHandle
deserializePayload(
{required int payloadType,
required int messageType,
required Uint8List byte,
required List<int> byte,
int? offset,
int? PayloadLength,
int? spTotal,

View File

@ -30,10 +30,45 @@ class UdpTalkDataHandler extends ScpMessageBaseHandle
talkDataOverTimeTimerManager.receiveMessage();
if (scpMessage.Payload != null) {
final TalkData talkData = scpMessage.Payload;
print('talkData: ${listToHexString(talkData.content)}');
//
_handleTalkData(talkData: talkData);
//
talkStatus.setDuringCall();
}
}
@override
deserializePayload(
{required int payloadType,
required int messageType,
required List<int> byte,
int? offset,
int? PayloadLength,
int? spTotal,
int? spIndex,
int? messageId}) {
if (messageType == MessageTypeConstant.RealTimeData) {
print(
'收到音视频数据:${byte.length} messageId:$messageId spTotal:$spTotal spIndex:$spIndex PayloadLength:$PayloadLength');
//
if (spTotal != null &&
spTotal > 1 &&
messageId != null &&
spIndex != null) {
//
return handleFragmentedPayload(
messageId: messageId,
spTotal: spTotal,
spIndex: spIndex,
byte: byte,
payloadType: payloadType,
);
} else {
//
final TalkData talkData = TalkData();
talkData.mergeFromBuffer(byte);
return talkData;
}
}
}
@ -69,7 +104,15 @@ class UdpTalkDataHandler extends ScpMessageBaseHandle
}
///
void _handleVideoImage(TalkData talkData) {}
void _handleVideoImage(TalkData talkData) {
final List<Uint8List> processCompletePayload =
_processCompletePayload(Uint8List.fromList(talkData.content));
//
processCompletePayload.forEach((element) {
talkData.content = element;
talkDataRepository.addTalkData(talkData);
});
}
/// g711音频数据
void _handleVideoG711(TalkData talkData) {
@ -84,36 +127,36 @@ class UdpTalkDataHandler extends ScpMessageBaseHandle
}
}
@override
deserializePayload(
{required int payloadType,
required int messageType,
required Uint8List byte,
int? offset,
int? PayloadLength,
int? spTotal,
int? spIndex,
int? messageId}) {
if (messageType == MessageTypeConstant.RealTimeData) {
//
if (spTotal != null &&
spTotal > 1 &&
messageId != null &&
spIndex != null) {
//
return handleFragmentedPayload(
messageId: messageId,
spTotal: spTotal,
spIndex: spIndex,
byte: byte,
payloadType: payloadType,
);
///
List<Uint8List> _processCompletePayload(Uint8List payload) {
//
List<Uint8List> frames = [];
// (0xFFD8 , 0xFFD9 )
int startIdx = payload.indexOf(0xFF);
while (startIdx != -1 && startIdx + 1 < payload.length) {
if (payload[startIdx + 1] == 0xD8) {
// 0xFFD8
int endIdx = startIdx + 2;
while (endIdx < payload.length - 1) {
endIdx = payload.indexOf(0xFF, endIdx);
if (endIdx == -1) break;
if (endIdx + 1 < payload.length && payload[endIdx + 1] == 0xD9) {
// 0xFFD9
Uint8List frame = payload.sublist(startIdx, endIdx + 2);
frames.add(frame);
startIdx = endIdx + 2; //
break;
} else {
endIdx += 1; //
}
}
} else {
//
final TalkData talkData = TalkData();
talkData.mergeFromBuffer(byte);
return talkData;
startIdx = payload.indexOf(0xFF, startIdx + 1); //
}
}
//
return frames;
}
}

View File

@ -49,7 +49,7 @@ class UdpTalkExpectHandler extends ScpMessageBaseHandle
deserializePayload(
{required int payloadType,
required int messageType,
required Uint8List byte,
required List<int> byte,
int? offset,
int? PayloadLength,
int? spTotal,

View File

@ -53,7 +53,7 @@ class UdpTalkHangUpHandler extends ScpMessageBaseHandle
deserializePayload(
{required int payloadType,
required int messageType,
required Uint8List byte,
required List<int> byte,
int? offset,
int? PayloadLength,
int? spTotal,

View File

@ -36,7 +36,7 @@ class UdpTalkPingHandler extends ScpMessageBaseHandle
deserializePayload(
{required int payloadType,
required int messageType,
required Uint8List byte,
required List<int> byte,
int? offset,
int? PayloadLength,
int? spTotal,

View File

@ -37,7 +37,7 @@ class UdpTalkPushHandler extends ScpMessageBaseHandle
deserializePayload(
{required int payloadType,
required int messageType,
required Uint8List byte,
required List<int> byte,
int? offset,
int? PayloadLength,
int? spTotal,

View File

@ -35,7 +35,7 @@ class UdpTalkReceiverTransferHandler extends ScpMessageBaseHandle
deserializePayload(
{required int payloadType,
required int messageType,
required Uint8List byte,
required List<int> byte,
int? offset,
int? PayloadLength,
int? spTotal,

View File

@ -50,7 +50,7 @@ class UdpTalkRejectHandler extends ScpMessageBaseHandle
deserializePayload(
{required int payloadType,
required int messageType,
required Uint8List byte,
required List<int> byte,
int? offset,
int? PayloadLength,
int? spTotal,

View File

@ -95,7 +95,7 @@ class UdpTalkRequestHandler extends ScpMessageBaseHandle
deserializePayload(
{required int payloadType,
required int messageType,
required Uint8List byte,
required List<int> byte,
int? offset,
int? PayloadLength,
int? spTotal,

View File

@ -34,7 +34,7 @@ class UnKnowPayloadTypeHandler extends ScpMessageBaseHandle
deserializePayload(
{required int payloadType,
required int messageType,
required Uint8List byte,
required List<int> byte,
int? offset,
int? PayloadLength,
int? spTotal,

View File

@ -1,5 +1,6 @@
import 'dart:async';
import 'dart:convert';
import 'dart:typed_data';
import 'package:audioplayers/audioplayers.dart';
import 'package:flutter_local_notifications/flutter_local_notifications.dart';
@ -19,6 +20,7 @@ import 'package:star_lock/talk/startChart/start_chart_talk_status.dart';
class ScpMessageBaseHandle {
final startChartManage = StartChartManage();
final List<int> _buffer = [];
///
// messageId
@ -33,12 +35,12 @@ class ScpMessageBaseHandle {
//
final talkePingOverTimeTimerManager = OverTimeTimerManager(
timeoutInSeconds: 15,
timeoutInSeconds: 55,
);
//
final talkDataOverTimeTimerManager = OverTimeTimerManager(
timeoutInSeconds: 13,
timeoutInSeconds: 53,
);
//
@ -86,7 +88,7 @@ class ScpMessageBaseHandle {
}) {
//
String key = '$messageId-$payloadType';
if (!_packetBuffer.containsKey(messageId)) {
if (!_packetBuffer.containsKey(key)) {
_packetBuffer[key] = List.filled(spTotal, []);
_startTimer(key);
}
@ -104,24 +106,17 @@ class ScpMessageBaseHandle {
//
if (_packetBuffer[key]!.every((packet) => packet.isNotEmpty)) {
//
List<int> completePayload =
_packetBuffer[key]!.expand((packet) => packet).toList();
Uint8List completePayload = Uint8List.fromList(
_packetBuffer[key]!.expand((packet) => packet).toList());
//
_clearPacketData(key);
// payload
// 使TalkData
if (payloadType == PayloadTypeConstant.talkData) {
final TalkData talkData = TalkData();
final talkData = TalkData();
talkData.mergeFromBuffer(completePayload);
return talkData;
}
// if (payloadType == PayloadTypeConstant.echoTest) {
// return completePayload;
// } else {
// String payload = utf8.decode(completePayload);
// return payload;
// }
} else {
// null
return null;

View File

@ -19,7 +19,7 @@ abstract class ScpMessageHandler {
dynamic deserializePayload({
required int payloadType,
required int messageType,
required Uint8List byte,
required List<int> byte,
int? offset,
int? PayloadLength,
int? spTotal,

View File

@ -17,7 +17,7 @@ import 'talk_data.pbenum.dart';
export 'talk_data.pbenum.dart';
/// 使Req
/// 使(Req/Resp)(RealTimeData)
/// Ping
class TalkData extends $pb.GeneratedMessage {
factory TalkData({
@ -78,6 +78,7 @@ class TalkData extends $pb.GeneratedMessage {
@$pb.TagNumber(1)
void clearContentType() => clearField(1);
/// PCM的字节H264的字节
@$pb.TagNumber(2)
$core.List<$core.int> get content => $_getN(1);
@$pb.TagNumber(2)

View File

@ -3,7 +3,7 @@ syntax = "proto3";
package main;
option go_package = "./spb/talk";
// 使Req
// 使(Req/Resp)(RealTimeData)
// Ping
message TalkData {
// H264G711
@ -13,10 +13,10 @@ message TalkData {
G711 = 2;
};
ContentTypeE ContentType = 1;
// PCM的字节H264的字节
bytes Content = 2;
// 0ms21000ms
//
//
uint32 DurationMs = 3;
//
//
uint32 DurationMs = 3;
}

View File

@ -21,6 +21,7 @@ import 'package:star_lock/talk/startChart/entity/relay_info_entity.dart';
import 'package:star_lock/talk/startChart/entity/report_information_data.dart';
import 'package:star_lock/talk/startChart/entity/scp_message.dart';
import 'package:star_lock/talk/startChart/entity/star_chart_register_node_entity.dart';
import 'package:star_lock/talk/startChart/exception/start_chart_message_exception.dart';
import 'package:star_lock/talk/startChart/handle/scp_message_handle.dart';
import 'package:star_lock/talk/startChart/handle/scp_message_handler_factory.dart';
import 'package:star_lock/talk/startChart/proto/talk_data.pb.dart';
@ -363,10 +364,6 @@ class StartChartManage {
//
void sendTalkExpectMessage({required TalkExpect talkExpect}) async {
if (talkStatus.status != TalkStatus.duringCall) {
_log(text: '当前未处于接听状态, 无法发送期望接受数据消息');
return;
}
final message = MessageCommand.talkExpectMessage(
ToPeerId: ToPeerId,
FromPeerId: FromPeerId,
@ -407,10 +404,6 @@ class StartChartManage {
//
Future<void> sendTalkPingMessage(
{required String ToPeerId, required String FromPeerId}) async {
if (talkStatus.status != TalkStatus.duringCall) {
_log(text: '当前未处于接听状态, 无法发送通话保持消息');
return;
}
final message = MessageCommand.talkPingMessage(
ToPeerId: ToPeerId,
FromPeerId: FromPeerId,
@ -474,7 +467,8 @@ class StartChartManage {
var result = await _udpSocket?.send(
message, InternetAddress(remoteHost), remotePort);
if (result != message.length) {
AppLog.log('❌Udp send data error----> $result ${message.length}');
throw StartChartMessageException(
'❌Udp send data error----> $result ${message.length}');
// _udpSocket = null;
}
}
@ -663,7 +657,7 @@ class StartChartManage {
.signPKCS1v15Bytes(signData, fastRsa.Hash.SHA256, pemPrivateKey);
resultSign = hex.encode(result);
} catch (e) {
_log(text: '❌--->上报信息生成签名时出现错误: $e');
throw StartChartMessageException('❌--->上报信息生成签名时出现错误: $e');
e.printError();
}
return resultSign ?? '';
@ -785,14 +779,14 @@ class StartChartManage {
}
if (deserialize.PayloadType != PayloadTypeConstant.heartbeat) {
if (deserialize.Payload != null) {
_log(text: 'Udp收到结构体数据---》$deserialize');
// _log(text: 'Udp收到结构体数据---》$deserialize');
}
// _log(text: 'text---》${utf8.decode(deserialize.Payload)}');
}
}
} catch (e, stackTrace) {
_log(text: '❌ Udp result data error ----> $e');
_log(text: '堆栈跟踪:\n$stackTrace');
throw StartChartMessageException(
'❌ Udp result data error ----> $e\n,$stackTrace');
}
}
});
@ -815,7 +809,7 @@ class StartChartManage {
handler.handleInvalidReq(scpMessage);
}
} catch (e, stackTrace) {
_log(text: '❌ 处理udp返回数据时遇到错误---> $e\n,$stackTrace');
throw StartChartMessageException('❌ 处理udp返回数据时遇到错误---> $e\n,$stackTrace');
}
}

View File

@ -64,6 +64,13 @@ class StartChartTalkStatus {
// "waitingAnswer"
}
///
void setWaitingData() {
_setStatus(TalkStatus.waitingData);
// "waitingAnswer"
}
///
void setDuringCall() {
_setStatus(TalkStatus.duringCall);