PDA

View Full Version : QFutureWatcher signals not firing



nwest
3rd December 2010, 18:39
Has anyone had problems with QFutureWatcher signals not firing? Here's the code:


QFutureWatcher<void> watcher;

connect(&watcher, SIGNAL(progressRangeChanged(int, int)), this, SLOT(progressRangeChanged(int, int)));
connect(&watcher, SIGNAL(progressValueChanged(int)), this, SLOT(progressValueChanged(int)));
connect(&watcher, SIGNAL(finished()), this, SLOT(finished()));

QFuture<dent_vec_t> dent_scan_future = QtConcurrent::mappedReduced(all_joint_scan_params, dent_scan_with_line,&combine_dent_lists);
watcher.setFuture(dent_scan_future);
while (!watcher.isFinished())
{
//Some debug code
int prog1 = watcher.progressMinimum();
int prog2 = watcher.progressMaximum();
int progValue = watcher.progressValue();
}
m_dents = dent_scan_future.result();

I threw in the debug code to see if there's any progress to report, and there is. Here are my slots:

Header:

public slots:
void finished();
void progressRangeChanged(int, int);
void progressValueChanged(int);

CPP:

void dent_scanner::finished()
{
cout<<"FINISHED"<<endl;
}

void dent_scanner::progressRangeChanged(int a, int b)
{
cout<<"PROGRESS RANGE CHANGED: " <<a<<", "<<b<<endl;
}

void dent_scanner::progressValueChanged(int a)
{
cout<<"PROGRESS VALUE CHANGED: " <<a<<endl;
}

This code won't execute no matter what I do. I have the Q_OBJECT macro in the header, and the moc file included at the bottom. The class inherits from QOBject. No errors print out when I connect up the signals and slots (already fixed that problem...)

I can usually find my way around signals and slots just fine. I probably just made a stupid mistake, but can't seem to figure out what it is. Any thoughts?

tbscope
3rd December 2010, 19:08
Are you sure the following line is correct?

QFutureWatcher<void> watcher;

Shouldn't that be the the following line?

QFutureWatcher<dent_vec_t> watcher;

nwest
3rd December 2010, 21:07
Well, I got the signals to fire, but not until everything was done, which defeats the point of monitoring the progress. So here's my new question: how can I actually monitor the progress DURING the threading. Maybe my code is doing something a little strange that won't allow any signals to fire until all the threads are free.

Added after 1:

OK this is getting annoying. Calling cancel on the Future returned from mappedReduced doesn't do anything until the entire computation has finished. I give it an array of 100's of items to process in mappedReduced, but it won't cancel until all have been processed. This is because the cancel signal won't get fired until the very end, just like all the other signals I'm dealing with.... Very strange. Anyone had this problem before?

wysota
3rd December 2010, 21:11
You are not letting the events be processed with your while() loop.

Keeping the GUI Responsive

nwest
3rd December 2010, 21:32
Yep, that seems to be it. I guess I just assumed the events would be processed during the threading automatically. I knew it would be something dumb like that.

It appears each individual thread that's running has to finish before it cancels. So there's no way to cancel a thread during its run. I guess it doesn't want to cause any bad states by killing a thread while it's processing data. If I'm wrong about this, please let me know. It would be great to able to kill a thread before it's finished.

Timoteo
3rd December 2010, 22:56
No, you're right. Killing a thread, such as calling TerminateThread(), allows no chance to clean up anything (which includes locking primitives!).