2022-08-25 18:43:03 +08:00
# include "mainwin.h"
2023-08-21 11:21:00 +08:00
# include "gutil/qjson.h"
2023-03-20 11:30:19 +08:00
# include "pcaprethread.h"
2023-09-01 16:17:33 +08:00
# include "pcap.h"
2022-08-25 18:43:03 +08:00
# include "fast.h"
# include "expertwin.h"
# include "brightwin.h"
2023-06-13 18:00:19 +08:00
# include "testwin.h"
2022-10-12 18:17:10 +08:00
# include "videowin.h"
2022-08-30 23:07:13 +08:00
# include <QLabel>
2022-08-25 18:43:03 +08:00
# include <QPushButton>
# include <QToolButton>
# include <QComboBox>
# include <QMouseEvent>
# include <QPainter>
# include <QPainterPath>
# include <QTimer>
2022-10-12 18:17:10 +08:00
# include <QMessageBox>
2022-12-16 15:08:53 +08:00
# include "globalfunc.h"
# include "basewin.h"
# include <QSettings>
# include <QDir>
# include <QApplication>
2023-05-27 17:43:57 +08:00
# include <QtEndian>
2023-07-28 14:48:41 +08:00
# include <QStandardPaths>
2023-08-21 11:21:00 +08:00
# include <QNetworkDatagram>
# include <QNetworkInterface>
2022-08-30 23:07:13 +08:00
2022-08-25 18:43:03 +08:00
class ImgBtn : public QToolButton {
public :
2022-09-06 23:40:02 +08:00
ImgBtn ( ) {
setStyleSheet ( " QToolButton{border: none; padding-top: 4px;} " ) ;
2022-08-25 18:43:03 +08:00
}
2022-09-06 23:40:02 +08:00
bool isEnter { false } ;
2022-08-25 18:43:03 +08:00
protected :
2022-09-06 23:40:02 +08:00
void resizeEvent ( QResizeEvent * event ) override {
QToolButton : : resizeEvent ( event ) ;
if ( isEnter ) setIconSize ( QSize ( width ( ) , width ( ) ) ) ;
else setIconSize ( QSize ( width ( ) - 8 , width ( ) - 8 ) ) ;
}
void enterEvent ( QEvent * event ) override {
QToolButton : : enterEvent ( event ) ;
2022-08-25 18:43:03 +08:00
setStyleSheet ( " QToolButton{border: none;} " ) ;
setIconSize ( QSize ( width ( ) , width ( ) ) ) ;
}
2022-09-06 23:40:02 +08:00
void leaveEvent ( QEvent * event ) override {
QToolButton : : leaveEvent ( event ) ;
2022-08-25 18:43:03 +08:00
setIconSize ( QSize ( width ( ) - 8 , width ( ) - 8 ) ) ;
setStyleSheet ( " QToolButton{border: none; padding-top: 4px;} " ) ;
}
} ;
inline QLabel * newImgLabel ( QPixmap pixmap ) {
QLabel * lb = new QLabel ( ) ;
lb - > setPixmap ( pixmap ) ;
return lb ;
}
inline QLabel * newSubLabel ( QString txt ) {
QLabel * lb = new QLabel ( txt ) ;
lb - > setAlignment ( Qt : : AlignCenter ) ;
return lb ;
}
2022-09-06 23:40:02 +08:00
ImgBtn * addImg ( QHBoxLayout * parent , const QIcon & icon , const QString & text ) {
auto imgBtn = new ImgBtn ( ) ;
2023-05-27 17:43:57 +08:00
auto ft = imgBtn - > font ( ) ;
ft . setPixelSize ( 14 ) ;
imgBtn - > setFont ( ft ) ;
2022-09-06 23:40:02 +08:00
imgBtn - > setIcon ( icon ) ;
imgBtn - > setText ( text ) ;
2022-08-25 18:43:03 +08:00
imgBtn - > setFixedSize ( 76 , 100 ) ;
imgBtn - > setToolButtonStyle ( Qt : : ToolButtonTextUnderIcon ) ;
parent - > addWidget ( imgBtn ) ;
2022-09-06 23:40:02 +08:00
return imgBtn ;
2022-08-25 18:43:03 +08:00
}
MainWin : : MainWin ( ) {
2022-12-16 15:08:53 +08:00
setWindowTitle ( " LedSet Express " ) ;
2023-05-27 17:43:57 +08:00
resize ( 900 , 600 ) ;
auto ft = font ( ) ;
ft . setPixelSize ( 14 ) ;
setFont ( ft ) ;
2022-08-25 18:43:03 +08:00
auto vBox = new QVBoxLayout ( center ) ;
vBox - > setContentsMargins ( 0 , 0 , 0 , 0 ) ;
vBox - > addLayout ( addBtns ( new QHBoxLayout ( ) ) ) ;
QHBoxLayout * imgsBar = new QHBoxLayout ( ) ;
2022-09-06 23:40:02 +08:00
auto btnImg = addImg ( imgsBar , QPixmap ( " :/imgs/fast.png " ) . scaledToWidth ( 128 , Qt : : SmoothTransformation ) , " 快速调屏 " ) ;
2023-06-13 18:00:19 +08:00
connect ( btnImg , & ImgBtn : : clicked , this , [ = ] {
2022-08-25 18:43:03 +08:00
( new Fast ( this ) ) - > show ( ) ;
} ) ;
2022-12-16 15:08:53 +08:00
btnImg = addImg ( imgsBar , QPixmap ( " :/imgs/expert.png " ) . scaledToWidth ( 128 , Qt : : SmoothTransformation ) , tr ( " 专家调屏 " ) ) ;
2023-06-13 18:00:19 +08:00
connect ( btnImg , & ImgBtn : : clicked , this , [ = ] {
2023-09-05 10:02:20 +08:00
auto item = table - > selectedItem ( ) ;
if ( item ) ( new ExpertWin ( this , ( enum_rcvCardType ) item - > data ( " type " ) . toInt ( ) ) ) - > show ( ) ;
else if ( QMessageBox : : question ( this , " Info " , tr ( " 未选择卡, 是否继续? " ) ) = = QMessageBox : : Yes ) ( new ExpertWin ( this , NoCard ) ) - > show ( ) ;
2022-08-25 18:43:03 +08:00
} ) ;
2022-12-16 15:08:53 +08:00
btnImg = addImg ( imgsBar , QPixmap ( " :/imgs/bright.png " ) . scaledToWidth ( 128 , Qt : : SmoothTransformation ) , tr ( " 亮度控制 " ) ) ;
2023-06-13 18:00:19 +08:00
connect ( btnImg , & ImgBtn : : clicked , this , [ = ] {
2022-08-25 18:43:03 +08:00
( new BrightWin ( this ) ) - > show ( ) ;
} ) ;
2022-12-16 15:08:53 +08:00
btnImg = addImg ( imgsBar , QPixmap ( " :/imgs/correct.png " ) . scaledToWidth ( 128 , Qt : : SmoothTransformation ) , tr ( " 相机矫正 " ) ) ;
2023-06-13 18:00:19 +08:00
connect ( btnImg , & ImgBtn : : clicked , this , [ = ] {
2022-08-25 18:43:03 +08:00
} ) ;
2022-12-16 15:08:53 +08:00
btnImg = addImg ( imgsBar , QPixmap ( " :/imgs/monitor.png " ) . scaledToWidth ( 128 , Qt : : SmoothTransformation ) , tr ( " 屏体监控 " ) ) ;
2023-06-13 18:00:19 +08:00
connect ( btnImg , & ImgBtn : : clicked , this , [ = ] {
2022-08-25 18:43:03 +08:00
} ) ;
2022-12-16 15:08:53 +08:00
btnImg = addImg ( imgsBar , QPixmap ( " :/imgs/multi.png " ) . scaledToWidth ( 128 , Qt : : SmoothTransformation ) , tr ( " 多功能卡 " ) ) ;
2023-06-13 18:00:19 +08:00
connect ( btnImg , & ImgBtn : : clicked , this , [ = ] {
2022-08-25 18:43:03 +08:00
//win->move(win->x()-1, win->y());
} ) ;
2023-06-13 18:00:19 +08:00
btnImg = addImg ( imgsBar , QPixmap ( " :/imgs/test.png " ) . scaledToWidth ( 128 , Qt : : SmoothTransformation ) , tr ( " 协议调试 " ) ) ;
connect ( btnImg , & ImgBtn : : clicked , this , [ = ] {
if ( reThd - > status ) return ;
( new TestWin ( this ) ) - > show ( ) ;
2022-08-25 18:43:03 +08:00
} ) ;
2022-12-16 15:08:53 +08:00
btnImg = addImg ( imgsBar , QPixmap ( " :/imgs/idea.png " ) . scaledToWidth ( 128 , Qt : : SmoothTransformation ) , tr ( " 模拟同步 " ) ) ;
2023-06-13 18:00:19 +08:00
connect ( btnImg , & ImgBtn : : clicked , this , [ = ] {
2022-12-16 15:08:53 +08:00
auto ins = VideoWin : : newIns ( net_name , this ) ;
if ( ins ) ins - > show ( ) ;
2022-08-25 18:43:03 +08:00
} ) ;
vBox - > addLayout ( imgsBar ) ;
2022-12-16 15:08:53 +08:00
vBox - > addSpacing ( 9 ) ;
2022-08-25 18:43:03 +08:00
vBox - > addWidget ( new QLabel ( " 硬件信息 " ) ) ;
2023-09-05 10:02:20 +08:00
table = new TreeWidget {
{ " _num_ " , " " , 20 } ,
2023-08-24 16:55:38 +08:00
{ " type " , " 控制系统类型 " } ,
2022-12-16 15:08:53 +08:00
{ " name " , " 名称 " } ,
{ " link " , " 连接方式 " } ,
2023-05-27 17:43:57 +08:00
{ " vcsNum " , " 接收卡数量 " } ,
{ " netPorts " , " 网口统计P1~Pn " } ,
{ " info " , " 其他信息 " , QHeaderView : : Stretch } ,
2022-12-16 15:08:53 +08:00
} ;
2023-05-27 17:43:57 +08:00
table - > setDefs ( ) ;
2023-09-05 10:02:20 +08:00
table - > setSortingEnabled ( true ) ;
table - > sortItems ( " name " ) ;
table - > setStyleSheet ( " TreeWidget::item{height: 26px;} " ) ;
2022-12-16 15:08:53 +08:00
vBox - > addWidget ( table ) ;
2023-08-21 11:21:00 +08:00
auto hBox = new HBox ( vBox ) ;
hBox - > addLabel ( " V " __VER__ " - " __DATE__ ) ;
hBox - > addStretch ( ) ;
2022-08-25 18:43:03 +08:00
2022-12-16 15:08:53 +08:00
auto btnNetSelect = new QPushButton ( " 通讯选择 " ) ;
connect ( btnNetSelect , & QPushButton : : clicked , this , [ this ] {
2023-03-24 18:41:48 +08:00
auto name = getNetDev ( this , net_name , false ) ;
2022-12-16 15:08:53 +08:00
if ( name . isEmpty ( ) ) return ;
//PCAP_OPENFLAG_DATATX_UDP: 2, 它定义了数据传输( 假如是远程抓包) 是否用UDP协议来处理。
//PCAP_OPENFLAG_NOCAPTURE_RPCAP: 4, 它定义了远程探测器是否捕获它自己产生的数据包。
2023-06-13 18:00:19 +08:00
char errbuf [ PCAP_ERRBUF_SIZE ] { 0 } ;
2022-12-16 15:08:53 +08:00
auto pcapR = pcap_open_live ( name . data ( ) , 65536 , PCAP_OPENFLAG_PROMISCUOUS | 4 | 8 | 16 , 50 , errbuf ) ;
if ( pcapR = = 0 ) {
QMessageBox : : critical ( this , " Error " , QString ( tr ( " 打开网卡失败 " ) ) + errbuf ) ;
return ;
}
auto pcapS = pcap_open_live ( name . data ( ) , 65536 , 0 , 50 , errbuf ) ;
if ( pcapS = = 0 ) {
QMessageBox : : critical ( this , " Error " , QString ( tr ( " 打开网卡失败 " ) ) + errbuf ) ;
return ;
}
2023-03-20 11:30:19 +08:00
if ( reThd ) reThd - > status = 2 ;
2022-12-16 15:08:53 +08:00
if ( pcapSend ) pcap_close ( pcapSend ) ;
pcapSend = pcapS ;
2023-03-20 11:30:19 +08:00
reThd = new PcapReThread ( pcapR ) ;
reThd - > start ( ) ;
2023-06-07 19:11:03 +08:00
QSettings ( ) . setValue ( " net_name " , net_name = name ) ;
2022-12-16 15:08:53 +08:00
} ) ;
2023-08-21 11:21:00 +08:00
hBox - > addWidget ( btnNetSelect ) ;
2022-12-16 15:08:53 +08:00
auto btnRefresh = new QPushButton ( tr ( " 刷新 " ) ) ;
2023-03-20 12:11:58 +08:00
connect ( btnRefresh , & QPushButton : : clicked , this , & MainWin : : getCard ) ;
2023-08-21 11:21:00 +08:00
hBox - > addWidget ( btnRefresh ) ;
2022-12-16 15:08:53 +08:00
2023-06-06 12:13:33 +08:00
show ( ) ;
2023-06-07 19:11:03 +08:00
QSettings config ;
2023-07-28 14:48:41 +08:00
gFileHome = config . value ( " FileHome " ) . toString ( ) ;
if ( gFileHome . isEmpty ( ) | | ! QFileInfo ( gFileHome ) . isDir ( ) ) gFileHome = QStandardPaths : : writableLocation ( QStandardPaths : : DocumentsLocation ) ;
2022-12-16 15:08:53 +08:00
auto name = config . value ( " net_name " ) . toByteArray ( ) ;
2023-03-24 18:41:48 +08:00
name = getNetDev ( this , name , true ) ;
2022-12-16 15:08:53 +08:00
if ( ! name . isEmpty ( ) ) {
2023-06-13 18:00:19 +08:00
char errbuf [ PCAP_ERRBUF_SIZE ] { 0 } ;
2023-03-20 11:30:19 +08:00
auto pcapRe = pcap_open_live ( name . data ( ) , 65536 , PCAP_OPENFLAG_PROMISCUOUS | 4 | 8 | 16 , 50 , errbuf ) ;
2022-12-16 15:08:53 +08:00
if ( pcapRe = = 0 ) QMessageBox : : critical ( this , " Error " , QString ( tr ( " 打开网卡失败 " ) ) + errbuf ) ;
else {
pcapSend = pcap_open_live ( name . data ( ) , 65536 , 0 , 50 , errbuf ) ;
if ( pcapSend = = 0 ) QMessageBox : : critical ( this , " Error " , QString ( tr ( " 打开网卡失败 " ) ) + errbuf ) ;
2023-03-20 11:30:19 +08:00
else {
config . setValue ( " net_name " , net_name = name ) ;
reThd = new PcapReThread ( pcapRe ) ;
reThd - > start ( ) ;
}
2022-12-16 15:08:53 +08:00
}
}
2023-08-21 11:21:00 +08:00
connect ( & mUdpSocket , & QUdpSocket : : readyRead , this , [ this ] {
while ( mUdpSocket . hasPendingDatagrams ( ) ) {
auto gram = mUdpSocket . receiveDatagram ( ) ;
auto data = gram . data ( ) ;
if ( data . isEmpty ( ) ) continue ;
auto senderAddress = gram . senderAddress ( ) ;
bool ok = true ;
if ( senderAddress . protocol ( ) = = QUdpSocket : : IPv6Protocol ) senderAddress . setAddress ( senderAddress . toIPv4Address ( & ok ) ) ;
auto addr = ok ? senderAddress . toString ( ) : " " ;
if ( data . startsWith ( " { \" " ) ) {
QString error ;
auto json = JFrom ( gram . data ( ) , & error ) ;
if ( ! error . isEmpty ( ) ) {
qDebug ( ) < < " Json Error: " + error ;
continue ;
}
auto cardId = json [ " cardId " ] . toStr ( ) ;
2023-09-05 10:02:20 +08:00
TreeWidgetItem * item ;
for ( int rr = 0 ; rr < table - > topLevelItemCount ( ) ; rr + + ) if ( ( item = table - > item ( rr ) ) - > text ( " name " ) = = cardId ) {
item - > setText ( " link " , addr ) ;
2023-08-21 11:21:00 +08:00
goto end ;
}
2023-09-05 10:02:20 +08:00
item = new TreeWidgetItem ( table ) ;
item - > setText ( " type " , tr ( " 异步卡 " ) , enum_xixun_async ) ;
item - > setText ( " name " , cardId ) ;
item - > setText ( " link " , addr ) ;
2023-08-21 11:21:00 +08:00
} else {
auto bytes = gram . data ( ) ;
auto packet = ( UDPPacket * ) bytes . data ( ) ;
2023-09-05 10:02:20 +08:00
TreeWidgetItem * item ;
for ( int rr = 0 ; rr < table - > topLevelItemCount ( ) ; rr + + ) if ( ( item = table - > item ( rr ) ) - > text ( " name " ) = = packet - > serialCode ) {
item - > setText ( " link " , addr ) ;
2023-08-21 11:21:00 +08:00
goto end ;
}
2023-09-05 10:02:20 +08:00
item = new TreeWidgetItem ( table ) ;
item - > setText ( " type " , tr ( " 异步卡 " ) , enum_xixun_async ) ;
item - > setText ( " name " , packet - > serialCode ) ;
item - > setText ( " link " , addr ) ;
2023-08-21 11:21:00 +08:00
}
end : ;
}
} ) ;
2023-09-01 16:17:33 +08:00
reThd - > addMultiCallback ( 0x105B14 , [ = ] ( int , const QByteArray data ) {
unsigned short ver = * ( quint16_be * ) ( data . data ( ) + headMap_zrf . protcolFlag ) ;
unsigned char pkgType = * ( quint8 * ) ( data . data ( ) + headMap_zrf . pkgType ) ;
if ( ver ! = 0x105B | | pkgType ! = 0x14 ) return ;
2023-09-01 17:25:53 +08:00
auto strDeviceName = QString ( QLatin1String ( data . data ( ) + headMap_zrf . paramStart + st_zrf_rb_param . deviceName , 9 ) ) ;
2023-09-05 10:02:20 +08:00
TreeWidgetItem * item ;
for ( int i = 0 ; i < table - > topLevelItemCount ( ) ; i + + ) if ( ( item = table - > item ( i ) ) - > text ( " name " ) = = strDeviceName ) goto end ;
item = new TreeWidgetItem ( table ) ;
2023-09-01 17:25:53 +08:00
end :
2023-09-05 10:02:20 +08:00
int virtualVCM = * ( quint8 * ) ( data . data ( ) + headMap_zrf . netPort ) + 1 ;
int rcvIdex = * ( quint8 * ) ( data . data ( ) + headMap_zrf . rcvIndex ) + 1 ;
2023-09-01 17:25:53 +08:00
if ( rcvIdex > maxNetPort_zrf ) maxNetPort_zrf = rcvIdex ;
2023-09-05 10:02:20 +08:00
item - > setText ( " type " , tr ( " PC虚拟卡V1.0 " ) , enum_zrf ) ;
item - > setText ( " name " , strDeviceName ) ;
item - > setText ( " link " , " 千兆网直连 " ) ;
item - > setText ( " vcsNum " , QString : : number ( maxNetPort_zrf ) ) ;
item - > setText ( " netPorts " , " P: " + QString : : number ( virtualVCM ) ) ;
item - > setText ( " info " , " 版本: " + QLatin1String ( data . data ( ) + headMap_zrf . paramStart + st_zrf_rb_param . deviceVer , 8 ) + " [备注:可直接配屏,无需发送卡] " ) ;
if ( table - > selectedItem ( ) = = 0 ) item - > setSelected ( true ) ;
2023-09-01 16:17:33 +08:00
} ) ;
2023-03-20 12:11:58 +08:00
getCard ( ) ;
}
2023-07-28 14:48:41 +08:00
MainWin : : ~ MainWin ( ) {
2023-08-21 11:21:00 +08:00
mUdpSocket . close ( ) ;
2023-07-28 14:48:41 +08:00
QSettings config ;
config . setValue ( " FileHome " , gFileHome ) ;
}
2022-12-16 15:08:53 +08:00
2023-03-20 12:11:58 +08:00
void MainWin : : getCard ( ) {
2023-09-05 10:02:20 +08:00
table - > clear ( ) ;
2023-05-27 17:43:57 +08:00
auto msg = QByteArray : : fromHex ( " 5555 01 0D 0008 FFFFFFFF 0000ABCD A0000000 0000 38CB847E 00000000 0000ABCD CD040446 " ) ;
2023-06-06 12:13:33 +08:00
auto res = sendMsg ( msg , 0x1E0 , 10000 , [ = ] ( int , const QByteArray data ) {
2023-05-27 17:43:57 +08:00
if ( * ( quint32_be * ) ( data . data ( ) + headMap . ptr ) ! = 0xA0000000 ) return ;
2023-09-05 10:02:20 +08:00
auto item = new TreeWidgetItem ( table ) ;
2023-05-27 17:43:57 +08:00
int virtualVCM = * ( quint16_be * ) ( data . data ( ) + headMap . srcAddr ) ;
2023-08-24 16:55:38 +08:00
//modified by alahover -s 20230822
auto ver = * ( byte * ) ( data . data ( ) + headMap . ver ) ;
2023-09-05 10:02:20 +08:00
if ( ver = = 0x01 ) item - > setText ( " type " , tr ( " PC虚拟卡V0.0 " ) , enum_xixun_sync ) ;
else if ( ver = = 0x58 ) item - > setText ( " type " , tr ( " PC虚拟卡V1.0 " ) , enum_zrf ) ;
item - > setText ( " name " , QString : : number ( virtualVCM ) + " (网口) " ) ;
item - > setText ( " link " , " 千兆网直连 " ) ;
item - > setText ( " vcsNum " , QString : : number ( * ( quint32_be * ) ( data . data ( ) + headMap . body ) ) ) ;
item - > setText ( " netPorts " , " P: " + QString : : number ( virtualVCM ) ) ;
item - > setText ( " info " , " 备注: 可直接配屏,无需发送卡 " ) ;
if ( table - > selectedItem ( ) = = 0 ) item - > setSelected ( true ) ;
2023-06-06 12:13:33 +08:00
} ) ;
2023-08-21 11:21:00 +08:00
if ( res ) {
QString err = pcap_geterr ( pcapSend ) ;
if ( ! err . endsWith ( " (2150891551) " ) ) QMessageBox : : critical ( this , " Error " , QString ( tr ( " 发送失败: " ) ) + QString : : fromLocal8Bit ( pcap_geterr ( pcapSend ) ) ) ;
}
2023-08-24 16:55:38 +08:00
//modified by alahover -s 20230822
2023-09-01 17:25:53 +08:00
//查询105B协议类型ZRF版本fpga的接收卡, 0x105B1400 表示是zrf协议类型并且是回读数据包
msg = QByteArray : : fromHex ( " 5555 001122334455 001122334455 105A 13 00 00 00 00 e0 ff ff 00 f2 f2 f2 f2 00 00 00 00 00 00 00 00 00 00 00 00 " ) ;
2023-09-01 16:17:33 +08:00
res = pcap_sendpacket ( pcapSend , ( const u_char * ) msg . data ( ) , msg . size ( ) ) ;
2023-08-24 16:55:38 +08:00
if ( res ) {
QString err = pcap_geterr ( pcapSend ) ;
if ( ! err . endsWith ( " (2150891551) " ) ) QMessageBox : : critical ( this , " Error " , QString ( tr ( " 发送失败: " ) ) + QString : : fromLocal8Bit ( pcap_geterr ( pcapSend ) ) ) ;
}
2023-08-21 11:21:00 +08:00
auto data = JToBytes ( JObj { { " action " , " getInfo " } } ) ;
uchar ccc [ ] { 0x7E , 0x7E , 0x7E , 0x90 , 0x42 , 0x72 , 0x6F , 0x61 , 0x64 , 0x63 , 0x61 , 0x73 , 0x74 , 0x21 ,
0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0x1C , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0x9F } ;
if ( mUdpSocket . writeDatagram ( data , QHostAddress ( " 255.255.255.255 " ) , 22222 ) ! = data . length ( ) ) qDebug ( ) < < " getInfo write to 255.255.255.255 failed " ;
if ( mUdpSocket . writeDatagram ( ( char * ) ccc , sizeof ( ccc ) , QHostAddress ( " 255.255.255.255 " ) , 31296 ) ! = sizeof ( ccc ) ) qDebug ( ) < < " getInfo write to 255.255.255.255 failed " ;
auto networkinterfaces = QNetworkInterface : : allInterfaces ( ) ;
foreach ( auto face , networkinterfaces ) {
auto flags = face . flags ( ) ;
bool can = ( flags & QNetworkInterface : : IsRunning ) & & ( flags & QNetworkInterface : : CanBroadcast ) & & ! ( flags & QNetworkInterface : : IsLoopBack ) ;
if ( ! can ) continue ;
auto addrEntries = face . addressEntries ( ) ;
foreach ( QNetworkAddressEntry addrEntry , addrEntries ) {
auto ip = addrEntry . ip ( ) ;
if ( ip . protocol ( ) ! = QAbstractSocket : : IPv4Protocol ) continue ;
auto broadcast = addrEntry . broadcast ( ) ;
if ( mUdpSocket . writeDatagram ( data , broadcast , 22222 ) ! = data . length ( ) ) qDebug ( ) < < " getInfo write failed. " < < ip . toString ( ) < < " -> " < < broadcast . toString ( ) ;
}
}
2022-12-16 15:08:53 +08:00
}