Trolltech Home | Qt4-preview-feedback Home | Recent Threads | All Threads | Author | Date
All threads index page 1

Qt4-preview-feedback Archive, February 2007
QGraphicsView exposed rectangle and intersection calculation issues

Pages: Prev | 1 | 2 | Next

Message 1 in thread

Hello,

I've been porting my application to QGraphicsView (at last), using one of the 
latest Qt 4.3 snapshots, and it works great, thanks a lot!
There are however some issues in respect to (don't hate me to bring this 
up ;-) ) painting and related performance.
I digged into the code, and found some things that might improve things a lot, 
some code paths seem to do the wrong calculation, imposing a lot of unneeded 
cpu overhead.

It this isn't the correct list, please let me know, so I can send it to the 
correct one or person!


Exposed rectangle calculation:

The updateScene(const QList<QRectF> &rects) by default adjusts the rectangles 
by 2 pixels into all 4 directions, to compensate for antialiasing.
However, by default a QGV doesn't have antialising set. Somewhere (didn't find 
where) the rectangles _allready_ are adjusted by 1 pixel !!
So by default, an exposed rectangle grows by 3 pixels into all directions.

Moving a 2 pixel width rectangle item over the sceen by one pixel at a time 
thus creates an update of it's height + 6 pixels @ 9 pixels width! OUCH ??

If no antialising is used, then the real bounding rect of the item would be 
sufficient, right? No need to adjust by 3 pixels into all directions.... ?
What about moving the responsability of compensating the bounding rect when 
antialiased painting is used to the program using QGV ?


GraphicsView::paintEvent:

For this particular case, scrolling the view with ~ 30 items painting 
polygons, 20% of the time spend in this function was spend in 
d->scene->items(rect, Qt::IntersectsItemBoundingRect), and most of that time 
was spend in _qt_pathIntersectsItem().

Despite the Qt::IntersectsItemBoundingRect flag, it appears (at least to me) 
that this function still uses QPainterPaths::intersect(path) function, 
(qgraphicsscene line 1313, hm, scary number lol) instead of using the 
QRectF::intersect(rect) function, imposing all the overhead of path based 
intersection calculation... ?
The QPainterPath::addPolygon() (line 1307) isn't particularly cheap either in 
this respect...?

Obviously, the more items, the higher the overhead. Well, it looks like a 
unwanted kind of calculation :-)


Duplicated paint events:

It so happened that when changing the bounding rects of the items, and 
scrolling to a new position (the new center position), from within one 
function, the resulting updates were send twice. (paintEvent() is called 2 
times with exactly the same QRegion)
Did I do something wrong, a bug maybe, known problem ?


Another problem that emerged was this:

When an item with say, 2 pixel width, and viewport height is located close to 
the left of the viewport is updated  _and_ the viewport scrolls to the right, 
the rect : item's viewport x pos -> viewport width get's updated.
Or in other words, the whole viewport is repainted, instead of the exposed 
rect due the scroll, and the rect of the moved item.

Last but not least, it would be wicked if there would be some kind of 
crosshair like item, that on move doesn't trigger repaints for the items 
below it, but rather buffers the background of it's new position, and 
restores the background of it's old position, which could easily be done from 
within the GQV's paintEvent function.
Of course, it needs to be kept out of the updateScene(); function to avoid 
triggering the repaint of items below it.


Reimplementing the slot updateScene(); could allready give the developers 
using QGV a lot more flexibility in this regard, but it's not a virtual 
function.

Reimplementing the paintEvent of course can be done allready, but not all the 
goodies in the default implemenation are accessable from the api :-(
After all, the QGV::paintEvent() isn't the problem per se, the cpu bottleneck 
there is in the scene->items() function.

After all, the arthur paint engine, specially in Qt 4.3 is doing a sublime 
job, so thats certainly not a problem.
Duplication of an update event that repaint the whole view, hum, is, as well 
as the 3 pixel adjustment even when no antialiasing is used :-)


Thanks for your time, if there is something I missed, then I really appreciate 
if you can point me how to do it correctly.
It might also be helpfull for others, since I think these issues might affect 
others as well (KGoldrunner discussion comes in mind heh)


Remon

To unsubscribe - send "unsubscribe" in the subject to qt4-preview-feedback-request@xxxxxxxxxxxxx


Message 2 in thread

Hi, Remon.

Remon wrote:
> Moving a 2 pixel width rectangle item over the sceen by one pixel at a
> time thus creates an update of it's height + 6 pixels @ 9 pixels width!
> OUCH ??

In 4.3, you can set an optimization flag to minimize this adjustment:
DontAdjustForAntialiasing. If you combine this with antialiasing, you're on
your own :-).

> For this particular case, scrolling the view with ~ 30 items painting
> polygons, 20% of the time spend in this function was spend in
> d->scene->items(rect, Qt::IntersectsItemBoundingRect), and most of that
> time was spend in _qt_pathIntersectsItem().

If you rerun this test with one of the latest snapshots, item discovery
should be completely gone from your benchmark. It's very fast now compared
to 4.2, and might get even faster.

> Duplicated paint events:
> It so happened that when changing the bounding rects of the items, and
> scrolling to a new position (the new center position), from within one
> function, the resulting updates were send twice. (paintEvent() is called 2
> times with exactly the same QRegion)
> Did I do something wrong, a bug maybe, known problem ?

I cannot say, can you send code that reproduces the problem?

> Another problem that emerged was this:
> When an item with say, 2 pixel width, and viewport height is located close
> to
> the left of the viewport is updated  _and_ the viewport scrolls to the
> right, the rect : item's viewport x pos -> viewport width get's updated.
> Or in other words, the whole viewport is repainted, instead of the exposed
> rect due the scroll, and the rect of the moved item.

I don't understand; do you mean QGraphicsView sometimes issues a full
viewport export even if there are only partial updates? Could you elaborate
on that?

> Last but not least, it would be wicked if there would be some kind of
> crosshair like item, that on move doesn't trigger repaints for the items

You can probably do this already; check out QPainter::CompositionMode_Xor in
4.3 snapshots (and QPaintEngine::PorterDuff).

> Reimplementing the slot updateScene(); could allready give the developers
> using QGV a lot more flexibility in this regard, but it's not a virtual
> function.

Slots have the same calling semantics as virtual functions; if you
reimplement them, they will be called.

> Reimplementing the paintEvent of course can be done allready, but not all
> the goodies in the default implemenation are accessable from the api :-(
> After all, the QGV::paintEvent() isn't the problem per se, the cpu
> bottleneck there is in the scene->items() function.

That bottleneck is probably gone now.

> Thanks for your time, if there is something I missed, then I really
> appreciate if you can point me how to do it correctly.
> It might also be helpfull for others, since I think these issues might
> affect others as well (KGoldrunner discussion comes in mind heh)

I /think/ all issues you asked about in this email have been solved. Good
luck!

Andreas

-- 
 [ signature omitted ] 

Message 3 in thread

Andreas Aardal Hanssen wrote:
> Hi, Remon.
> 
> Remon wrote:
>> Moving a 2 pixel width rectangle item over the sceen by one pixel at a
>> time thus creates an update of it's height + 6 pixels @ 9 pixels width!
>> OUCH ??
> 
> In 4.3, you can set an optimization flag to minimize this adjustment:
> DontAdjustForAntialiasing. If you combine this with antialiasing, you're on
> your own :-).
> 
>> For this particular case, scrolling the view with ~ 30 items painting
>> polygons, 20% of the time spend in this function was spend in
>> d->scene->items(rect, Qt::IntersectsItemBoundingRect), and most of that
>> time was spend in _qt_pathIntersectsItem().
> 
> If you rerun this test with one of the latest snapshots, item discovery
> should be completely gone from your benchmark. It's very fast now compared
> to 4.2, and might get even faster.

Andreas to which snapshot do you refer? Last week I tried 4.3-20070215 
and 4.2 was still superior to 4.3

When enabling the timing debug option in QGraphicsView:

4.3 TIMINGS:
Item discovery.......  4709 msecs ( 437925 items, 92997.5 / sec )
Drawing background...  0 msecs ( 1 segments )
Drawing items........  6518 msecs ( 67187 / sec )
Drawing foreground...  64 msecs ( 1 segments )
Total rendering time:  11291 msecs ( 0.0885661 fps )

4.2 TIMINGS:
Item discovery.......  3520 msecs ( 437925 items, 124411 / sec )
Drawing background...  1 msecs ( 1 segments )
Drawing items........  5878 msecs ( 74502.4 / sec )
Drawing foreground...  62 msecs ( 1 segments )
Total rendering time:  9462 msecs ( 0.105686 fps )

Well 0.105686 fps is not great but 0.0885661 is fps more then 15%
slower.

Henk Jan
> 
>> Duplicated paint events:
>> It so happened that when changing the bounding rects of the items, and
>> scrolling to a new position (the new center position), from within one
>> function, the resulting updates were send twice. (paintEvent() is called 2
>> times with exactly the same QRegion)
>> Did I do something wrong, a bug maybe, known problem ?
> 
> I cannot say, can you send code that reproduces the problem?
> 
>> Another problem that emerged was this:
>> When an item with say, 2 pixel width, and viewport height is located close
>> to
>> the left of the viewport is updated  _and_ the viewport scrolls to the
>> right, the rect : item's viewport x pos -> viewport width get's updated.
>> Or in other words, the whole viewport is repainted, instead of the exposed
>> rect due the scroll, and the rect of the moved item.
> 
> I don't understand; do you mean QGraphicsView sometimes issues a full
> viewport export even if there are only partial updates? Could you elaborate
> on that?
> 
>> Last but not least, it would be wicked if there would be some kind of
>> crosshair like item, that on move doesn't trigger repaints for the items
> 
> You can probably do this already; check out QPainter::CompositionMode_Xor in
> 4.3 snapshots (and QPaintEngine::PorterDuff).
> 
>> Reimplementing the slot updateScene(); could allready give the developers
>> using QGV a lot more flexibility in this regard, but it's not a virtual
>> function.
> 
> Slots have the same calling semantics as virtual functions; if you
> reimplement them, they will be called.
> 
>> Reimplementing the paintEvent of course can be done allready, but not all
>> the goodies in the default implemenation are accessable from the api :-(
>> After all, the QGV::paintEvent() isn't the problem per se, the cpu
>> bottleneck there is in the scene->items() function.
> 
> That bottleneck is probably gone now.
> 
>> Thanks for your time, if there is something I missed, then I really
>> appreciate if you can point me how to do it correctly.
>> It might also be helpfull for others, since I think these issues might
>> affect others as well (KGoldrunner discussion comes in mind heh)
> 
> I /think/ all issues you asked about in this email have been solved. Good
> luck!
> 
> Andreas
> 

To unsubscribe - send "unsubscribe" in the subject to qt4-preview-feedback-request@xxxxxxxxxxxxx


Message 4 in thread

Henk Jan Priester wrote:
> Andreas to which snapshot do you refer? Last week I tried 4.3-20070215
> and 4.2 was still superior to 4.3

The last optimizations went in on Friday last week; have you tried the most
recent ones?

Andreas

-- 
 [ signature omitted ] 

Message 5 in thread

Andreas Aardal Hanssen wrote:
> Henk Jan Priester wrote:
>> Andreas to which snapshot do you refer? Last week I tried 4.3-20070215
>> and 4.2 was still superior to 4.3
> 
> The last optimizations went in on Friday last week; have you tried the most
> recent ones?

No I only tried 20070215, I will test it again this week.

Henk Jan
> 
> Andreas
> 

To unsubscribe - send "unsubscribe" in the subject to qt4-preview-feedback-request@xxxxxxxxxxxxx


Message 6 in thread

Andreas Aardal Hanssen wrote:
> Henk Jan Priester wrote:
>> Andreas to which snapshot do you refer? Last week I tried 4.3-20070215
>> and 4.2 was still superior to 4.3
> 
> The last optimizations went in on Friday last week; have you tried the most
> recent ones?

Andreas,

I compiled both the 4.2.2 snapshot and the 4.3 snapshot (20070220) and 
tested it with my program.

It looks that the last optimizations made item discovery faster then
the 4.3 version of last week and also faster then 4.2

When I load a file I now have with 4.3:

QGraphicsView::paintEvent( QRegion(size=1), bounds = QRect(0,0 776x584)
  -  0 QRect(0,0 776x584)
  )
         Item discovery.......  2252 msecs ( 437916 items, 194456 / sec )
         Drawing background...  1 msecs ( 1 segments )
         Drawing items........  6511 msecs ( 67257.9 / sec )
         Drawing foreground...  61 msecs ( 1 segments )
         Total rendering time:  8825 msecs ( 0.113314 fps )
QGraphicsView::paintEvent( QRegion(size=1), bounds = QRect(0,0 776x584)
  -  0 QRect(0,0 776x584)
  )
         Item discovery.......  2300 msecs ( 437916 items, 190398 / sec )
         Drawing background...  0 msecs ( 1 segments )
         Drawing items........  6397 msecs ( 68456.5 / sec )
         Drawing foreground...  60 msecs ( 1 segments )
         Total rendering time:  8757 msecs ( 0.114194 fps )

With 4.2

QGraphicsView::paintEvent( QRegion(size=1), bounds = QRect(0,0 776x584)
  -  0 QRect(0,0 776x584)
  )
         Item discovery.......  3373 msecs ( 437915 items, 129830 / sec )
         Drawing background...  0 msecs ( 1 segments )
         Drawing items........  6445 msecs ( 67946.5 / sec )
         Drawing foreground...  60 msecs ( 1 segments )
         Total rendering time:  9879 msecs ( 0.101225 fps )
QGraphicsView::paintEvent( QRegion(size=2), bounds = QRect(71,0 705x584)
  -  0 QRect(468,0 16x2)
  -  1 QRect(71,2 705x582)
  )
         Item discovery.......  3835 msecs ( 437915 items, 114189 / sec )
         Drawing background...  0 msecs ( 2 segments )
         Drawing items........  6970 msecs ( 62828.6 / sec )
         Drawing foreground...  60 msecs ( 2 segments )
         Total rendering time:  10865 msecs ( 0.0920387 fps )

I have done some other tests as well and I have not had a case where the 
new 4.3 Item discovery is slower. Drawing items seems a bit slower then
with 4.2.

The item discovery is discovery is definitely improved. I am just 
wondering why the paintEvent is called twice. When loading these 
inefficient files the whole paintEvent takes quite a lot of time.
This could be caused by our program as well I need to have a
look.

Henk Jan

> 
> Andreas
> 

To unsubscribe - send "unsubscribe" in the subject to qt4-preview-feedback-request@xxxxxxxxxxxxx


Message 7 in thread

Henk Jan Priester wrote:
>> The last optimizations went in on Friday last week; have you tried the
>> most recent ones?
> I compiled both the 4.2.2 snapshot and the 4.3 snapshot (20070220) and
> tested it with my program.
> It looks that the last optimizations made item discovery faster then
> the 4.3 version of last week and also faster then 4.2

Good, that sounds right.

> When I load a file I now have with 4.3:
>...
> With 4.2
>...
> I have done some other tests as well and I have not had a case where the
> new 4.3 Item discovery is slower. Drawing items seems a bit slower then
> with 4.2.

Keep in mind that the benchmark numbers in paintEvent() are very unreliable,
because they use the system timer to measure speed in one frame only - the
timer resolution isn't high enough to pick up subtle differences. The best
thing is to let an animation run for a fixed number of frames, and use a
profiler (like callgrind) to measure the number of instructions and
simulated time spent.

> The item discovery is discovery is definitely improved. I am just
> wondering why the paintEvent is called twice. When loading these
> inefficient files the whole paintEvent takes quite a lot of time.
> This could be caused by our program as well I need to have a
> look.

Can you provide an example that demonstrates this? If this is application
start-up, there's nothing we can do (as the desktop sends us two complete
refreshes, one for an inactive window, and then one for the active state).

Andreas

-- 
 [ signature omitted ] 

Message 8 in thread

Andreas Aardal Hanssen wrote:
> Henk Jan Priester wrote:
>>> The last optimizations went in on Friday last week; have you tried the
>>> most recent ones?
>> I compiled both the 4.2.2 snapshot and the 4.3 snapshot (20070220) and
>> tested it with my program.
>> It looks that the last optimizations made item discovery faster then
>> the 4.3 version of last week and also faster then 4.2
> 
> Good, that sounds right.
> 
>> When I load a file I now have with 4.3:
>> ...
>> With 4.2
>> ...
>> I have done some other tests as well and I have not had a case where the
>> new 4.3 Item discovery is slower. Drawing items seems a bit slower then
>> with 4.2.
> 
> Keep in mind that the benchmark numbers in paintEvent() are very unreliable,
> because they use the system timer to measure speed in one frame only - the
> timer resolution isn't high enough to pick up subtle differences. The best
> thing is to let an animation run for a fixed number of frames, and use a
> profiler (like callgrind) to measure the number of instructions and
> simulated time spent.

Well that is true but when I have a scene with 1000's of elements
then the timers more are reliable.
For example:

QGraphicsView::paintEvent( QRegion(size=1), bounds = QRect(0,0 849x591)
  -  0 QRect(0,0 849x591)
  )
         Item discovery.......  3529 msecs ( 437925 items, 124093 / sec )
         Drawing background...  1 msecs ( 1 segments )
         Drawing items........  5780 msecs ( 75765.6 / sec )
         Drawing foreground...  59 msecs ( 1 segments )
         Total rendering time:  9370 msecs ( 0.106724 fps )
QGraphicsView::paintEvent( QRegion(size=1), bounds = QRect(101,0 748x591)
  -  0 QRect(101,0 748x591)
  )
         Item discovery.......  3606 msecs ( 437925 items, 121443 / sec )
         Drawing background...  0 msecs ( 1 segments )
         Drawing items........  5945 msecs ( 73662.7 / sec )
         Drawing foreground...  63 msecs ( 1 segments )
         Total rendering time:  9614 msecs ( 0.104015 fps )
QGraphicsView::paintEvent( QRegion(size=26), bounds = QRect(76,0 773x591)
  -  0 QRect(76,0 675x5)
  -  1 QRect(76,5 675x22)
  -  2 QRect(806,5 38x22)
  -  3 QRect(76,27 675x7)
  -  4 QRect(776,27 68x7)
  -  5 QRect(76,34 675x22)
  -  6 QRect(776,34 38x22)
  -  7 QRect(76,56 675x61)
  -  8 QRect(76,117 675x28)
  -  9 QRect(812,117 37x28)
  -  10 QRect(76,145 675x166)
  -  11 QRect(76,311 675x28)
  -  12 QRect(759,311 34x28)
  -  13 QRect(76,339 675x15)
  -  14 QRect(76,354 675x29)
  -  15 QRect(757,354 35x29)
  -  16 QRect(76,383 675x26)
  -  17 QRect(76,409 709x29)
  -  18 QRect(76,438 675x40)
  -  19 QRect(97,478 654x87)
  -  20 QRect(96,565 655x15)
  -  21 QRect(96,580 80x7)
  -  22 QRect(305,580 37x7)
  -  23 QRect(504,580 35x7)
  -  24 QRect(96,587 80x4)
  -  25 QRect(504,587 35x4)
  )
         Item discovery.......  5370 msecs ( 437884 items, 81542.6 / sec )
         Drawing background...  3 msecs ( 26 segments )
         Drawing items........  13004 msecs ( 33673 / sec )
         Drawing foreground...  61 msecs ( 26 segments )
         Total rendering time:  18439 msecs ( 0.0542329 fps )

As you can see in my case there are 437884 items and when the paintEvent
consists of many multiple regions the total rendering time can be
a lot worser then redrawing everything.
In this example it is 18.4 vs 9.3 seconds. I have seen even more
worse examples. I think at some point it is more efficient to combine
all those small regions to one bigger region.
In one case I got 1104 regions but there are only 670 elements.

> 
>> The item discovery is discovery is definitely improved. I am just
>> wondering why the paintEvent is called twice. When loading these
>> inefficient files the whole paintEvent takes quite a lot of time.
>> This could be caused by our program as well I need to have a
>> look.
> 
> Can you provide an example that demonstrates this? If this is application
> start-up, there's nothing we can do (as the desktop sends us two complete
> refreshes, one for an inactive window, and then one for the active state).

It is not at application startup it happens after we load a
vector file in the application (a simple vector editor).
For files with less then 10000 it is not realy a problem but when
we add files with more then 100000 items it becomes slower.
We also use the 'fit to view' and I need to debug this first if it
is not our fault. I will see if I can reproduce it with a small
program.

Henk Jan


> 
> Andreas
> 

To unsubscribe - send "unsubscribe" in the subject to qt4-preview-feedback-request@xxxxxxxxxxxxx


Message 9 in thread

Henk Jan Priester wrote:
> In this example it is 18.4 vs 9.3 seconds. I have seen even more
> worse examples. I think at some point it is more efficient to combine
> all those small regions to one bigger region.
> In one case I got 1104 regions but there are only 670 elements.

In 4.3, if you set QGraphicsView::SmartViewportUpdate, you'll get this
behavior; at a certain threshold (currently set to 50 rects), the bounding
rect is used instead. Otherwise, you can always subclass QGraphicsView an
provide a custom updateScene() slot.

-- 
 [ signature omitted ] 

Message 10 in thread

Andreas Aardal Hanssen wrote:
> Henk Jan Priester wrote:
>> In this example it is 18.4 vs 9.3 seconds. I have seen even more
>> worse examples. I think at some point it is more efficient to combine
>> all those small regions to one bigger region.
>> In one case I got 1104 regions but there are only 670 elements.
> 
> In 4.3, if you set QGraphicsView::SmartViewportUpdate, you'll get this
> behavior; at a certain threshold (currently set to 50 rects), the bounding
> rect is used instead. Otherwise, you can always subclass QGraphicsView an
> provide a custom updateScene() slot.

Andreas,

Thanks for the suggestion, I will have a look at the 'SmartViewportUpdate'.
Last time when we tried to reimplement something within
QGraphicsView we had some problems. Most virtual functions
rely on accessing the implementation and in a subclass
you don't have access to this and we ended with duplicating code.

For example in the updateScene:

     Q_D(QGraphicsView);

     if (d->viewportUpdateMode == QGraphicsView::NoViewportUpdate)
         return;

I need to have a look if all members of the 'D-part' are accessible 
using functions.

Henk Jan





To unsubscribe - send "unsubscribe" in the subject to qt4-preview-feedback-request@xxxxxxxxxxxxx


Message 11 in thread

Andreas Aardal Hanssen wrote:
> Henk Jan Priester wrote:
>> In this example it is 18.4 vs 9.3 seconds. I have seen even more
>> worse examples. I think at some point it is more efficient to combine
>> all those small regions to one bigger region.
>> In one case I got 1104 regions but there are only 670 elements.
> 
> In 4.3, if you set QGraphicsView::SmartViewportUpdate, you'll get this
> behavior; at a certain threshold (currently set to 50 rects), the bounding
> rect is used instead. Otherwise, you can always subclass QGraphicsView an
> provide a custom updateScene() slot.

Andreas,

The SmartViewportUpdate is a big improvement for a some of the
performance issues we had.
Reimplementing is not so easy as it could be because updateScene()
accesses members in the private part like 'accelerateScrolling' etc.

I worked around it by calling the default implementation within
my implementation. It now also works when using 4.2.2

void
JGvView::updateScene( const QList<QRectF> &rects )
{
    if ( rects.size() < 25 )
    {
       QGraphicsView::updateScene(rects);
       return;
    }

    QRectF sumRect;
    foreach(QRectF rect, rects)
    {
       sumRect |= rect;
    }

    QList<QRectF> newrects;
    newrects.append(sumRect);
    QGraphicsView::updateScene(newrects);
}

Most of the double paintEvents I had where caused by my own code
when pre-scaling pixmaps (scaled pixmap are slow on X11). Also it
looks when using scrollbar option the 'Qt::ScrollBarAsNeeded' sometimes
double paintEvents are generated. (Qt:ScrollBarAlwaysOn works better
in mine case).

Henk Jan


> 

To unsubscribe - send "unsubscribe" in the subject to qt4-preview-feedback-request@xxxxxxxxxxxxx


Message 12 in thread

Henk Jan Priester wrote:
> Andreas,
> The SmartViewportUpdate is a big improvement for a some of the
> performance issues we had.

Good!

> Reimplementing is not so easy as it could be because updateScene()
> accesses members in the private part like 'accelerateScrolling' etc.
> I worked around it by calling the default implementation within
> my implementation. It now also works when using 4.2.2

That's not a workaround ;-). It's the correct way to reimplement any
function in C++ where you want base behavior. The base implementation is
almost guaranteed to access private data.

> void
> JGvView::updateScene( const QList<QRectF> &rects )
> {
> ...
> Most of the double paintEvents I had where caused by my own code
> when pre-scaling pixmaps (scaled pixmap are slow on X11). Also it
> looks when using scrollbar option the 'Qt::ScrollBarAsNeeded' sometimes
> double paintEvents are generated. (Qt:ScrollBarAlwaysOn works better
> in mine case).

I'll have to see this in code before I can understand why you'd be getting
double repaints.

Andreas

-- 
 [ signature omitted ] 

Message 13 in thread

Andreas Aardal Hanssen wrote:

>> Most of the double paintEvents I had where caused by my own code
>> when pre-scaling pixmaps (scaled pixmap are slow on X11). Also it
>> looks when using scrollbar option the 'Qt::ScrollBarAsNeeded' sometimes
>> double paintEvents are generated. (Qt:ScrollBarAlwaysOn works better
>> in mine case).
> 
> I'll have to see this in code before I can understand why you'd be getting
> double repaints.

I have created a simple example that shows this behaviour.

Just compile the attached example and run it, just click on the file
open button and select any file. (file is not used, but in my actual
program the file is used to fill the scene).

NOW I get two paint events:

FILE OPEN CALLED

QGraphicsView::paintEvent( QRegion(size=1), bounds = QRect(0,0 252x164)
  -  0 QRect(0,0 252x164)
  )
         Item discovery.......  97 msecs ( 25001 items, 257742 / sec )
         Drawing background...  0 msecs ( 1 segments )
         Drawing items........  467 msecs ( 53535.3 / sec )
         Drawing foreground...  4 msecs ( 1 segments )
         Total rendering time:  568 msecs ( 1.76056 fps )
QGraphicsView::paintEvent( QRegion(size=1), bounds = QRect(44,0 166x164)
  -  0 QRect(44,0 166x164)
  )
         Item discovery.......  106 msecs ( 25001 items, 235858 / sec )
         Drawing background...  0 msecs ( 1 segments )
         Drawing items........  510 msecs ( 49021.6 / sec )
         Drawing foreground...  4 msecs ( 1 segments )
         Total rendering time:  620 msecs ( 1.6129 fps )

The first time when you do a zoom-in you also get 2 paintEvents.
(but this one goes away when you always force the scrollbars to on)

Zoom IN
QGraphicsView::paintEvent( QRegion(size=1), bounds = QRect(0,0 252x164)
  -  0 QRect(0,0 252x164)
  )
         Item discovery.......  79 msecs ( 10555 items, 133608 / sec )
         Drawing background...  0 msecs ( 1 segments )
         Drawing items........  231 msecs ( 45692.6 / sec )
         Drawing foreground...  1 msecs ( 1 segments )
         Total rendering time:  312 msecs ( 3.20513 fps )
QGraphicsView::paintEvent( QRegion(size=1), bounds = QRect(0,0 237x149)
  -  0 QRect(0,0 237x149)
  )
         Item discovery.......  47 msecs ( 8979 items, 191043 / sec )
         Drawing background...  0 msecs ( 1 segments )
         Drawing items........  168 msecs ( 53446.4 / sec )
         Drawing foreground...  1 msecs ( 1 segments )
         Total rendering time:  217 msecs ( 4.60829 fps )

In our application rendering the scene sometimes costs 15 sec, so
that extra paintEvent is a bit annoying. We often use a fit to view
after a zoom-in and then you get a similiar behaviour. The workaround
is to force the scrollbars always on.

Henk Jan



> 
> Andreas
> 

Attachment:

Attachment: qview.tar.gz
Description: GNU Zip compressed data


Message 14 in thread

Hello Andreas,

Thanks a lot your response, will comment on some issues below.

> > Moving a 2 pixel width rectangle item over the sceen by one pixel at a
> > time thus creates an update of it's height + 6 pixels @ 9 pixels width!
> > OUCH ??
>
> In 4.3, you can set an optimization flag to minimize this adjustment:
> DontAdjustForAntialiasing. If you combine this with antialiasing, you're on
> your own :-).

Works great, thanks!
There still seems to be an adjustment of 1 pixel, could you please elaborate 
why this is needed ?


> > For this particular case, scrolling the view with ~ 30 items painting
> > polygons, 20% of the time spend in this function was spend in
> > d->scene->items(rect, Qt::IntersectsItemBoundingRect), and most of that
> > time was spend in _qt_pathIntersectsItem().
>
> If you rerun this test with one of the latest snapshots, item discovery
> should be completely gone from your benchmark. It's very fast now compared
> to 4.2, and might get even faster.

It's not completely gone, but it's a good deal faster indeed! It's about 10% 
now of the paintEvent() function, and it was about 20%, though it's always a 
bit hard to get those numbers right, there might be more/less time spend in 
the drawItems function, from an  older profile run, the Ir number has been 
cut in 1/3.
So definately an improvement here!

> > Duplicated paint events:
> > It so happened that when changing the bounding rects of the items, and
> > scrolling to a new position (the new center position), from within one
> > function, the resulting updates were send twice. (paintEvent() is called
> > 2 times with exactly the same QRegion)
> > Did I do something wrong, a bug maybe, known problem ?
>
> I cannot say, can you send code that reproduces the problem?

Sending code is a little hard, would you mind to have a look at the actuall 
code in question? It's not that much really, and I could compile a short 
tutor where to look, to see what happens at the events that cause the 
duplicated paint events, and other things .....

Duplicated paint events happen when the program changes the bounding rect of a 
number of items, and then recalculates the scene rectangle, since it could 
either be larger or smaller due the resized graphicsitems.

I've been thinking to just set the scene rect to as large as possible, and 
replace the scrollbars with custom ones, and calculate the correct positions 
of them by calculating the 'real' scene rect based on the position and size 
of the items in the view...

Well, that is, if it's not possible to both resize items _and_ recalculating 
the scene rect of a GraphicsView :-)

> > Another problem that emerged was this:
> > When an item with say, 2 pixel width, and viewport height is located
> > close to
> > the left of the viewport is updated  _and_ the viewport scrolls to the
> > right, the rect : item's viewport x pos -> viewport width get's updated.
> > Or in other words, the whole viewport is repainted, instead of the
> > exposed rect due the scroll, and the rect of the moved item.
>
> I don't understand; do you mean QGraphicsView sometimes issues a full
> viewport export even if there are only partial updates? Could you elaborate
> on that?

Screenshots say it all: [1]

The playhead, blue line which is a qgraphics item of 2 width scene height, 
moves during play over the canvas.
When it comes close to the right edge of the view,  a QTimeLine is used to 
scroll the view by about 3/4 page.
Obviously, the playhead moves during the scroll as well.
The exposed region now becomes the region from the playhead to the right edge 
of the viewport.
At the end of the scroll, that means about 3/4 of the viewport is repainted!

> > Last but not least, it would be wicked if there would be some kind of
> > crosshair like item, that on move doesn't trigger repaints for the items
>
> You can probably do this already; check out QPainter::CompositionMode_Xor
> in 4.3 snapshots (and QPaintEngine::PorterDuff).

OK, thanks, will have a look at that!


> > Reimplementing the slot updateScene(); could allready give the developers
> > using QGV a lot more flexibility in this regard, but it's not a virtual
> > function.
>
> Slots have the same calling semantics as virtual functions; if you
> reimplement them, they will be called.

Ah, didn't know, makes live much easier!

> > Reimplementing the paintEvent of course can be done allready, but not all
> > the goodies in the default implemenation are accessable from the api :-(
> > After all, the QGV::paintEvent() isn't the problem per se, the cpu
> > bottleneck there is in the scene->items() function.
>
> That bottleneck is probably gone now.

Yes, it has become much better by now, though if there is room for 
improvement, go for it! :-)

> > Thanks for your time, if there is something I missed, then I really
> > appreciate if you can point me how to do it correctly.
> > It might also be helpfull for others, since I think these issues might
> > affect others as well (KGoldrunner discussion comes in mind heh)
>
> I /think/ all issues you asked about in this email have been solved. Good
> luck!

There is at least one more issue, besides the duplicated paint events, and 
I've no idea where it comes from.

The audio wave form item accepts hover events (it's background color is 
different when the mouse hovers its).
On mouse enter, it's boundingrect seems to have grown by 1 pixel at the 
bottom, but horror, it grows also to the left edge of the view!!
(So all items left of it in the view, as well as the items below it due the 1 
pixel  additonal adjustment at the bottom get repainted :-( )
Don't ask me why or how this happens lol.

When the mouse leaves the item again, the exposed region is fine again, and == 
the items bounding rect, so I hardly can think of anything I did wrong ?

Thanks for your time,


Remon

[1] http://vt.shuis.tudelft.nl/~remon/traverso/screenies/screen7.png

To unsubscribe - send "unsubscribe" in the subject to qt4-preview-feedback-request@xxxxxxxxxxxxx


Message 15 in thread

> On mouse enter, it's boundingrect seems to have grown by 1 pixel at the
> bottom, but horror, it grows also to the left edge of the view!!

Correction: It seems the exposed area is viewport width!

Might make debugging a lot easier :-)


Remon

To unsubscribe - send "unsubscribe" in the subject to qt4-preview-feedback-request@xxxxxxxxxxxxx


Pages: Prev | 1 | 2 | Next