QSerialPort::readLine 在 MS Windows 上无法按预期工作
QSerialPort::readLine doesn't work as expected on MS Windows
我正在尝试通过USB串行电缆将微控制器与台式电脑连接。我的台式电脑操作系统是Windows 8.1,USB串行电缆是TTL-232R-3V3。(FTDI)(Qt版本:5.2.0 beta1,Qt创建者版本:3.0,编译器:MSVC2012)
现在我正在尝试读/写环回测试,这就是为什么USB串行电缆的RX/TX引脚相互连接的原因。
这是我的密码。
#include <QtCore/QCoreApplication>
#include <QtSerialPort/QSerialPort>
#include <QtSerialPort/QSerialPortInfo>
#include <QtCore/QDebug>
#define PORT_NAME "COM3"
#define BAUDRATE 19600
#define TIMEOUT_MS 1000
QT_USE_NAMESPACE
int main(int argc, char *argv[])
{
QCoreApplication a(argc, argv);
QSerialPort pSerial(PORT_NAME);
const char strMsg[] = "#1:Send data line n #2:Send data linen #3:Send data line endn";
char strBuf[256];
qint64 nByte;
if(pSerial.open(QIODevice::ReadWrite)){
pSerial.setBaudRate(BAUDRATE);
qDebug() << "OPEN PASS";
pSerial.write(strMsg);
pSerial.flush();
if(pSerial.waitForBytesWritten(TIMEOUT_MS)){
qDebug() << "WRITE PASS";
}
pSerial.waitForReadyRead(TIMEOUT_MS);
while(true){
if( pSerial.canReadLine()){
qDebug() << "CAN READ LINE";
nByte = pSerial.readLine(strBuf,sizeof(strBuf));
qDebug() << "Length: " << nByte;
qDebug() << "Read data: " << strBuf;
}
}
pSerial.close();
} else {
qDebug() << "OPEN FAILn";
}
return a.exec();
}
当程序开始运行时,结果与我预期的不同。只能接收发送数据的第一行。因此,打印"读取数据:#1发送数据行"在控制台上。但发送的其余数据将永远不会被接收。有人知道为什么吗?
如有任何帮助,我们将不胜感激。提前谢谢。
编辑:我根据Papp的评论修改了代码。然后它像我预期的那样工作。已收到所有发送的消息。
这是否意味着我误解了readLine()或canReadLine()的用法?
// while(true){
// if( pSerial.canReadLine()){
// qDebug() << "CAN READ LINE";
// nByte = pSerial.readLine(strBuf,sizeof(strBuf));
// qDebug() << "Length: " << nByte;
// qDebug() << "Read data: " << strBuf;
// }
// }
pSerial.waitForReadyRead(TIMEOUT_MS);
QByteArray readData = pSerial.readAll();
while (pSerial.waitForReadyRead(TIMEOUT_MS)) {
readData.append(pSerial.readAll());
}
qDebug() << "Read data: " << readData;
第二次编辑:以下代码也适用于我。
while(true){
if( pSerial.waitForReadyRead(TIMEOUT_MS) && pSerial.canReadLine()){ // I revised this line
qDebug() << "CAN READ LINE";
nByte = pSerial.readLine(strBuf,sizeof(strBuf));
qDebug() << "Length: " << nByte;
qDebug() << "Read data: " << strBuf;
qDebug() << "Error Message: " << pSerial.errorString();
}
}
这是因为你需要在这样的循环中阅读:
QByteArray readData = serialPort.readAll();
while (serialPort.waitForReadyRead(5000))
readData.append(serialPort.readAll());
请参阅creadersync
示例,了解我在5.2中添加的详细信息。您也可以检查creaderasync
示例中的非阻塞操作。
公平地说,我们还没有测试过readLine,但它在Unix上对我有效,在Windows上对其他人也有效。
您所犯的错误是期望在waitForReadyRead
返回时接收所有发送的数据。当waitForReadyRead
完成时,您所能保证的只是一些数据可供读取。它可能只有一个字符,而不一定是一整行。
上一次修改后的循环是几乎正确的方法。您应该将行的读数嵌套在一个单独的循环中。以下代码是应该如何完成的,并且与QIODevice
:的语义一致
while (pSerial.waitForReadyRead(TIMEOUT_MS)) {
while (pSerial.canReadLine()) {
qDebug() << "NEW LINE";
QByteArray line = pSerial.readLine();
qDebug() << "Length: " << line.size();
qDebug() << "Read data: " << line;
qDebug() << "Error Message: " << pSerial.errorString();
}
}
qDebug << "TIMED OUT";
请注意,这些代码都不应该在GUI线程中运行。理想情况下,您应该将它移动到一个QObject,使用QIODevice
(因此也是QSerialPort
)发出的信号,并将该对象移动到单独的线程。
GUI线程有时会阻塞很长一段时间,通常不希望它干扰设备通信的及时性。类似地,您不希望设备超时阻塞GUI线程。两者都同样糟糕,是糟糕用户体验的常见来源。Qt让多线程变得非常容易——为了用户的利益而利用它,并正确地执行它。
在Linux上,我必须这样做才能接收以'n'
结尾的ASCII文本
QByteArray readData = pSerial.readAll();
while (readData[readData.length() - 1] != 'n') {
pSerial.waitForReadyRead(5000);
readData.append(pSerial.readAll());
}
QString result(readData);
QSerialPort::readLine()
对我也不起作用
- QSqlquery prepare()和bindvalue()不工作
- 导入库可以跨dll版本工作吗
- 以螺旋方式打印矩阵的程序.(工作不好)
- 对象指针在c++中是如何工作的
- 为什么在Windows上的VS 2019和Clang 9中"size_t"在没有标题的情况下工作
- VSOMEIP-2个设备之间的通信(TCP/UDP)不工作
- 为字符串中每 N 个字符插入空格的函数没有按照我认为的方式工作?
- C++为线程工作动态地分割例程
- 为什么我的 std::ref 无法按预期工作?
- 布尔比较运算符是如何在C++中工作的
- SampleConsensusPrerejective(ext.RANSAC)是如何真正工作的
- 不确定要在我的main中放入什么才能使我的代码正常工作
- 为什么std::condition_variable notify_all的工作速度比notify_one快(对于随机请
- <<操作员在下面的行中工作
- 有人能解释一下为什么下界是这样工作的吗C++的
- ExtractIconEx:可以工作,但偶尔会崩溃
- C++中的memset函数工作不正常
- 当我在第一个循环中使用"auto"时,它工作正常,但是使用"int"它会给出错误,为什么?
- 链表c++插入,所有情况都已检查,但没有任何工作
- QSerialPort::readLine 在 MS Windows 上无法按预期工作