How to implement receive buffer
-
Hi all,
I am working with serial port. Device that is connected to my pc is sending data in idle state. That data is equal to 0x63.
When I press a start button on that device new frame is generated and I can receive it in my Qt app.
Frame starts with 0x01 0x01 0xFF and it is transmitted every few milliseconds.What is the best way to handle this data. First I need to detect this start frame and from that position I need to read few more bytes and send to GUI.
regards
-
And what is the problem? You already wrote:
First I need to detect this start frame and from that position I need to read few more bytes and send to GUI.
and that is exactly what you have to do. you can either
peek()
intoQSerialPorts
internal buffer, orreadAll()
and store the results in your own buffer.Just note, that the message comes in in parts and you may need multiple
readyReadSignals
until a complete message is arrived. And of course, you need to dismiss any incomplete message before the start sequence.Regards
-
@zgembo have you check the source code of any of the Qt serial port examples? like serial terminal for instance
-
@pablo-j-rogina Yes I have, but I am having difficulties in detecting start frame 0x01;0x01;0xFF
I have tried to use QByteArrayMatcher with QByteArray to detect start frame pattern but it is a little bit messy.
-
@zgembo said in How to implement receive buffer:
I have tried to use QByteArrayMatcher with QByteArray
What's wrong with QByteArray::indexOf() ?
-
Hi @zgembo,
Here is a (absolutely untested, not even compiled) code snippet that could show you the direction:
static QByteArray nextFrame(QByteArray &buffer) { const QByteArray startOfFrame("\x01\0x01\xFF"); // SOF enum { FrameSize = 10 }; const int pos = buffer.indexIn(startOfFrame); if (pos < 0) return QByteArray(); // delete everything before SOF buffer.remove(0, pos); if (buffer.size() < FrameSize) // frame is not complete return; // extract next frame from buffer const QByteArray newFrame = buffer.left(0, FrameSize); buffer.remove(0, FrameSize); return newFrame; } // connect this slot to the QSerialPort::readRead signal void serialReadyRead() { static QByteArray buffer; buffer.append(m_serial.readAll()); QByteArray frame = nextFrame(buffer); while (!frame.isEmpty) { qDebug() << frame.toHex(); frame = nextFrame(buffer); } }
I hope you get the idea.
Regards
-
@aha_1980 Thank you for your code snippet. I know that you did not even try to compile this code but I have some questions.
I do not understand nextFrame function completely. You read a frame and then you try to detect position of the SOF block with indexOf function.
I do not follow you after this part. If the buffer size is less than a frame size you return from the function, but what do you do if it is not? -
When an empty QByteArray is returned, the loop in serialReadyRead() is stopped.