SerialPortReader output in a text file
-
@Denta1000 There is an example in the documentation (https://doc.qt.io/qt-5/qtextstream.html):
QFile data("output.txt"); if (data.open(QFile::WriteOnly | QFile::Truncate)) { QTextStream out(&data); out << "Result: " << qSetFieldWidth(10) << left << 3.14 << 2.7; // writes "Result: 3.14 2.7 " }
So, in constructor open the file (make the QFile instance class member) and pass the pointer to it as parameter to QTextStream.
-
@jsulm you can see, the OP actually does that, in the initializer list
@Denta1000 QTesxtStream has a
setDevice()
function, use that to set the device after you open it, see if that helps 🤷♂️ -
@jsulm said in SerialPortReader output in a text file:
@J-Hilk Ah, you're right, need more coffee :-)
😜
I'm out of coffee, thank god, today is a short work day!
-
@jsulm @J-Hilk thanks for your help,
I tried using setdevice() but it changed nothing.
So far, I constructed a second QTextStream linked to the same file, before file.open() to verify my hypothesis :
*QTextStream out(&file); //constructed before file opening if(!file.open(QIODevice::WriteOnly | QIODevice::Append)){ //test file opening qDebug() << "can't open fichier.txt \n"; } qDebug() << file.fileName() << "opened"; //test opening success qDebug() << "out associated Device : " << out.device(); //First QTextStream infos qDebug() << "out status : " << out.status(); out << "First test"; m_standardOutput.setDevice(out.device()); // setdevice() after file opening qDebug() << "m_standard associated device : " << m_standardOutput.device(); qDebug ()<< "m_standard status : " << m_standardOutput.status(); m_standardOutput << "second test \n";*
Here QTextStream out is constructed before file.open() , and yet it does write into file.
Whereas, m_standardOutput.setdevice() is used after the file opening and m_standarOutput still doesn't write into the file.qDebug output shows that the two QTextStreams are similar :
According to QTextStream:: , status 0 means "The text stream is operating normally."
-
I tried setting m_standardOutput as a QTextStream pointer :
QTextStream out(&file); m_standardOutput = &out;
and then I call :
*m_StandardOutput << "Second test";
It does write into the file when used in the SerialPortReader constructor.
So I called "*m_standardOutput <<" in the SerialPortReader::handleReadyRead().void SerialPortReader::handleReadyRead() { //qDebug() << "device inside handleReadyRead : " << m_standardOutput->device(); *m_standardOutput << "deuxieme test out \n" ; //second try writing into the file , meant to write serialport content in the futur m_readData = m_serialPort->readAll(); // datas receiving verification qDebug () << m_readData; //m_serialPort->flush(); m_timer.start(5000); }
But as soon as the program encounters a command involving m_standardOutput inside the HandleReadyRead() part, it blocks...
-
Hi,
@Denta1000 said in SerialPortReader output in a text file:
QTextStream out(&file);
m_standardOutput = &out;You realize that you are taking the address of a local and thus temporary object that will be destroyed at the end of the method it was created in ?
-
Yes it is destroyed since it's variable that is local to the constructor.
-
Well , in fact it sounds logical...
Then I should juste have to construct the link beetween m_standardOutput and file since they are both part of the SerialPortReader object
But m_standardOutput doesn't write anything in the file, even during the constructor part.SerialPortReader::SerialPortReader(QSerialPort* serialPort,QObject* parent) : QObject(parent), m_serialPort(serialPort), file("file.txt"),m_standardOutput(&file) //construction of FILE and linking with QTextStream m_standardOutput { if(!file.open(QIODevice::WriteOnly | QIODevice::Append)){ //test file opening qDebug() << "can't open fichier.txt \n"; } //m_standardOutput.setDevice(&file); qDebug() << file.fileName() << "opened"; qDebug() << "file permissions :" << file.permissions() << "\n"; m_standardOutput << "test 2"; qDebug() << "m_standard associated device : " << m_standardOutput.device(); qDebug ()<< "m_standard status : " << m_standardOutput.status();
This part of the code should be sufficient to write the "test 2" text in the file but it doesn't, even though qDebug shows that the link is correct...
-
@Denta1000 said in SerialPortReader output in a text file:
should be sufficient to write the "test 2" text in the file but it doesn't
I don't really understand why you're saying anything is wrong. It reports status OK, what is it that makes you say something has gone wrong? I wouldn't expect to see anything in the file till you've closed or at least flushed it, if that's what you're looking at.
-
@JonB thanks a lot, it was all because I wouldn't close the file properly. But I thought I read that file.close flushes the file. Doesn't "flush" means the file's content get destroyed ?
Thanks a lot, even if I feel a bit ashamed now ... ^^'
How do I make the post Resolved ?
-
Hi
Flushing a file means making sure all buffers are saved to disk.
Often file IO has buffers and flushing means to get all data on the disk.Often closing the file will also make it flush first.
- How do I make the post Resolved ?
In the first post. There is Topic Tool button that make flag as solved.
-
@Denta1000
When you send bytes to aQTextStream
they are in memory in a buffer, not yet in disk file. You can callQTextStream::flush()
toFlushes any buffered data waiting to be written to the device.
Flushing here does not mean discarding pending-written data, it only means flushing it from memory to disk.
I believe that rather than sending the
"\n"
which you do,endl
would flush:m_standardOutput << "second test out" << endl;
You should call
QFile::close()
to close the backing file. There may be buffering going on inQFile
as well as inQTextStream
, I don't know. There is aQIODevice::Unbuffered
flag which can be passed when openingQFile
. Nor do I know whether you need to callQTextStream::flush()
before closing the file.You would have to play to find out how
QTextStream
andQFile
interact for all this buffering/flushing!