Matt Phillips
Matt Phillips

Reputation: 9691

How do I wait until QWidget::repaint is finished?

I have a gui with a QWidget (specifically, a QwtPlot but I don't think the problem is Qwt-specific) which I redraw using a timer. I.e., every 100ms QWidget::update gets called, via QwtPlot::replot. When the timer interval too small, or the number of samples in the QwtCurve (QPolygonF) is too large, the program crashes, usually with an error message like this:

QWidget::repaint: Recursive repaint detected

QPainter::begin: A paint device can only be painted by one painter at a time.

QPainter::translate: Painter not active

QPainter::begin: A paint device can only be painted by one painter at a time.

QPainter::save: Painter not active

QPainter::setClipRect: Painter not active

QPainter::save: Painter not active

QPainter::setRenderHint: Painter must be active to set rendering hints

QPainter::setRenderHint: Painter must be active to set rendering hints

QPainter::restore: Unbalanced save/restore

QPainter::save: Painter not active

QPainter::setRenderHint: Painter must be active to set rendering hints

QPainter::setRenderHint: Painter must be active to set rendering hints

QPainter::save: Painter not active

QPainter::setPen: Painter not active

QPainter::Pen: Painter not active

QPainter::restore: Unbalanced save/restore

QPainter::restore: Unbalanced save/restore

QPainter::save: Painter not active ...

The standard reason for a 'recursive repaint' error is if you call paint() within update or something like that, but I am not subclassing QWidget so this never happens in my code. Qwt has been around long enough that I'm pretty sure that no fundamental error such as this is present in that code. This leaves me thinking that update is getting called before the last draw has finished, which leads me to my question: Is there a way to find out whether a repaint is complete, and so, skip a given repaint if the last one hasn't finished at the time the timer fires again?

Edit: I use a timer because the calculations which generate the data to be drawn are done in a worker thread. I use a Qt::BlockingQueuedConnection for this signal and guarantee with an assert() that replot is only ever called from the main thread. This why I don't use the autoreplot functionality of QwtPlot, the program will crash if I try.

Upvotes: 0

Views: 2142

Answers (1)

Fabian
Fabian

Reputation: 1844

As Chris says the update() call should not cause any problem.

It might help to install a custom message handler via qInstallMsgHandler() in your application. This way you can get a break point at the time when the warning appears and check out when/why this exactly happens.

Upvotes: 0

Related Questions