Write text file in Qthread
-
Hello, thanks to Qt Forum I currently finish my GUI work. but the professor asked me to add a writing function so that I can plot the time-location graph.
the purpose of the writing function is to write the current location of the motor and time in the textfile repeatly.
My GUI displays the location in the QTextBrowser using QThread. Here are my codesPosition.h
class Position : public QObject { Q_OBJECT; public: Position(); ~Position(); void startThread1(MDCE* pcom, QTextBrowser* browser); void measureLocation1(MDCE* pcom); void stopMeasure(); private: QThread* thread1; QElapsedTimer* timer; signals: void location_changed1(QString location); };
Position.cpp
//Start the thread that displays built-in position value of motor void Position::startThread1(MDCE* pcom, QTextBrowser* browser) { connect(this, &Position::location_changed1, browser, &QTextBrowser::setText); thread1 = QThread::create(std::bind(&Position::measureLocation1,this, pcom)); thread1->start(); } void Position::measureLocation1(MDCE* pcom) { double location; char record[] = "X_enc_pos"; // From now, this is my modification of code QFile file("C:/Users/Sonic/experiment.txt"); if (!file.open(QFile::WriteOnly | QFile::Text)) { return; } QTextStream out(&file); timer->start(); // while (1) { GetVarN(record, &location, 0, pcom); //this function returns double value to location. out << timer->elapsed() << " " << location<<"\n"; // write time and location value to experiment.txt emit location_changed1(QString::number(location)); if (QThread::currentThread()->isInterruptionRequested()) return; } }
and finally, in mainwindow.cpp
connect(ui->btnData, SIGNAL(clicked()), this, SLOT(data())); void MainWindow::data() { thread->startThread1(motor, ui->statusHeader); }
When I run the codes without addition, It works properly-displays the location value to statusheader, but with addition, It doesn't work.
It seems to have a problem in while loop in position.cpp because I checked the
experiment.txt
file is created.Can you do me a favor?
-
Hi,
And what exactly is your issue ?
I hope you are giving due credit to the people helping you when returning your assignments ;-)
-
@SGaist
Hi, My issue is when I put the opening and writing file code, the while loop doesn't run.
My original code is like belowvoid Position::measureLocation1(MDCE* pcom) { double location; char record[] = "X_enc_pos"; while (1) { GetVarN(record, &location, 0, pcom); //this function returns double value to location. emit location_changed1(QString::number(location)); if (QThread::currentThread()->isInterruptionRequested()) return; } }
It emits signals repeatedly in the thread properly.
I expect the code runs through the following process when I changed codes
create experiment.txt
in while loop
{
write elapsed time and the value of the position to experiment.txt
emit signal
}
when I give interruption, stop the while loop.I already mentioned to the professor that thanks to QT forum, I found breakthrough in my GUI work :) I really appreciate it.
-
@H-dragon
so, have you tried thisout << timer->elapsed() << " " << location<<"\n";
without thread and while loop and everything?
depending on what it is, QTextStream may not be able to interpret that variables to write them to file -
@J-Hilk
Yes, I runout << timer->elapsed() << " " << location<<"\n";
in the following 4 situations.- run in mainwindow.cpp just once -> run properly
- use QTextStream as parameter -> compile error
void MainWindow::data() { QFile file("C:/Users/Sonic/experiment.txt"); if (!file.open(QFile::WriteOnly | QFile::Text)) { return; } QTextStream out(&file); thread->startThread1(motor, ui->statusHeader, out); ///QTextStream as parameter }
- run in the thread, but not in while loop -> GUI terminate. It doesn't work.
- run in while loop -> my goal, but doesn't work too
-
If it works without the thread and the while loop, then my guess is, you're overwhelming the OS's file IO system or QTextStream. The write attempt probably happens a couple hundred times per second.
Try to explicitly flush, after writing
GetVarN(record, &location, 0, pcom); //this function returns double value to location. out << timer->elapsed() << " " << location<<"\n"; // write time and location value to experiment.txt out.flush(); emit location_changed1(QString::number(location)); if (QThread::currentThread()->isInterruptionRequested()) return;
-
Check with your debugger if the QTextBrowser is not accessed from the second thread. All GUI actions must be performed from the main thread. it's forbidden to access GUI from another thread.