Seite 1 von 1

QGraphicsView/QGraphicsScene - schlechte Performance

Verfasst: 31. Mai 2009 13:33
von shapoc
Hallo zusammen,

ich bin noch neu in der QT-Welt, möchte euch aber trotzdem um Rat fragen.

Es geht darum, eine große Menge von Bildern zu visualisieren. Dazu habe ich mir das QGraphicsFramework angeschaut, mit den Beispielen herumexperimentiert (u.a. das Chip-Example) und habe dann mal angefangen, was eigenes aufzusetzen.

Es funktioniert soweit auch alles recht gut, nur bin ich nun an einem Punkt angekommen, an dem die Performance deutlich abnimmt und mein Programm überhaupt nicht mehr benutzbar wird.

Mein Projekt besteht bisher aus einem MainWindow, einer View-Klasse (von QGraphicsView), einer Scene (QGraphicsScene) und einer eigenen Item-Klasse.
Jedes Item stellt ein Bild (ca. 140x200 Pixel) dar, welches ich als QPixmap dort halte. Die Items selbst sind "statisch", d.h. nicht selektierbar, nur die View kann per "setDragMode(QGraphicsView::ScrollHandDrag)" verschoben und gezoomt werden.

Und das ist mein eigentliches Problem: Wenn ich herauszoome und mehr als ca. 200 Items sichtbar sind, kann ich weder zoomen noch scrollen, ohne zwischendurch Tee trinken zu gehen :-( ! Es ist einfach nicht performant.

Auch das Chip-Beispiel lässt sich nach dem totalen rauszoomen nicht wirklich gut scrollen, aber bis zu einem gewissen Grad ist es noch gut machbar.

Meine Frage nun: Wo kann ich ansetzen und die Performance verbessern? Gibt es Alternativen zum Graphics Framework in Qt? Vielleicht direkt als QGLWidget und dann alles selbst zeichnen?

Ich hab natürlich schon hier gesucht und auch google befragt, jedoch finden sich keine Ansätze für mein Problem mit sehr vielen Items?

Ich würde mich über Hilfe echt freuen!!!

Grüße,
Shapoc

System:
Win XP, AMD Athlon64 3200+, 1GB RAM
Qt 4.4.3

Verfasst: 31. Mai 2009 14:24
von upsala
Bringt es etwas, wenn du in der Demo auf OpenGL umschaltest?
Außerdem könnte es event. hilfreich sein, in den Items das passende Pixmap zu cachen.

Verfasst: 31. Mai 2009 14:30
von shapoc
Nein, weder in der Demo noch bei mir hilft die OpenGL Einstellung.
Ich setze sie bei mir mit:

Code: Alles auswählen

setViewport(new QGLWidget);
habe es aber auch schon mit:

Code: Alles auswählen

setViewport(new QGLWidget(QGLFormat(QGL::SampleBuffers)));
probiert, welches zusätzlich noch Antialiasing enabled, was ich aber eigentlich gar nicht brauche.

Den Cache-Mode habe ich mal auf:

Code: Alles auswählen

item->setCacheMode(QGraphicsItem::ItemCoordinateCache);
gesetzt, ebenfalls ohne sichtbare Verbesserung :-(

Gibt es noch weitere Performance-"Schrauben"?!

Verfasst: 31. Mai 2009 16:04
von upsala
Die Pixmaps selbst runterskalieren und catchen unter Berücksichtung von levelOfDetail.

Antialiasing vermeiden.

Event. noch mit isObscured() und opaqueArea() experimentieren.

Verfasst: 1. Juni 2009 11:30
von shapoc
Danke für die Tipps.

Ich habe jetzt mal folgendes probiert, und das gibt mir zu denken:

In meinen Items zeichne ich je nach levelOfDetail:

Code: Alles auswählen

	 if (option->levelOfDetail > 0.5)
	 {
		 painter->drawPixmap(0, 0, img->width(), img->height(),(*img) );
		return;
	}
	 else
	 {
		 painter->fillRect(boundingRect(), QBrush(QColor(100, 100, 100)));
		return;
	 }
Trotzdem ist das verschieben unerträglich langsam. Zudem werden nicht alle Items beim herauszoomen durch die Rechtecke "ersetzt", sondern erst die die vorher außerhalb des sichtbaren Bereichs lagen, wenn man dann nochmal rauszoomt, auch die im Zentrum der Scene.

Dann hab ich auch nochmal ausprobiert, direkt nur Rechtecke zu zeichnen, also in der paint-Methode mit:

Code: Alles auswählen

painter->fillRect(0,0,100,100, QBrush(QColor(100, 100, 100)));
return;
Trotzdem das gleiche Verhalten. Ab ca. 200 Items wird scrollen unmöglich.

Das kann doch nicht wirklich die Grenze sein? Kann das jemand vielleicht selbst mal verifizieren, ob das an Qt oder an meinem System liegt?

@upsala: was meinst du mit isObscured() und opaqueArea() ? HAst du dafür Beispiele?!

Verfasst: 1. Juni 2009 11:44
von shapoc
Gute Nachricht: Ich glaube den "Fehler" gefunden zu haben!

Beim Erstellen der Items habe ich mit verschiedenen Flags herumexperimentiert, u.a. mit:

Code: Alles auswählen

item->setCacheMode(QGraphicsItem::ItemCoordinateCache);
Als ich das eben zufällig rausgenommen hab, gings deutlich schneller. Nun kann ich auch bei sehr vielen Items gut scrollen.