1.QtSerialport 是我自己定义的串口操作的类,里面的成员有QSerialPort *serialport;
在主程序里,我把串口操作又放到了一个线程里
serialPort = new QtSerialport();
serialPortThread = new QThread();
serialPort->moveToThread(serialPortThread); //移动到线程里
connect(serialPort,SIGNAL(setBrightnessResult(bool)),this,SLOT(OnSetBrightnessResult(bool))); //主程序通过发信号触发操作
connect(this,SIGNAL(setBrightness(int)),serialPort,SLOT(OnSetScreenBrightness(int)));//通过信号,串口设置屏的亮度操作
connect(serialPort,SIGNAL(destroyed()),serialPortThread,SLOT(quit()));//串口操作类用deleterLater()销毁后,触发线程退出
connect(serialPortThread, SIGNAL(finished()), serialPortThread, SLOT(deleteLater()));//线程退出,触发线程对象销毁
serialPortThread->start();//开启线程
串口操作类Init函数里有new的操作,但这个函数不能在主程序里调用,而是要放在线程里,不然会报错
QObject: Cannot create children for a parent that is in a different thread.
(Parent is QSerialPort(0x4a6f9c0), parent's thread is QThread(0x178e950), current thread is QThread(0x4a89e70)
,好像没影响
我放在了OnSetScreenBrightness槽函数里调用
void QtSerialport::Init(QString name,int bitrate,int databits,int parity,int stopbits)
{
serialport = new QSerialPort();
connect(serialport,SIGNAL(readyRead()),this,SLOT(OnReadyRead()));//有数据时,会触发读数据,但可能读不全
serialport->setPortName(name);
}
2.QSerialPort串口读数据可能一次读不全,有数据时,要用校验如异或校验,来确保读的完整,不全就保存数据退出,下次
再读,
char getOneXor(QByteArray buf)//异或校验
{
char tmp = buf[0];
for(int i = 0; i < buf.count(); i++)
{
tmp = tmp ^ buf[i+1];
}
return tmp;
}
void QtSerialport::OnReadyRead()
{
usleep(50*1000);//等50毫秒再读
QByteArray buf = serialport->readAll();
tmpBuf = tmpBuf.append(buf);//保存数据
applog::LOGGER->Log(applog::kLogInfo, "QtSerialport::OnReadyRead tmpBuf= %s", tmpBuf.toHex().constData());
QByteArray tmp = tmpBuf.left(tmpBuf.count() -1);
char lastByte = tmpBuf.at(tmpBuf.count() -1);
if(lastByte != getOneXor(tmp))//异或校验
{
applog::LOGGER->Log(applog::kLogInfo, "QtSerialport::OnReadyRead buffer= %s,but not correct", tmpBuf.toHex().constData());
return;
}