fix:增加音视频数据的丢包率判断、调整udp发送和接收缓冲区大小

This commit is contained in:
liyi 2025-06-18 14:59:34 +08:00
parent 9f2c049147
commit bf4c2b4750

View File

@ -50,6 +50,10 @@ import 'package:star_lock/tools/deviceInfo_utils.dart';
import 'package:star_lock/tools/storage.dart';
import 'package:uuid/uuid.dart';
// Socket选项常量
const int SO_RCVBUF = 8; //
const int SO_SNDBUF = 7; //
class StartChartManage {
// new对象
StartChartManage._internal();
@ -125,6 +129,17 @@ class StartChartManage {
// StartChartTalkStatus
StartChartTalkStatus talkStatus = StartChartTalkStatus.instance;
//
final Map<int, Set<int>> _avFrameParts = {};
int _avFrameTotal = 0;
int _avFrameLost = 0;
//
double getAvFrameLossRate() {
if (_avFrameTotal == 0) return 0.0;
return _avFrameLost / _avFrameTotal;
}
//
Future<void> init() async {
if (F.isXHJ) {
@ -225,6 +240,25 @@ class StartChartManage {
var addressIListenFrom = InternetAddress.anyIPv4;
RawDatagramSocket.bind(addressIListenFrom, localPort)
.then((RawDatagramSocket socket) {
// (SO_RCVBUF = 8)
socket.setRawOption(
RawSocketOption.fromInt(
RawSocketOption.levelSocket,
8, // SO_RCVBUF for Android/iOS
2 * 1024 * 1024, // 2MB receive buffer
),
);
// (SO_SNDBUF = 7)
socket.setRawOption(
RawSocketOption.fromInt(
RawSocketOption.levelSocket,
7, // SO_SNDBUF for Android/iOS
2 * 1024 * 1024, // 2MB send buffer
),
);
_udpSocket = socket;
/// 广
@ -1017,35 +1051,54 @@ class StartChartManage {
void _onReceiveData(RawDatagramSocket socket, BuildContext context) {
socket.listen((RawSocketEvent event) {
if (event == RawSocketEvent.read) {
Datagram? dg = socket.receive();
try {
if (dg?.data != null) {
final deserialize = ScpMessage.deserialize(dg!.data);
Datagram? dg;
while ((dg = socket.receive()) != null) {
try {
if (dg?.data != null) {
final deserialize = ScpMessage.deserialize(dg!.data);
// //ToDo:
// UdpTalkDataHandler().updateRecvDataRate(dg.data.length);
// //
// Provider.of<DebugInfoModel>(context, listen: false).updateDebugInfo(
// UdpTalkDataHandler().getLastRecvDataRate() ~/ 1024, // KB
// UdpTalkDataHandler().getLastRecvPacketCount(),
// UdpTalkDataHandler().getLastSendDataRate() ~/ 1024, // KB
// UdpTalkDataHandler().getLastSendPacketCount(),
// );
if (deserialize != null) {
//
_handleUdpResultData(deserialize);
}
if (deserialize.PayloadType != PayloadTypeConstant.heartbeat) {
if (deserialize.Payload != null) {
// _log(text: 'Udp收到结构体数据---》$deserialize');
// PayloadType==talkData的数据包
if (deserialize != null &&
deserialize.PayloadType == PayloadTypeConstant.talkData) {
int? msgId = deserialize.MessageId;
int spTotal = deserialize.SpTotal ?? 1;
int spIndex = deserialize.SpIndex ?? 1;
if (msgId != null) {
//
_avFrameParts.putIfAbsent(msgId, () => <int>{});
_avFrameParts[msgId]!.add(spIndex);
//
if (spIndex == spTotal) {
_avFrameTotal++;
if (_avFrameParts[msgId]!.length < spTotal) {
_avFrameLost++;
// _log(text: '音视频丢包丢失的messageId: $msgId');
}
_avFrameParts.remove(msgId);
// 100
if (_avFrameTotal % 100 == 0) {
_log(
text:
'音视频帧丢包率: ${(getAvFrameLossRate() * 100).toStringAsFixed(2)}%');
}
}
}
}
if (deserialize != null) {
//
_handleUdpResultData(deserialize);
}
// if (deserialize.PayloadType != PayloadTypeConstant.heartbeat) {
// if (deserialize.Payload != null) {
// _log(text: 'Udp收到结构体数据---》$deserialize');
// }
// _log(text: 'text---》${utf8.decode(deserialize.Payload)}');
// }
}
} catch (e, stackTrace) {
throw StartChartMessageException('$e\n,$stackTrace');
}
} catch (e, stackTrace) {
throw StartChartMessageException('$e\n,$stackTrace');
}
}
});