Optimizing Qt 4 Graphics View

來源:互聯網
上載者:User

During the summer I worked a lot with one of the latest addition to the Qt framework
,
the graphics view. The graphics view is basically a canvas to draw
2D-graphics, and replaced the QCanvas class from Qt 3.x. It was added
to Qt in version 4.2.

The application I worked on is used for displaying a sea map along
with various other maritime related information (and a lot of other
stuff that’s not really relevant). While the application functioned the
way it was, we wanted to replace our old (somewhat hackish) way of
representing the parts of the program as CSS-themed top-level widgets
and using a embedded graphics view to represent the entire UI of the
application. This approach would give us a better ability to integrate
the various parts of the application, as well as support transitions
between various view states of the program (and other nifty graphics
effects). With the recent addition of QGraphicsProxyWidget in Qt 4.4
this was finally an option, so we decided to give it a shot.

During the initial porting of the application, we did not notice
much in the way of performance loss, but as soon as we added more (and
larger) dynamical elements to the GUI, it started slowing down. This
led me to investigate why the application was slowing down, and how to
remedy the situation. The reason why is pretty simple: in order for Qt
to draw widgets inside the graphics view, it apparently has to render
them twice. Qt will first render the widget to an off-screen buffer,
and then render the content of the off-screen buffer to the graphics
scene as a texture. As soon as we knew why, we started looking at how
to optimize it.

Accelerating the Scene:

Qt allows you to use OpenGL to accelerate the scene. This can
greatly increase the performance, assuming the graphics card in your
computer has decent support for hardware accelerating 2D operations
(this is not the case for nVidia today). To enable OpenGL acceleration,
you will have to create a QGLWidget and tell the graphics scene to use
it as a viewport.  Here’s an example:

QGLWidget* viewport = new QGLWidget(QGLFormat(QGL::DoubleBuffer | QGL::Rgba |
QGL::AlphaChannel | QGL::DirectRendering | QGL::SampleBuffers));
myGraphicsScene->setViewport(viewport);


Item Cache:

The graphics view allows you to independently set the cache mode for each item in the scene.  Setting the cache mode to QGraphicsItem::DeviceCoordinateCache
will make Qt use the cached version of a item instead of redrawing the
item (twice) every time the scene is updated. This sort of cache will
not work if you need to transform (rotate, scale, shear, etc.) the
item. If you need transformation you should have a look at the QGraphicsItem::ItemCoordinateCache
cache mode.

Increasing the Pixmap Cache Size:

While caching the items works good when you’ve got a small amount of
small objects, I soon figured out that when adding larger items, or
just a lot of small ones, the drawing becomes slow again. It took me
some time, but I finally figured out why. When you tell Qt to use cache
for graphics items, it uses its internal QPixmapCache as a buffer for
the items. This is not explicitly mentioned in the documentation, only
a hint is given in the “See also”-section of the documentation. The
default size for this cache is 1024kb
, which explains
why it gets slower the more items you add. Increasing the cache size is
imperative if your application will use a lot of objects and you want
cache. You can achieve this by calling the static function QPixmapCache::setCacheLimit(int)
, just keep in mind it takes kilobytes as the argument.

Other tricks:

While these tricks are the ones that gave the greatest increase in
performance (a dogmatic conclusion, no real benchmarks where made) in
our application, there are several other functions you might want
to  look at:

QGraphicsView::setOptimizationFlag
QGraphicsView::setViewportUpdateMode
QGraphicsScene::setItemIndexMethod

These functions may give an increase in performance, depending on the nature of the application.

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.