PDA

View Full Version : update a counter in PlainTextEdit on the same line



qt_gotcha
11th August 2010, 08:19
I have a PlainTextEdit called commandWindow in which I want to display a counter. The counter comes from a thread process. The counter is always on the last line of the PlainTextEdit. I made some test code, the sqrt is to delay the counter:

QString out;
QStringList list;
for (int i = 0; i < 100; i++)
{
double x;
out = commandWindow->toPlainText();
list = out.split("\n");
list.removeLast();
for (int j = 0; j < 10000; j++)
x = sqrt(847239);
list << QString("%1 %2").arg(i).arg(x);
out = list.join("\n");
commandWindow->setPlainText(out);
}
commandWindow->appendPlainText("done\n");
this doesn't display the counter but only updates the commandWIndow whenit is done, it display 99. Also if I comment out the list.removeLast();, it only shows the hunderd lines after it is finished. Suggestions are welcome.

Lesiok
11th August 2010, 08:39
Because for loop is disabling event dispatcher. Just write Yours code like this :

....
commandWindow->setPlainText(out);
QCoreApplication::processEvents();
....

qt_gotcha
13th August 2010, 11:08
actually
QCoreApplication::sendPostedEvents(this, 0);
works better

I have a QProcess (calcProcess) that is linked to a unix programme that gives of blocks of bytes (no readlines, '\n'). It outputs only on the error channel. It outputs first its name, then an umpty line, then a counter that looks like "Execute timstep xxx". That output should be processed in a PlainTextEdit called commandWindow

my code now looks like this for those who are interested:

calcProcess->setReadChannel ( QProcess::StandardError );
connect(calcProcess, SIGNAL(readyReadStandardError()),this, SLOT(readFromStderr()) );
connect(calcProcess, SIGNAL(finished(int)),this, SLOT(finishedModel(int)) );


In the starter function of the process:


{
[...] //get relevant proces info

commandWindow->appendPlainText(" ");
commandWindow->appendPlainText(" ");
commandWindow->appendPlainText(" ");
xlast = commandWindow->document()->lineCount();
// append extra empty lines that will be replaced with the process output

calcProcess->start(prog, args);
}

The function to proces the output on screen is as follows:



void nutshellqt::readFromStderr()
{
QByteArray buf;
buf.clear();
buf = calcProcess->readAllStandardError();
onScreen(QString(buf));
}

void nutshellqt::onScreen(QString buffer)
{
QString output;
QStringList list, listb;
QTimer tT;
tT.setSingleShot(true);

buffer.replace('\r','\n');
// replace unix CR with \n
listb.clear();
listb = buffer.split("\n");
// split process output all out in seperate lines

output = commandWindow->toPlainText();
list = output.split("\n");
// get the lines in the commandWindow, might get slow?

foreach (QString str, listb)
{
if(str.contains("version") )
list.replace(xlast-3,str);
if (str.contains("Exec") )
list.replace(xlast-1,str);

QCoreApplication::sendPostedEvents(this, 0);
// update the plaintextedit with these two actions

tT.start(100);
//delay slightly for readability

output=list.join("\n");
commandWindow->setPlainText(output);
// join new lines and replace the commandWindow

QTextCursor cur = commandWindow->textCursor();
cur.setPosition(output.size());
commandWindow->setTextCursor(cur);
//put the cursor at the end

QCoreApplication::sendPostedEvents(this, 0);
// update plaintextedit with last actions
}
}