1.更新MDNS广播的服务类型命名规范,防止出现多设备打开找不到MDNS的广播的问题 2.更新区分前后板的TAG

This commit is contained in:
钟富强 2024-09-02 10:22:41 +08:00
parent e0c1e37191
commit 09c5843358
22 changed files with 501 additions and 304 deletions

View File

@ -105,6 +105,7 @@
<QtMoc Include="SourceCode\Network\mdns\servicemodel.h" />
<QtMoc Include="SourceCode\Network\mdns\qmdnsengine\include\abstractserver.h" />
<QtMoc Include="SourceCode\Network\httpClient.h" />
<QtMoc Include="SourceCode\Media\VideoDecoder\FocusWindow.h" />
<ClInclude Include="SourceCode\Network\mdns\qmdnsengine\include\bitmap.h" />
<QtMoc Include="SourceCode\Network\mdns\qmdnsengine\include\browser.h" />
<QtMoc Include="SourceCode\Network\mdns\qmdnsengine\include\cache.h" />

View File

@ -160,6 +160,9 @@
<QtMoc Include="SourceCode\Network\httpClient.h">
<Filter>Network</Filter>
</QtMoc>
<QtMoc Include="SourceCode\Media\VideoDecoder\FocusWindow.h">
<Filter>Media\VideoDecoder</Filter>
</QtMoc>
</ItemGroup>
<ItemGroup>
<None Include=".editorconfig" />

View File

@ -15,7 +15,7 @@ FFmpegDecoder::FFmpegDecoder(QObject* parent) :
{
av_log_set_level(AV_LOG_QUIET); // 设置日志级别为安静模式
avformat_network_init(); // 初始化网络
//qDebug() << "FFmpegDecoder created";
qDebug() << "FFmpegDecoder created";
}
FFmpegDecoder::~FFmpegDecoder()
@ -31,16 +31,54 @@ FFmpegDecoder::~FFmpegDecoder()
qDebug() << "FFmpegDecoder destroyed";
}
void FFmpegDecoder::processVideo(int itemIndex)
{
#if 0
int width = 720;
int height = 1280;
#elif 1
int width = 640;
int height = 480;
#else
int width = 480;
int height = 640;
#endif
if (width * 16 == height * 9) {
FocusWindowDialog* dialog = new FocusWindowDialog(nullptr, QSize(540, 960));
dialog->exec();
}
else if (width * 9 == height * 16) {
FocusWindowDialog* dialog = new FocusWindowDialog(nullptr, QSize(960, 540));
dialog->exec();
}
else if (width * 4 == height * 3) {
FocusWindowDialog* dialog = new FocusWindowDialog(nullptr, QSize(480, 640));
dialog->exec();
}
else if (width * 3 == height * 4) {
FocusWindowDialog* dialog = new FocusWindowDialog(nullptr, QSize(640, 480));
dialog->exec();
}
}
void FFmpegDecoder::initialize()
{
// 初始化FFmpeg库
avformat_network_init();
}
void FFmpegDecoder::stopFFmpegDecoder()
{
mutex.lock();
abort = true;
condition.wakeOne(); // 唤醒等待的线程
mutex.unlock();
}
void FFmpegDecoder::decodeFile(const QString& filePath, QLabel* videoDisplayLabel)
{
QMutexLocker locker(&mutex);
this->filePath = filePath;
this->filePath = filePath;
this->videoLabel = videoDisplayLabel;
if (!isRunning()) {
qDebug() << "Starting decoder thread";
@ -55,7 +93,7 @@ void FFmpegDecoder::run()
QFile file(filePath);
qint64 fileSize = 0;
while (true) {
while (!isInterruptionRequested()) {
mutex.lock();
while (!restart && !abort) {
condition.wait(&mutex);
@ -65,14 +103,12 @@ void FFmpegDecoder::run()
qDebug() << "Decoder thread aborting";
break;
}
restart = false;
QLabel* currentVideoLabel = videoLabel;
QSize labelSize = currentVideoLabel->size();
mutex.unlock();
if (labelSize.width() <= 0 || labelSize.height() <= 0) {
// 自动调整 QLabel 大小
labelSize = QSize(800, 600); // 例如设置为默认大小
if (labelSize.width() < 740 || labelSize.height() < 357) {
labelSize = QSize(740, 357);
currentVideoLabel->setFixedSize(labelSize);
qDebug() << "Adjusting video label size to: Width =" << labelSize.width() << ", Height =" << labelSize.height();
}
@ -88,14 +124,18 @@ void FFmpegDecoder::run()
file.close();
continue;
}
restart = false;
while (!abort) {
qint64 currentFileSize = file.size();
//qDebug() << "Decoder thread currentFileSize:" << currentFileSize;
//qDebug() << "Decoder thread fileSize:" << fileSize;
if (currentFileSize > fileSize) {
fileSize = currentFileSize;
file.seek(fileSize); // 设置文件读取位置到末尾
//qDebug() << "---------------1---------------";
// 读取并处理数据包
while (av_read_frame(formatContext, packet) >= 0) {
//qDebug() << "---------------2---------------";
if (packet->stream_index == videoStreamIndex) {
int ret = avcodec_send_packet(codecContext, packet);
if (ret < 0) {
@ -103,6 +143,7 @@ void FFmpegDecoder::run()
av_packet_unref(packet);
continue;
}
//qDebug() << "---------------3---------------";
while (ret >= 0) {
ret = avcodec_receive_frame(codecContext, frame);
if (ret == AVERROR(EAGAIN) || ret == AVERROR_EOF) {
@ -113,28 +154,31 @@ void FFmpegDecoder::run()
qWarning() << "Error during decoding";
break;
}
qDebug() << "H264 video resolution: Width =" << frame->width << ", Height =" << frame->height;
//qDebug() << "---------------4---------------";
QImage img = avFrameToQImage(frame);
//qDebug() << "---------------5---------------";
QImage scaledImage = img.scaled(labelSize, Qt::KeepAspectRatio, Qt::SmoothTransformation);
//qDebug() << "---------------6---------------";
currentVideoLabel->setPixmap(QPixmap::fromImage(scaledImage));
QThread::msleep(10); // Simulate 25 FPS frame rate
//qDebug() << "---------------7---------------";
}
}
av_packet_unref(packet);
//qDebug() << "---------------8---------------";
}
}
//qDebug() << "---------------9---------------";
mutex.lock();
if (restart) {
restart = false;
mutex.unlock();
break;
}
//qDebug() << "---------------10---------------";
mutex.unlock();
}
//qDebug() << "---------------11---------------";
cleanup();
file.close();
@ -148,6 +192,10 @@ void FFmpegDecoder::run()
bool FFmpegDecoder::initializeFFmpeg(const QString& filePath)
{
if (!QFile::exists(filePath)) {
qWarning() << "FFmpeg File does not exist:" << filePath;
return false;
}
if (avformat_open_input(&formatContext, filePath.toStdString().c_str(), nullptr, nullptr) != 0) {
qWarning() << "Failed to open file with FFmpeg:" << filePath;
return false;
@ -227,6 +275,8 @@ QImage FFmpegDecoder::avFrameToQImage(AVFrame* frame)
{
int width = frame->width;
int height = frame->height;
qDebug() << "H264 video resolution: Width =" << frame->width << ", Height =" << frame->height;
AVPixelFormat pixFmt = (AVPixelFormat)frame->format;
if (!swsContext) {

View File

@ -14,8 +14,10 @@
#include <QWaitCondition>
#include <cstdint>
#include <vector>
#include <QDir>
#include "RingBuffer.h"
#include "FocusWindow.h"
extern "C" {
#include <libavcodec/avcodec.h>
@ -38,9 +40,10 @@ public:
void initialize();
void decodeFile(const QString& filePath, QLabel* videoLabel);
void decodeSingleFrame(const QByteArray& data, QLabel* videoLabel); // 添加 videoLabel 参数
void FFmpegDecoder::processVideo(int itemIndex);
bool initializeFFmpeg(const QString& filePath);
void cleanup();
void stopFFmpegDecoder();
protected:
void run() override;
@ -48,19 +51,19 @@ protected:
private:
QImage avFrameToQImage(AVFrame* frame);
QMutex mutex;
QWaitCondition condition;
QString filePath;
QLabel* videoLabel;
bool abort;
bool restart;
QMutex mutex;
QWaitCondition condition;
QString filePath;
QLabel* videoLabel;
bool abort;
bool restart;
AVFormatContext* formatContext;
AVCodecContext* codecContext;
AVFrame* frame;
AVPacket* packet;
SwsContext* swsContext;
int videoStreamIndex;
AVCodecContext* codecContext;
AVFrame* frame;
AVPacket* packet;
SwsContext* swsContext;
int videoStreamIndex;
RingBuffer* ringBuffer;
//QLabel* singleFrameLabel; // 用于解码单帧的标签

View File

@ -0,0 +1,26 @@
#include <QDialog>
#include <QVBoxLayout>
#include <QLabel>
#include <QPushButton>
class FocusWindowDialog : public QDialog
{
Q_OBJECT
public:
FocusWindowDialog(QWidget* parent = nullptr, const QSize& labelSize = QSize(480, 640)) : QDialog(parent)
{
QVBoxLayout* layout = new QVBoxLayout(this);
QLabel* label = new QLabel("1111 This is a new window opened by clicking the new button.", this);
label->setFixedSize(labelSize); // 设置QLabel的固定大小
layout->addWidget(label);
QPushButton* closeButton = new QPushButton("Close", this);
layout->addWidget(closeButton);
connect(closeButton, &QPushButton::clicked, this, &FocusWindowDialog::accept);
setLayout(layout);
setWindowTitle("SL100 视频播放窗口");
//resize(500, 700); // 设置对话框的大小
}
};

View File

@ -9,7 +9,7 @@ ClientHandler::ClientHandler(QTcpSocket* socket,
QJsonArray frontBoardDevInfoJson, QJsonArray frontBoardLicenseJson,
QJsonArray backBoardOneClickTest, QJsonArray backBoardTest, QJsonArray backBoardFuncConfig,
QJsonArray backBoardDevInfoJson, QJsonArray backBoardUuidJson,
QJsonArray getPicJson, QJsonArray getVideoJson, int clientId, QObject* parent)
QJsonArray getPicJson, QJsonArray getVideoJson, int clientId, int isBackBoardOrAllBoard, QObject* parent)
: QObject(parent), socket(socket),
frontBoardOneClickTest(frontBoardOneClickTest), frontBoardTest(frontBoardTest),
frontBoardFuncConfig(frontBoardFuncConfig), frontBoardDevInfoJson(frontBoardDevInfoJson),
@ -17,7 +17,7 @@ ClientHandler::ClientHandler(QTcpSocket* socket,
backBoardOneClickTest(backBoardOneClickTest), backBoardTest(backBoardTest),
backBoardFuncConfig(backBoardFuncConfig), backBoardDevInfoJson(backBoardDevInfoJson),
backBoardUuidJson(backBoardUuidJson), getPicJson(getPicJson), getVideoJson(getVideoJson),
currentItemIndex(0), clientId(clientId),
currentItemIndex(0), clientId(clientId), isBackBoardOrAllBoard(isBackBoardOrAllBoard),
isManualSend(false), isSingleSend(false), isClickedSend(false), size(0),
isFirstDataReceived(true), processDataFunction(nullptr),
isDataStuck(false), dataProcessingActive(false), isRecvVideoData(true),
@ -35,6 +35,37 @@ ClientHandler::~ClientHandler() {
qDebug() << "ClientHandler destroyed for clientId:" << clientId;
}
// 实现 QRunnable 的 run 函数,在线程池中执行
void ClientHandler::run()
{
start();
}
// 重置索引
void ClientHandler::resetCurrentItemIndex()
{
currentItemIndex = 0;
currentFuncItemIndex = 0;
itemsProcessedCount = 0;
emit startTimeout(0);
}
// 开始处理客户端
void ClientHandler::start()
{
resetCurrentItemIndex(); // 初始化计数器和索引
sendNextItem();
}
// 处理客户端断开连接
void ClientHandler::onDisconnected() {
qDebug() << ">>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>";
qDebug() << "> A device is disconnected. ID:" << clientId;
qDebug() << ">>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>";
emit clientDisconnected(this);
socket->deleteLater();
}
void ClientHandler::startReadVideoDataTimer(int client_Id)
{
//emit startReadTimer(clientId);
@ -94,31 +125,9 @@ QString ClientHandler::getClientAddress() const
return socket->peerAddress().toString() + ":" + QString::number(socket->peerPort());
}
// 实现 QRunnable 的 run 函数,在线程池中执行
void ClientHandler::run()
{
start();
}
// 重置索引
void ClientHandler::resetCurrentItemIndex()
{
currentItemIndex = 0;
currentFuncItemIndex = 0;
itemsProcessedCount = 0;
emit startTimeout(0);
}
// 开始处理客户端
void ClientHandler::start()
{
resetCurrentItemIndex(); // 初始化计数器和索引
sendNextItem();
}
void ClientHandler::sendDataToClient(const QByteArray& data)
{
emit sendData(data);
emit sendData(data, isBackBoardOrAllBoard);
}
void ClientHandler::sendJsonItem(const QJsonArray& jsonArray, int itemIndex, const QString text, const QString& itemType)
@ -470,6 +479,8 @@ bool ClientHandler::RNDISFirstData(QByteArray& data) {
setThreadPriority(QThread::LowPriority);
socket->setReadBufferSize(20 * 1024);
controlClientId = clientId;
// 前板有设备连接自动发送获取设备信息
//sendDevInfoItem();
break;
default:
qWarning() << "Unhandled client type:" << clientType;
@ -671,15 +682,6 @@ void ClientHandler::processPendingData()
}
}
// 处理客户端断开连接
void ClientHandler::onDisconnected() {
qDebug() << ">>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>";
qDebug() << "> A device is disconnected. ID:" << clientId;
qDebug() << ">>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>";
emit clientDisconnected(this);
socket->deleteLater();
}
// 处理超时
void ClientHandler::onTimeout()
{

View File

@ -33,7 +33,7 @@ public:
QJsonArray frontBoardFuncConfig, QJsonArray frontBoardDevInfoJson, QJsonArray frontBoardLicenseJson,
QJsonArray backBoardOneClickTest, QJsonArray backBoardTest, QJsonArray backBoardFuncConfig, QJsonArray backBoardDevInfoJson,
QJsonArray backBoardUuidJson, QJsonArray getPicJson, QJsonArray getVideoJson,
int clientId, QObject* parent = nullptr);
int clientId, int isBackBoardOrAllBoard, QObject* parent = nullptr);
~ClientHandler();
int preVideoClientId = 0;
@ -92,7 +92,7 @@ signals:
const QJsonArray& jsonArray, int itemJsonIndex);
void handleData(QByteArray& data);
// 数据发送信号
void sendData(const QByteArray& data);
void sendData(const QByteArray& data, int isBoardType);
// 状态更新信号
void statusUpdated(const QString& client, int itemIndex, int funcItemIndex,
bool success, const QString& itemData, const QString& funcItemData,
@ -144,6 +144,7 @@ private:
int currentItemIndex; // 当前处理的测试 JSON 项目索引
int currentFuncItemIndex; // 当前处理的功能 JSON 项目索引
int clientId; // 新增的客户端编号
int isBackBoardOrAllBoard;
int itemsProcessedCount; // 跟踪处理项目的数量

View File

@ -27,6 +27,8 @@
#include <QtCore/qglobal.h>
#define BUILD_SHARED_LIBS
#define QMDNSENGINE_LIBRARY
#if defined(BUILD_SHARED_LIBS)
# if defined(QMDNSENGINE_LIBRARY)
# define QMDNSENGINE_EXPORT Q_DECL_EXPORT

View File

@ -339,7 +339,10 @@ void toPacket(const Message &message, QByteArray &packet)
{
quint16 offset = 0;
quint16 flags = (message.isResponse() ? 0x8400 : 0) |
(message.isTruncated() ? 0x200 : 0);
(message.isTruncated() ? 0x200 : 0);
qDebug() << "Flags set in toPacket:" << QString::number(flags, 16);
writeInteger<quint16>(packet, offset, message.transactionId());
writeInteger<quint16>(packet, offset, flags);
writeInteger<quint16>(packet, offset, message.queries().length());

View File

@ -71,7 +71,6 @@ void ProberPrivate::assertRecord()
message.addQuery(query);
message.addRecord(proposedRecord);
server->sendMessageToAll(message);
// Wait two seconds to confirm it is unique
timer.stop();
timer.start(2 * 1000);
@ -80,14 +79,15 @@ void ProberPrivate::assertRecord()
void ProberPrivate::onMessageReceived(const Message &message)
{
// If the response matches the proposed record, increment the suffix and
// try with the new name
if (confirmed || !message.isResponse()) {
// try with the new name
//if (confirmed || !message.isResponse()) {
if (confirmed) {
return;
}
const auto records = message.records();
for (const Record &record : records) {
if (record.name() == proposedRecord.name() && record.type() == proposedRecord.type()) {
qDebug() << "Conflict detected for name:" << proposedRecord.name() << "with type:" << record.type();
++suffix;
assertRecord();
}

View File

@ -79,8 +79,8 @@ void ProviderPrivate::confirm()
delete prober;
}
prober = new Prober(server, srvProposed, this);
connect(prober, &Prober::nameConfirmed, [this](const QByteArray &name) {
connect(prober, &Prober::nameConfirmed, [this](const QByteArray &name) {
// If existing records were confirmed, indicate that they are no
// longer valid
if (confirmed) {
@ -128,7 +128,7 @@ void ProviderPrivate::onMessageReceived(const Message &message)
if (!confirmed || message.isResponse()) {
return;
}
//qDebug() << "Failed to start server. Error:" << server->errorString();
bool sendBrowsePtr = false;
bool sendPtr = false;
bool sendSrv = false;
@ -227,13 +227,16 @@ void Provider::update(const Service &service)
return;
}
bool registered = d->hostname->isRegistered();
//qDebug() << "Hostname registered:" << registered;
if(registered) {
// 不确认服务名称,直接进行广播
d->publish();
//if (d->hostname->isRegistered()) {
if (!d->confirmed || fqName != d->srvRecord.name()) {
/*if (!d->confirmed || fqName != d->srvRecord.name()) {
qDebug() << "confirm()";
d->confirm();
} else {
qDebug() << "publish()";
d->publish();
}
}*/
}
}

View File

@ -129,8 +129,6 @@ void Server::sendMessageToAll(const Message &message)
{
QByteArray packet;
toPacket(message, packet);
//qDebug() << "MdnsMsg :" << packet.toHex();
qDebug() << "MdnsPort:" << MdnsPort;
qint64 sentBytes = d->ipv4Socket.writeDatagram(packet, MdnsIpv4Address, MdnsPort);
qDebug() << "ipv4Socket sentBytes:" << sentBytes;
sentBytes = d->ipv6Socket.writeDatagram(packet, MdnsIpv6Address, MdnsPort);

View File

@ -1,4 +1,4 @@
// #include "servicemodel.cpp"
// servicemodel.cpp
#include "servicemodel.h"
Q_DECLARE_METATYPE(QMdnsEngine::Service)

View File

@ -1,3 +1,4 @@
// servicemodel.h
#ifndef SERVICEMODEL_H
#define SERVICEMODEL_H
@ -7,7 +8,8 @@
#include "qmdnsengine/include/hostname.h"
#include "qmdnsengine/include/provider.h"
#include "qmdnsengine/include/service.h"
#include "qmdnsengine/include/message.h"
#include "qmdnsengine/include/query.h"
class ServiceProvider : public QObject
{

View File

@ -27,11 +27,14 @@ DataHandler::DataHandler(QLabel* leftLens_imageLabel, QLabel* rightLens_imageLab
ffmpegDecoder->initialize(); // 初始化解码器
clearAllRecvData();
initializeMsgIdToCmdMap();
qDebug() << "DataHandler created";
}
DataHandler::~DataHandler()
{
qDebug() << "---1--- DataHandler destroyed";
if (ffmpegDecoder) {
ffmpegDecoder->stopFFmpegDecoder();
ffmpegDecoder->requestInterruption();
ffmpegDecoder->wait(); // 等待解码器线程完成
delete ffmpegDecoder;
@ -39,6 +42,14 @@ DataHandler::~DataHandler()
}
delete buffer;
buffer = nullptr;
qDebug() << "---2--- DataHandler destroyed";
}
void DataHandler::handleOpenFocusWindow(int itemIndex)
{
if (ffmpegDecoder) {
ffmpegDecoder->processVideo(itemIndex); // 调用 FFmpegDecoder 的处理函数
}
}
QByteArray DataHandler::hexStringToByteArray(const QString& hexString)
@ -50,16 +61,17 @@ QByteArray DataHandler::hexStringToByteArray(const QString& hexString)
return byteArray;
}
const QString filePath_1 = "add1.h264";
const QString filePath_1 = "/add1.h264";
// 显示视频的函数
void DataHandler::showVideo(const QString& client, const QByteArray& valData)
{
static QFile file(filePath_1);
QString h264filePath = QDir::currentPath() + filePath_1;
static QFile file(h264filePath);
if (!file.isOpen()) {
if (QFile::exists(filePath_1)) {
QFile::remove(filePath_1);
if (QFile::exists(h264filePath)) {
QFile::remove(h264filePath);
}
if (!file.open(QIODevice::Append | QIODevice::WriteOnly)) {
qWarning() << "无法打开H264文件:" << file.errorString();
@ -74,7 +86,7 @@ void DataHandler::showVideo(const QString& client, const QByteArray& valData)
if (!start_run) {
start_run = 1;
ffmpegDecoder->decodeFile(filePath_1, videoLabel);
ffmpegDecoder->decodeFile(h264filePath, videoLabel);
}
//ffmpegDecoder->decodeFile(filePath_1, videoLabel);
}

View File

@ -46,7 +46,7 @@ public slots:
void handleData(const QString& client, const QByteArray& data, int msg_id, int currentRecvItemIndex,
int currentRecvFuncItemIndex, const QString& itemData, const QString& funcItemData,
const QJsonArray& jsonArray, int itemJsonIndex);
void handleOpenFocusWindow(int itemIndex);
signals:
void statusUpdated(const QString& clientAddress, int currentItemIndex, int currentFuncItemIndex,
bool success, const QString& currentItemLabel, const QString& currentFuncItemLabel,

View File

@ -8,10 +8,11 @@ class NewButtonDialog : public QDialog
Q_OBJECT
public:
NewButtonDialog(QWidget* parent = nullptr) : QDialog(parent)
NewButtonDialog(QWidget* parent = nullptr, const QSize& labelSize = QSize(480, 640)) : QDialog(parent)
{
QVBoxLayout* layout = new QVBoxLayout(this);
QLabel* label = new QLabel("This is a new window opened by clicking the new button.", this);
label->setFixedSize(labelSize); // 设置QLabel的固定大小
layout->addWidget(label);
QPushButton* closeButton = new QPushButton("Close", this);
@ -20,6 +21,6 @@ public:
setLayout(layout);
setWindowTitle("SL100 视频播放窗口");
resize(480, 640); // 设置对话框的大小
//resize(500, 700); // 设置对话框的大小
}
};

View File

@ -1,7 +1,6 @@
// MainWidget.cpp
#include "MainWidget.h"
void onThreadFinished(QThread* thread, ClientHandler* handler)
{
qDebug() << "Thread finished. Deleting handler and thread.";
@ -27,36 +26,79 @@ MainWidget::MainWidget(QWidget* parent) :
multicastTimer(new QTimer(this))
#endif
{
leftLens_imageLabel = new QLabel(this);
rightLens_imageLabel = new QLabel(this);
videoLabel = new QLabel(this);
leftLens_imageLabel = new QLabel(this);
rightLens_imageLabel = new QLabel(this);
videoLabel = new QLabel(this);
frontFuncConfigLineEdit = new QLineEdit(this);
backFuncConfigLineEdit = new QLineEdit(this);
licenseHwInfoEdit = new QTextEdit(this);
UuidHwInfoEdit = new QTextEdit(this);
backFuncConfigLineEdit = new QLineEdit(this);
licenseHwInfoEdit = new QTextEdit(this);
UuidHwInfoEdit = new QTextEdit(this);
// 创建 mDNS 服务的 Server 和 Hostname 对象
QMdnsEngine::Server myserver;
QMdnsEngine::Hostname hostname(&myserver);
// 创建服务提供者Provider
QMdnsEngine::Provider provider(&myserver, &hostname);
// 定义要广播的服务
QMdnsEngine::Service service;
service.setName("Test Service");
service.setType("_test._tcp"); // 服务类型,包括 _tcp 或 _udp
service.setPort(12345); // 服务使用的端口号
// 启动服务广播
provider.update(service);
qDebug() << "mDNS service started. Broadcasting service:"
<< service.name() << service.type() << "on port" << service.port();
setupUI();
// 打印线程池状态信息
setupTimerForThreadPoolInfo();
server = new QTcpServer(this);
/*
// 创建 DataHandler 对象并连接信号
DataHandler* dataHandler = new DataHandler(leftLens_imageLabel, rightLens_imageLabel, videoLabel, licenseHwInfoEdit, &devInfoLineEdits,
frontBoardOneClickTest, frontBoardTest, frontBoardFuncConfig,
frontBoardDevInfoJson, frontBoardLicenseJson,
backBoardOneClickTest, backBoardTest, backBoardFuncConfig, backBoardDevInfoJson,
backBoardUuidJson, getPicJson, getVideoJson, this);
//FactoryToolSendGetUuidToHttpServer();
//FactoryToolSendGetLicenseToHttpServer();
//FactoryToolSendPostComfirmToHttpServer();
//FactoryToolSendPostTestToHttpServer();
//FactoryToolSendPostLicenseToHttpServer();
connect(this, &MainWidget::openFocusWindowRequested, dataHandler, &DataHandler::handleOpenFocusWindow);
connect(dataHandler, &DataHandler::statusUpdated, this, &MainWidget::onStatusUpdated);
*/
connect(server, &QTcpServer::newConnection, this, [this]() {
// 检查是否有挂起的连接
while (server->hasPendingConnections()) {
QTcpSocket* socket = server->nextPendingConnection();
int clientId = nextClientId++;
int clientId = nextClientId ++;
QHostAddress clientIp = socket->peerAddress();
quint16 clientPort = socket->peerPort();
QString ipString = clientIp.toString();
if (ipString.startsWith("::ffff:")) {
ipString = ipString.mid(7);
}
qDebug() << ">>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>";
qDebug() << "> A client is connected. ID:" << clientId;
qDebug() << "> Client IP:" << ipString << " Port:" << clientPort;
qDebug() << ">>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>";
if (ipString.startsWith("10.10.10")) {
qDebug() << "The client IP address is front board !!!";
isBackBoardOrAllBoard = 0;
}
else {
qDebug() << "The client IP address is back board or all board";
isBackBoardOrAllBoard = clientId;
}
stopMdnsService();
connectedClientsCount++;
connectedClientsCount ++;
updateServerButtonText();
QTimer* timer = new QTimer(this);
@ -76,11 +118,11 @@ MainWidget::MainWidget(QWidget* parent) :
}
});
QThread* thread = new QThread(this);
QThread* thread = new QThread(this);
ClientHandler* handler = new ClientHandler(socket, frontBoardOneClickTest, frontBoardTest, frontBoardFuncConfig,
frontBoardDevInfoJson, frontBoardLicenseJson,
backBoardOneClickTest, backBoardTest, backBoardFuncConfig, backBoardDevInfoJson,
backBoardUuidJson, getPicJson, getVideoJson, clientId, nullptr);
backBoardUuidJson, getPicJson, getVideoJson, clientId, isBackBoardOrAllBoard, nullptr);
// 将 ClientHandler 移动到线程池中的线程
handler->moveToThread(thread);
@ -91,7 +133,7 @@ MainWidget::MainWidget(QWidget* parent) :
});
// 将sendData信号连接到主线程中的槽上
connect(handler, &ClientHandler::sendData, this, [socket](const QByteArray& data) {
connect(handler, &ClientHandler::sendData, this, [socket](const QByteArray& data, int isBoardType) {
/*socket->write(data);
socket->flush();*/
//qDebug() << "---------------------data.size():" << data.size();
@ -99,7 +141,12 @@ MainWidget::MainWidget(QWidget* parent) :
QDataStream stream(&prefix, QIODevice::WriteOnly);
stream.setByteOrder(QDataStream::LittleEndian);
stream << quint32(0x55AA55AA);
stream << quint16(0x0420);
if (isBoardType != 0) {
stream << quint16(0x0421);
}
else {
stream << quint16(0x0420);
}
stream << quint32(data.size());
prefix.append(data);
@ -124,15 +171,20 @@ MainWidget::MainWidget(QWidget* parent) :
connect(handler, &ClientHandler::allItemsProcessed, this, &MainWidget::onAllItemsProcessed);
connect(handler, &ClientHandler::selectClientDisconnected, this, &MainWidget::onDisconnectClient);
#if 1
// 创建 DataHandler 对象并连接信号
DataHandler* dataHandler = new DataHandler(leftLens_imageLabel, rightLens_imageLabel, videoLabel, licenseHwInfoEdit, &devInfoLineEdits,
frontBoardOneClickTest, frontBoardTest, frontBoardFuncConfig,
frontBoardDevInfoJson, frontBoardLicenseJson,
backBoardOneClickTest, backBoardTest, backBoardFuncConfig, backBoardDevInfoJson,
backBoardUuidJson, getPicJson, getVideoJson, this);
connect(handler, &ClientHandler::dataReceived, dataHandler, &DataHandler::handleData);
connect(dataHandler, &DataHandler::statusUpdated, this, &MainWidget::onStatusUpdated);
dataHandlers[clientId] = dataHandler;
connect(this, &MainWidget::openFocusWindowRequested, dataHandler, &DataHandler::handleOpenFocusWindow);
connect(handler, &ClientHandler::dataReceived, dataHandler, &DataHandler::handleData);
connect(dataHandler, &DataHandler::statusUpdated, this, &MainWidget::onStatusUpdated);
#else
connect(handler, &ClientHandler::dataReceived, dataHandler, &DataHandler::handleData);
#endif
connect(handler, &ClientHandler::startReadTimer, this, &MainWidget::startClientReadTimer);
connect(handler, &ClientHandler::stopReadTimer, this, &MainWidget::stopClientReadTimer);
@ -157,7 +209,6 @@ MainWidget::MainWidget(QWidget* parent) :
connectionStatusCheckTimer = new QTimer(this);
connect(connectionStatusCheckTimer, &QTimer::timeout, this, &MainWidget::onCheckConnectionStatus);
//connectionStatusCheckTimer->start(100); // 每100ms检查一次连接状态
connect(mdnsTimer, &QTimer::timeout, this, &MainWidget::startMdnsService);
#if TEST_UDP_BROADCAST
@ -199,6 +250,12 @@ MainWidget::~MainWidget()
delete timer;
}
clientReadTimers.clear();
for (auto dataHandler : dataHandlers) {
dataHandler->deleteLater();
}
dataHandlers.clear();
for (ClientHandler* handler : clients) {
handler->deleteLater();
}
@ -228,6 +285,206 @@ MainWidget::~MainWidget()
qDebug() << "MainWidget destroyed";
}
// 处理客户端断开连接信号
void MainWidget::onClientDisconnected(ClientHandler* handler)
{
int clientId = handler->getClientId();
qDebug() << " preVideoClientId :" << handler->preVideoClientId;
qDebug() << " clientId :" << clientId;
if (handler->preVideoClientId == clientId) {
qDebug() << "Current path: " << QDir::currentPath();
QString filePath = QDir::currentPath() + "/add1.h264";
if (QFile::exists(filePath)) {
QFile file(filePath);
if (file.open(QIODevice::WriteOnly | QIODevice::Truncate)) {
qDebug() << "File add1.h264 cleared successfully.";
}
else {
qDebug() << "Failed to clear file add1.h264:" << file.errorString();
}
}
else {
qDebug() << "File add1.h264 does not exist.";
}
}
if (clientTimers.contains(clientId)) {
QTimer* timer = clientTimers[clientId];
timer->stop();
delete timer;
clientTimers.remove(clientId);
}
clients.removeOne(handler);
/*
ClientHandler
ClientHandler
*/
handler->deleteLater(); // 延迟删除 ClientHandler 对象
qDebug() << "-----------dataHandlers-----------";
if (dataHandlers.contains(clientId)) {
DataHandler* dataHandler = dataHandlers[clientId];
dataHandlers.remove(clientId); // 从容器中移除
dataHandler->deleteLater(); // 延迟删除 DataHandler 对象
}
// 更新连接数并更新按键文本
connectedClientsCount--;
qDebug() << " connectedClientsCount :" << connectedClientsCount;
if (nextClientId <= 2) nextClientId--;
deviceConnected = true;
updateServerButtonText();
}
// 更新按键文本的函数
void MainWidget::updateServerButtonText()
{
if (deviceConnected) {
if (connectedClientsCount > 0) {
startServerButton->setText(tr("正在监听(Listening)\n%1 台设备连接").arg(connectedClientsCount));
}
else if (connectedClientsCount == 0) {
#if START_MDNS // 这里会开启多个mdns广播去掉
startMdnsService();
#endif
deviceConnected = false;
startServerButton->setText(tr("正在监听(Listening)"));
}
}
else if (connectedClientsCount == 0) {
startServerButton->setText(tr("开始监听\n(Start Listening...)"));
}
else {
startServerButton->setText(tr("正在监听(Listening)\n%1 台设备连接").arg(connectedClientsCount));
}
}
// 设置 UI
void MainWidget::setupUI()
{
startServerButton = new QPushButton("开始监听\n(Start Listening...)", this);
startServerButton->setFixedSize(190, 70);
sendAllButton = new QPushButton("一键功能测试", this);
sendAllButton->setFixedSize(190, 70);
sendAllButton->setEnabled(false);
statusListWidget = new QListWidget(this);
statusListWidget->setMinimumSize(350, 840);
statusListWidget->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding);
QHBoxLayout* buttonLayout = new QHBoxLayout;
buttonLayout->addWidget(startServerButton);
buttonLayout->addWidget(sendAllButton);
buttonLayout->addStretch();
QVBoxLayout* leftLayout = new QVBoxLayout;
leftLayout->addLayout(buttonLayout);
leftLayout->setStretch(0, 1);
leftLayout->addWidget(statusListWidget);
leftLayout->setStretch(1, 200);
saveCheckBox = new QCheckBox("", this);
saveCheckBox->setChecked(true);
selectFileButton = new QPushButton("Save", this);
selectFileButton->setFixedSize(45, 28);
clearLogButton = new QPushButton("Clear", this);
clearLogButton->setFixedSize(55, 28);
filePathLineEdit = new QLineEdit(this);
filePathLineEdit->setFixedSize(250, 28);
filePathLineEdit->setReadOnly(true);
QHBoxLayout* fileLayout = new QHBoxLayout;
fileLayout->addWidget(saveCheckBox);
fileLayout->addWidget(selectFileButton);
fileLayout->addWidget(filePathLineEdit);
fileLayout->addWidget(clearLogButton);
leftLayout->addLayout(fileLayout);
leftLayout->setStretch(2, 1);
// 读取 JSON 配置文件
readJsonConfig();
QWidget* leftContainer = new QWidget(this);
leftContainer->setLayout(leftLayout);
leftContainer->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding);
// 前板
QGroupBox* frontDeviceInfoGroupBox = createFrontDeviceInfoGroupBox();
QGroupBox* frontLicenseGroupBox = createLicenseGroupBox();
QHBoxLayout* frontGroupBoxLayout = new QHBoxLayout;
frontGroupBoxLayout->addWidget(frontDeviceInfoGroupBox, 1);
frontGroupBoxLayout->addWidget(frontLicenseGroupBox, 1);
QTabWidget* frontTabWidget = new QTabWidget(this);
frontTabWidget->setFixedSize(900, 315);
QWidget* frontFunctionTestTab = createFunctionTestTab(frontBoardTest, "frontBoardTest");
QWidget* frontFunctionConfigTab = createFunctionConfigTab(frontBoardFuncConfig, "frontBoardFuncConfig");
frontTabWidget->addTab(frontFunctionTestTab, "前板测试项");
frontTabWidget->addTab(frontFunctionConfigTab, "前板配置项");
QTabWidget* mainTabWidget = new QTabWidget(this);
QWidget* frontDevAreaTab = new QWidget(this);
QVBoxLayout* frontDevLayout = new QVBoxLayout(frontDevAreaTab);
frontDevLayout->addLayout(frontGroupBoxLayout);
frontDevLayout->addWidget(frontTabWidget, 2, Qt::AlignTop | Qt::AlignLeft);
mainTabWidget->addTab(frontDevAreaTab, "前 板");
// 后板
QGroupBox* backDeviceInfoGroupBox1 = createBackDeviceInfoGroupBox();
QGroupBox* BackConnectServerGroupBox = createBackConnectServerGroupBox();
QHBoxLayout* backGroupBoxLayout = new QHBoxLayout;
backGroupBoxLayout->addWidget(backDeviceInfoGroupBox1, 1);
backGroupBoxLayout->addWidget(BackConnectServerGroupBox, 1);
QTabWidget* backTabWidget = new QTabWidget(this);
backTabWidget->setFixedSize(900, 315);
QWidget* backFunctionTestTab = createFunctionTestTab(backBoardTest, "backBoardTest");
QWidget* backFunctionConfigTab = createFunctionConfigTab(backBoardFuncConfig, "backBoardFuncConfig");
backTabWidget->addTab(backFunctionTestTab, "后板测试项");
backTabWidget->addTab(backFunctionConfigTab, "后板配置项");
QWidget* backDevAreaTab = new QWidget(this);
QVBoxLayout* backDevLayout = new QVBoxLayout(backDevAreaTab);
backDevLayout->addLayout(backGroupBoxLayout);
backDevLayout->addWidget(backTabWidget, 2, Qt::AlignTop | Qt::AlignLeft);
mainTabWidget->addTab(backDevAreaTab, "后 板");
// 整机
QWidget* allDevAreaTab = new QWidget(this);
QVBoxLayout* allDevLayout = new QVBoxLayout(allDevAreaTab);
mainTabWidget->addTab(allDevAreaTab, "整 机");
QTabWidget* tabWidget_media = new QTabWidget(this);
QWidget* imageDisplayTab = createImageDisplayTab();
QWidget* videoDisplayTab = createVideoDisplayTab();
tabWidget_media->addTab(imageDisplayTab, "图像显示区");
tabWidget_media->addTab(videoDisplayTab, "视频显示区");
QVBoxLayout* rightVerticalLayout = new QVBoxLayout;
rightVerticalLayout->addWidget(mainTabWidget, 5);
rightVerticalLayout->addWidget(tabWidget_media, 4);
QHBoxLayout* mainLayout = new QHBoxLayout;
mainLayout->addWidget(leftContainer, 1, Qt::AlignTop | Qt::AlignLeft);
mainLayout->addLayout(rightVerticalLayout, 3);
setLayout(mainLayout);
setWindowTitle("SL100 工厂产测工具 - V0.0.1");
resize(1340, 900);
connect(startServerButton, &QPushButton::clicked, this, &MainWidget::onStartServerClicked);
connect(sendAllButton, &QPushButton::clicked, this, &MainWidget::onSendAllClicked);
connect(statusListWidget, &QListWidget::itemChanged, this, &MainWidget::scrollToBottom);
connect(selectFileButton, &QPushButton::clicked, this, &MainWidget::onSelectFileButtonClicked);
connect(clearLogButton, &QPushButton::clicked, this, &MainWidget::onclearLogButtonClicked);
connect(saveCheckBox, &QCheckBox::stateChanged, this, &MainWidget::onSaveCheckBoxStateChanged);
}
// 服务器响应
void MainWidget::onHttpRequestFinished(const QJsonObject& response)
{
@ -546,131 +803,6 @@ void MainWidget::readJsonConfig()
getVideoJson = readJson_getVideo();
}
// 设置 UI
void MainWidget::setupUI()
{
startServerButton = new QPushButton("开始监听\n(Start Listening...)", this);
startServerButton->setFixedSize(190, 70);
sendAllButton = new QPushButton("一键功能测试", this);
sendAllButton->setFixedSize(190, 70);
sendAllButton->setEnabled(false);
statusListWidget = new QListWidget(this);
statusListWidget->setMinimumSize(350, 840);
statusListWidget->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding);
QHBoxLayout* buttonLayout = new QHBoxLayout;
buttonLayout->addWidget(startServerButton);
buttonLayout->addWidget(sendAllButton);
buttonLayout->addStretch();
QVBoxLayout* leftLayout = new QVBoxLayout;
leftLayout->addLayout(buttonLayout);
leftLayout->setStretch(0, 1);
leftLayout->addWidget(statusListWidget);
leftLayout->setStretch(1, 200);
saveCheckBox = new QCheckBox("", this);
saveCheckBox->setChecked(true);
selectFileButton = new QPushButton("Save", this);
selectFileButton->setFixedSize(45, 28);
clearLogButton = new QPushButton("Clear", this);
clearLogButton->setFixedSize(55, 28);
filePathLineEdit = new QLineEdit(this);
filePathLineEdit->setFixedSize(250, 28);
filePathLineEdit->setReadOnly(true);
QHBoxLayout* fileLayout = new QHBoxLayout;
fileLayout->addWidget(saveCheckBox);
fileLayout->addWidget(selectFileButton);
fileLayout->addWidget(filePathLineEdit);
fileLayout->addWidget(clearLogButton);
leftLayout->addLayout(fileLayout);
leftLayout->setStretch(2, 1);
// 读取 JSON 配置文件
readJsonConfig();
QWidget* leftContainer = new QWidget(this);
leftContainer->setLayout(leftLayout);
leftContainer->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding);
// 前板
QGroupBox* frontDeviceInfoGroupBox = createFrontDeviceInfoGroupBox();
QGroupBox* frontLicenseGroupBox = createLicenseGroupBox();
QHBoxLayout* frontGroupBoxLayout = new QHBoxLayout;
frontGroupBoxLayout->addWidget(frontDeviceInfoGroupBox, 1);
frontGroupBoxLayout->addWidget(frontLicenseGroupBox, 1);
QTabWidget* frontTabWidget = new QTabWidget(this);
frontTabWidget->setFixedSize(900, 315);
QWidget* frontFunctionTestTab = createFunctionTestTab(frontBoardTest, "frontBoardTest");
QWidget* frontFunctionConfigTab = createFunctionConfigTab(frontBoardFuncConfig, "frontBoardFuncConfig");
frontTabWidget->addTab(frontFunctionTestTab, "前板测试项");
frontTabWidget->addTab(frontFunctionConfigTab, "前板配置项");
QTabWidget* mainTabWidget = new QTabWidget(this);
QWidget* frontDevAreaTab = new QWidget(this);
QVBoxLayout* frontDevLayout = new QVBoxLayout(frontDevAreaTab);
frontDevLayout->addLayout(frontGroupBoxLayout);
frontDevLayout->addWidget(frontTabWidget, 2, Qt::AlignTop | Qt::AlignLeft);
mainTabWidget->addTab(frontDevAreaTab, "前 板");
// 后板
QGroupBox* backDeviceInfoGroupBox1 = createBackDeviceInfoGroupBox();
QGroupBox* BackConnectServerGroupBox = createBackConnectServerGroupBox();
QHBoxLayout* backGroupBoxLayout = new QHBoxLayout;
backGroupBoxLayout->addWidget(backDeviceInfoGroupBox1, 1);
backGroupBoxLayout->addWidget(BackConnectServerGroupBox, 1);
QTabWidget* backTabWidget = new QTabWidget(this);
backTabWidget->setFixedSize(900, 315);
QWidget* backFunctionTestTab = createFunctionTestTab(backBoardTest, "backBoardTest");
QWidget* backFunctionConfigTab = createFunctionConfigTab(backBoardFuncConfig, "backBoardFuncConfig");
backTabWidget->addTab(backFunctionTestTab, "后板测试项");
backTabWidget->addTab(backFunctionConfigTab, "后板配置项");
QWidget* backDevAreaTab = new QWidget(this);
QVBoxLayout* backDevLayout = new QVBoxLayout(backDevAreaTab);
backDevLayout->addLayout(backGroupBoxLayout);
backDevLayout->addWidget(backTabWidget, 2, Qt::AlignTop | Qt::AlignLeft);
mainTabWidget->addTab(backDevAreaTab, "后 板");
// 整机
QWidget* allDevAreaTab = new QWidget(this);
QVBoxLayout* allDevLayout = new QVBoxLayout(allDevAreaTab);
mainTabWidget->addTab(allDevAreaTab, "整 机");
QTabWidget* tabWidget_media = new QTabWidget(this);
QWidget* imageDisplayTab = createImageDisplayTab();
QWidget* videoDisplayTab = createVideoDisplayTab();
tabWidget_media->addTab(imageDisplayTab, "图像显示区");
tabWidget_media->addTab(videoDisplayTab, "视频显示区");
QVBoxLayout* rightVerticalLayout = new QVBoxLayout;
rightVerticalLayout->addWidget(mainTabWidget, 5);
rightVerticalLayout->addWidget(tabWidget_media, 4);
QHBoxLayout* mainLayout = new QHBoxLayout;
mainLayout->addWidget(leftContainer, 1, Qt::AlignTop | Qt::AlignLeft);
mainLayout->addLayout(rightVerticalLayout, 3);
setLayout(mainLayout);
setWindowTitle("SL100 工厂产测工具 - V0.0.1");
resize(1340, 900);
connect(startServerButton, &QPushButton::clicked, this, &MainWidget::onStartServerClicked);
connect(sendAllButton, &QPushButton::clicked, this, &MainWidget::onSendAllClicked);
connect(statusListWidget, &QListWidget::itemChanged, this, &MainWidget::scrollToBottom);
connect(selectFileButton, &QPushButton::clicked, this, &MainWidget::onSelectFileButtonClicked);
connect(clearLogButton, &QPushButton::clicked, this, &MainWidget::onclearLogButtonClicked);
connect(saveCheckBox, &QCheckBox::stateChanged, this, &MainWidget::onSaveCheckBoxStateChanged);
}
void MainWidget::onSelectFileButtonClicked()
{
QString filePath = QFileDialog::getSaveFileName(this, tr("选择文件路径"), "", tr("Text Files (*.txt);;All Files (*)"));
@ -754,75 +886,14 @@ void MainWidget::onDisconnectClient(int clientId)
clientTimers.remove(clientId);
}
handler->deleteLater();
connectedClientsCount--;
connectedClientsCount --;
updateServerButtonText();
break;
}
}
// 启动 mDNS 服务广播
startMdnsService();
}
// 处理客户端断开连接信号
void MainWidget::onClientDisconnected(ClientHandler* handler)
{
int clientId = handler->getClientId();
qDebug() << " preVideoClientId :" << handler->preVideoClientId;
qDebug() << " clientId :" << clientId;
if (handler->preVideoClientId == clientId) {
qDebug() << "Current path: " << QDir::currentPath();
QString filePath = QDir::currentPath() + "/add1.h264";
if (QFile::exists(filePath)) {
QFile file(filePath);
if (file.open(QIODevice::WriteOnly | QIODevice::Truncate)) { // 使用 Truncate 模式打开文件以清空内容
qDebug() << "File add1.h264 cleared successfully.";
}
else {
qDebug() << "Failed to clear file add1.h264:" << file.errorString();
}
}
else {
qDebug() << "File add1.h264 does not exist.";
}
}
if (clientTimers.contains(clientId)) {
QTimer* timer = clientTimers[clientId];
timer->stop();
delete timer;
clientTimers.remove(clientId);
}
clients.removeOne(handler);
/*
ClientHandler
ClientHandler
*/
handler->deleteLater(); // 延迟删除 ClientHandler 对象
// 更新连接数并更新按键文本
connectedClientsCount--;
qDebug() << " connectedClientsCount :" << connectedClientsCount;
if (nextClientId <= 2) nextClientId--;
deviceConnected = true;
updateServerButtonText();
}
// 更新按键文本的函数
void MainWidget::updateServerButtonText()
{
if (deviceConnected) {
deviceConnected = false;
startServerButton->setText(tr("正在监听(Listening)"));
if (connectedClientsCount == 0) startMdnsService();
}
else if (connectedClientsCount == 0) {
startServerButton->setText(tr("开始监听\n(Start Listening...)"));
}
else {
startServerButton->setText(tr("正在监听(Listening)\n%1 台设备连接").arg(connectedClientsCount));
if (connectedClientsCount == 0) {
// 启动 mDNS 服务广播
startMdnsService();
}
}
@ -1026,7 +1097,7 @@ void MainWidget::startMdnsService()
QString formattedTime = currentTime.toString("yyyy-MM-dd hh:mm:ss.zzz");
qDebug() << "[" << formattedTime << "]:" << "Start Mdns Broadcast Service";
QString serviceName = "SL100 FactoryTool Mdns Broadcast Service";
QString serviceType = "_SL100_FactoryTool-service._tcp";
QString serviceType = "_myservice._tcp.local";
quint16 port = TCP_CONNECT_PORT;
mServiceProvider->startServiceBroadcast(serviceName, serviceType, port);
@ -1086,13 +1157,15 @@ void MainWidget::onStartServerClicked()
startServerButton->setText(tr("开始监听\n(Start Listening...)"));
startServerButton->setStyleSheet("");
sendAllButton->setEnabled(false);
stopMdnsService();
}
}
void MainWidget::sendDataToClient(int clientId, const QByteArray& data)
{
if ((clientId == 0) && (isBackBoardOrAllBoard)) {
clientId = isBackBoardOrAllBoard;
}
if (clients_1.contains(clientId)) {
ClientHandler* handler = clients_1[clientId];
handler->sendDataToClient(data); // 调用 ClientHandler 中的方法发送数据
@ -1232,9 +1305,7 @@ void MainWidget::onOpenFocusWindowClicked()
int itemIndex = button->property("getVideoIndex").toInt();
//qDebug() << "New Button clicked with itemIndex:" << itemIndex;
if (itemIndex == 2) {
// 创建并显示新窗口
NewButtonDialog dialog(this);
dialog.exec();
emit openFocusWindowRequested(itemIndex); // 发送信号
}
}
}
@ -1301,7 +1372,7 @@ void MainWidget::onSendBackFuncItemClicked()
QPushButton* button = qobject_cast<QPushButton*>(sender());
int itemIndex = button->property("backBoardFuncConfig").toInt();
for (ClientHandler* handler : clients) {
if (handler->getClientId() == handler->controlClientId) {
if ((isBackBoardOrAllBoard) || (handler->getClientId() == handler->controlClientId)) {
QString text = backFuncConfigLineEdit->text();
qDebug() << "Text in backFuncConfigLineEdit:" << text;
handler->sendBackFuncItem(itemIndex, text);
@ -1342,7 +1413,7 @@ void MainWidget::onSendBackItemClicked()
QPushButton* button = qobject_cast<QPushButton*>(sender());
int itemIndex = button->property("backBoardTest").toInt();
for (ClientHandler* handler : clients) {
if (handler->getClientId() == handler->controlClientId) {
if ((isBackBoardOrAllBoard) || (handler->getClientId() == handler->controlClientId)) {
handler->sendBackItem(itemIndex);
break;
}

View File

@ -54,8 +54,16 @@
#include "FocusWindow.h"
#include "../Network/mdns/qmdnsengine/include/server.h"
#include "../Network/mdns/qmdnsengine/include/hostname.h"
#include "../Network/mdns/qmdnsengine/include/provider.h"
#include "../Network/mdns/qmdnsengine/include/service.h"
#include "../Network/mdns/qmdnsengine/include/message.h"
#include "../Network/mdns/qmdnsengine/include/query.h"
#define TEST_UDP_BROADCAST 0 // 用于测试 UDP 组播实现 mdns 功能 非标准 mdns
#define MANUAL_UPLOAD_LICENSE 0 // 打开手动上传 License的功能
#define START_MDNS 1
#define TCP_CONNECT_PORT 12412 // TCP监听的端口
@ -68,6 +76,9 @@ public:
explicit MainWidget(QWidget* parent = nullptr);
~MainWidget();
signals:
void openFocusWindowRequested(int itemIndex);
private slots:
// 发送HTTP请求
//void onSomeButtonClicked();
@ -178,6 +189,7 @@ private:
int nextClientId; // 新增的客户端编号
int connectedClientsCount = 0; // 连接客户端的数量
int isRequestSuccessful = 0; // GET请求是否成功
int isBackBoardOrAllBoard = 0;
bool manualSend; // 判断是否是手动触发的发送
bool deviceConnected = false; // 判断是否有设备连接过
bool isSendingAll; // 一键功能测试 状态
@ -217,6 +229,7 @@ private:
QTimer* threadStatusTimer; // 检查线程状态的定时器
QTimer* connectionStatusCheckTimer; // 检查连接状态的定时器
QMap<int, DataHandler*> dataHandlers;
QMap<int, QThread*> clientThreads;
QMap<int, QTimer*> clientReadTimers;
QMap<int, ClientHandler*> clients_1;

View File

@ -23,7 +23,7 @@ int main(int argc, char* argv[]) {
//closeConsole(); // 调用函数关闭控制台窗口
//FreeConsole(); // 关闭控制台窗口
QApplication app(argc, argv);
qDebug() << "Current working directory:" << QDir::currentPath();
QIcon appIcon("./app_icon.ico");
app.setWindowIcon(appIcon);

View File

@ -0,0 +1,6 @@
device ID: 1 - Item 0: ---> NG
device ID: 1 - Item 0: ---> NG
device ID: 1 - Item 0: ---> NG
device ID: 1 - Item 0: ---> NG
device ID: 1 - Item 0: ---> NG
device ID:-1 ---> All 5 items test completed !!!

Binary file not shown.