QT 에서 하드웨어 펌웨어 프로 토 콜 에 대한 테스트 소결 및 몇 개의 QT 가 직면 한 문제 해결
네트워크 udp 통신 을 기반 으로 하 는 펌웨어 프로 토 콜 을 테스트 하기 위해 QT 로 테스트 도 구 를 작성 합 니 다.그 사이 에 몇 가지 문제 에 부 딪 혀 하나씩 해결 되 었 다.여기 있 습 니 다.
1. 네트워크 프로 토 콜 을 기반 으로 하기 때문에 IP 를 가 져 와 UDP 데 이 터 를 편리 하 게 보 내 고 받 아야 합 니 다.다만 가상 랜 카드 등 으로 IP 를 선별 해 야 한다.
QHostAddress addr;
QList list = QNetworkInterface::allAddresses();
foreach (addr, list)
{
if(addr.protocol() == QAbstractSocket::IPv4Protocol){
if (addr.toString().contains("192.168")){
address = QHostAddress(addr.toString());
}
}
}
명령 을 보 낼 때 방송 으로 보 내 면 어떤 카드 로 방송 을 할 지 고려 해 야 한다.그래서 ip 을 먼저 연결 해 야 합 니 다.
udpCMDSocket = new QUdpSocket(this);
udpCMDSocket->bind(QHostAddress(ip));
udpCMDSocket->writeDatagram(cmd.toLocal8Bit(), HubAddr, port);
2. 홈 UI 에서 while 순환 과 같은 높 은 점용 작업 이 임시로 필요 할 때 Qapplication:: processEvents () 를 사용 하여 인터페이스 에 있 는 처리 할 이벤트 에 응답 할 수 있 습 니 다.
while (!binFile.atEnd() {
QByteArray byte = binFile.read(len);
。。。
sendCMD2Port(cmd, HubAddr, port);
Sleep(interval);
QApplication::processEvents();
}
3. 파일 을 열 고 경로 가 있 으 면 기 존 경 로 를 표시 합 니 다.
QString tmpBinfile;
if (BinFilePath.size() == 0)
tmpBinfile = QFileDialog::getOpenFileName(this, tr("Open Bin File"), ".", tr("Bin File(*.bin)"));
else
tmpBinfile = QFileDialog::getOpenFileName(this, tr("Open Bin File"), BinFilePath, tr("Bin File(*.bin)"));
4. 파일 읽 기, QListWidget 생 성, 정렬
bool CaseInsSort(const QString &info1, const QString &info2)
{
return info1.toLower() < info2.toLower();
}
void loadCases()
{
QFile file(filename);
if (file.open(QFile::ReadWrite|QIODevice::Text)){
QTextStream data(&file);
QStringList fonts;
QString line1;
QString line2;
while (!data.atEnd()){
line1 = data.readLine();
line2 = data.readLine();
fonts<addItems(fonts);// listwidget
file.close();
}
}
5. QListWidgetItem 이름 변경
void renameCase()
{
QListWidgetItem *caseItem = caseList->currentItem();
if (caseItem){
caseList->openPersistentEditor(caseItem);
}
}
6. UDP 명령 발송
void sendCMD2Port(QString cmd, QHostAddress HubAddr, int port)
{
udpCMDSocket = new QUdpSocket(this);
udpCMDSocket->writeDatagram(cmd.toLocal8Bit(), HubAddr, port);
udpCMDSocket->close();
}
7. 감청 스 레 드 는 주 스 레 드 에 독립 되 어 있 으 며 감청 데이터 처 리 를 모두 run 에 포함 합 니 다.
void listenPortThread::run()
{
QUdpSocket udpListenSocket;
bool result = udpListenSocket.bind(address, port,QUdpSocket::ShareAddress);//
if(!result)// ,
{
udpListenSocket.close();
stop();
return;
}
islisten = true;
m_bStop = false;
while(!m_bStop)
{
QByteArray array;
QHostAddress address;
quint16 port;
if (islisten){
while (udpListenSocket.hasPendingDatagrams()) {
array.resize(udpListenSocket.pendingDatagramSize());//
udpListenSocket.readDatagram(array.data(),array.size(),&address,&port); //
QString str = array;
。。。
8. 1 차 타이머 로 제어 하여 시한 내 에 답장 을 받 았 는 지 판단 한다.시간 이 되면 timeout 함수 에서 판단 합 니 다.
QTimer::singleShot(1500,this,SLOT(timeout()));
sendCMD2Port(cmd, HubAddr, port);
9. 받 은 제 이 슨 의 답장 을 분석 하고 키 워드 를 통 해 결 과 를 조회 합 니 다.
bool listenPortThread::parseJson(QByteArray array, QString *sendID, QString *result, QString key){
QJsonParseError jsonError;
QJsonDocument doucment = QJsonDocument::fromJson(array, &jsonError); // JSON
if (!doucment.isNull() && (jsonError.error == QJsonParseError::NoError)) { //
if (doucment.isObject()) { // JSON
QJsonObject object = doucment.object(); //
if (!key.isEmpty() && object.contains(key)){
QJsonValue Jvalue = object.value(key);
if (Jvalue.isString()) {
QString strvalue = Jvalue.toString();
*result = strvalue;
}
}
10. 돌아 오 는 json 데 이 터 는 base 64 데 이 터 를 포함 하여 디 코딩 하고 float 로 복원 합 니 다.
QJsonValue Jdata = object1.value("data");
if (Jdata.isString()) {
QString strdata = Jdata.toString();
QByteArray Hex = QByteArray::fromBase64(strdata.toLatin1()).toHex();
QString calidata = "";
for (int i=0; i<12; i++){
QString str =Hex.mid(i*8+6,2)+Hex.mid(i*8+4,2)+Hex.mid(i*8+2,2)+Hex.mid(i*8,2); //
int iHex = str.toUInt(0,16);
float fHex = *(float*)&iHex ;
calidata += QString("%1, ").arg(fHex);
}
*result = calidata;
}
11. pro 파일 에서 VERSION 을 통 해 APP 버 전 번 호 를 설정 하고 프로그램 에서 APP 버 전 번 호 를 가 져 옵 니 다.
쓰다
In the YourApp.pro:
VERSION = 0.0.0.1
DEFINES += APP_VERSION=\\\"$$VERSION\\\"
In the main.cpp:
#include
QCoreApplication::setApplicationVersion(QString(APP_VERSION));
Wherever else in your sources, e.g. in the imaginary controller.cpp:
#include
QString yourAppVersion = QCoreApplication::applicationVersion();
12. 릴 리 스 버 전 프로그램 을 발표 하고 QT 에 필요 한 동적 라 이브 러 리 를 자동 으로 압축 합 니 다.
쓰다
Qt 공식 개발 환경 은 기본적으로 동적 링크 라 이브 러 리 방식 을 사용 합 니 다. 생 성 된 실행 가능 한 프로그램 을 발표 할 때 우 리 는 많은 동적 라 이브 러 리 를 복사 해 야 합 니 다. 만약 에 동적 라 이브 러 리 를 복사 하면 이것저것 잃 어 버 려 서 다른 컴퓨터 에서 프로그램 이 정상적으로 작 동 하지 못 할 수도 있 습 니 다.따라서 Qt 공식 개발 환경 에서 개발 자 들 이 대부분의 의존 라 이브 러 리 를 자동 으로 복사 할 수 있 도록 배치 도 구 를 가 져 왔 습 니 다.
Windows 개발 환경 에서 windeployqt 도구 (Qt 의 bin 디 렉 터 리 를 PATH 환경 에 추가 했다 면 명령 행 에서 windeployqt 호출 을 직접 사용 할 수 있 습 니 다.)우선 프로젝트 의 release 파일 에 있 는 실행 가능 한 파일 을 새 폴 더 에 복사 합 니 다. 예 를 들 어 procject. exe 는 Qt 자체 적 으로 필요 한 dll 파일 을 만 드 는 프로그램 windeployqt 로 필요 한 동적 라 이브 러 리 를 이 폴 더 에 복사 하고 명령 행 을 열 어 windeployqtproject. exe 를 입력 합 니 다. 이때 대부분의 dll 파일 은 자동 으로 복사 되 었 습 니 다.그러나 프로젝트 에 OpenCV, Chartdir 51 등 다른 SDK 를 사용 했다 면 필요 한 dll 을 수 동 으로 복사 해 야 합 니 다. 어떤 소프트웨어 가 더 필요 한 지 모 르 면 Dependency Walker 로 어떤 dll 파일 이 부족 한 지 확인 할 수 있 습 니 다.
메모: 발 표 된 응용 프로그램 이 Qt Quick Application 응용 프로그램 이 라면 명령 행 에 QML 설치 디 렉 터 리 를 추가 해 야 합 니 다.명령 의 D: \ \ Qt \ \ Qt 5.5.1 \ \ qml 는 qml 설치 디 렉 터 리 입 니 다. qml 설치 디 렉 터 리 로 바 꿔 주세요!!!!
windeployqt hello.exe --qmldir D:\Qt\Qt5.5.1\qml
그 다음 에 높 은 친 구 는 Enigma VirtualBox 소프트웨어 가상 화 도구 로 여러 개의 파일 을 응용 프로그램의 메 인 파일 에 밀봉 하여 단일 실행 파일 로 만 드 는 녹색 소프트웨어 를 만 들 수 있다.
13. 다 국어 버 전 만 들 기, QT linguist 로 언어 팩 만 들 기
쓰다
1. pro 파일 에 TRANSLATIONS + = filename 추가CN.ts
2. 도구 -- > 외부 -- > linguist -- > 업데이트 로 ts 파일 을 생 성 합 니 다.그러나 직접 사용 하면 qt 가 잘못 보고 할 수 있 습 니 다.VS 를 찾 을 환경 이 없어 서 요.그래서.
a. Create a translate.bat with the following single-line content:
"%programfiles(x86)%\Microsoft Visual Studio\2017\Community\VC\Auxiliary\Build\vcvars64.bat" & lupdate.exe %1
and put it under %{CurrentProject:QT_INSTALL_BINS} (in my case C:\Qt\Qt5.9.1\5.9.1\msvc2017_64\bin). Make sure that the translate.bat contains the correct path to vcvars64.bat on your machine. You may as well put another version of vcvars if you need.
b. In Qt Creator select Tools/Options/Environment/External Tools and then Add Tool under Linguist category. Name it something like Create/Update TS files. Setup the fields for this entry as follows:
Executable: %{CurrentProject:QT_INSTALL_BINS}\translate.bat,
Arguments: %{CurrentProject:FilePath},
Working directory: %{CurrentProject:QT_INSTALL_BINS},
as shown here: External Tools, then apply the changes and close the Options window.
c. Go to Tools/External/Linguist, select Create/Update TS files and now it should do the job as usual.
3. linguist 에서 ts 파일 을 편집 하고 언어 번역 을 추가 합 니 다.
4. linguist 에서 직접 발표 하거나 qt 의 도구 -- > 외부 -- > linguist -- > 로 발표 하여 ts 파일 로 qm 파일 을 생 성 합 니 다.
5. 메 인 프로그램 에서
QApplication app(argc, argv);
QTranslator translator;
bool ok=translator.load(":/qm/filename_CN.qm");
app.installTranslator(&translator);
14. qt 전역 매크로 변수
쓰다
pro 에 다음 매크로 정의 코드 를 추가 합 니 다:
DEFINES += HELLO=\\\"$$PWD/\\\"
DEFINES += SUCCESS=\\\"string\\\"
. cpp 에서 테스트 코드 는 다음 과 같 습 니 다.
#ifdef HELLO
qDebug()< #else
qDebug()< #endif
이 내용에 흥미가 있습니까?
현재 기사가 여러분의 문제를 해결하지 못하는 경우 AI 엔진은 머신러닝 분석(스마트 모델이 방금 만들어져 부정확한 경우가 있을 수 있음)을 통해 가장 유사한 기사를 추천합니다:
Qt How to use connect between incompatible signal and slotIn this I want to call a function, that function will receive a point . But this function should be invoked by a timer's...
텍스트를 자유롭게 공유하거나 복사할 수 있습니다.하지만 이 문서의 URL은 참조 URL로 남겨 두십시오.
CC BY-SA 2.5, CC BY-SA 3.0 및 CC BY-SA 4.0에 따라 라이센스가 부여됩니다.