Seite 1 von 1

QGraphicsScene in QWidget

Verfasst: 13. Juli 2011 16:01
von hardi
Hallo Qt Experten,

ich beschäftige mich seit kurzem mit Qt und möchte eine QGraphicsScene in einem QWidget laden. Ist dies möglich oder widersprechen sich die Konzepte von QGraphicsScene und QWidget?

Ich habe bereits folgendes ausprobiert:
Das offizielle Qt-Beispiel "colliding mice" habe ich modifiziert in der Datei main.cpp und die Klasse MyWidget hinzugefügt (Files mywidget.h und mywidget.cpp). Beim Kompilieren gab es keine Fehlermeldung. Leider war das Ergebnis war ein Bild mit grauem Inhalt statt umher irrenden Mäusen. Was habe ich an dieser Stelle vergessen?

Ich bin dankbar für eure Tipps! javascript:emoticon(':wink:')

Achja, hier der modifizierte/neue Code:


main.cpp

Code: Alles auswählen

 #include <QtGui>
 #include <math.h>
 #include "widget.h"

 int main(int argc, char **argv)
 {
     QApplication app(argc, argv);
     MyWidget window;
     window.show();
     return app.exec();
 }

mywidget.h

Code: Alles auswählen

#ifndef MYWIDGET_H_
#define MYWIDGET_H_

#include <QtGui>
#include <math.h>

#include "mouse.h"

class MyWidget : public QWidget
{
    Q_OBJECT

public:
    MyWidget(QWidget *parent = 0);
    ~MyWidget() {}
};
#endif

mywidget.cpp

Code: Alles auswählen

#include "mywidget.h"
using namespace std;
static const int MouseCount = 7;

MyWidget::MyWidget(QWidget *parent) : QWidget(parent) {

     QGraphicsScene scene;
     scene.setSceneRect(-300, -300, 600, 600);
     scene.setItemIndexMethod(QGraphicsScene::NoIndex);
     for (int i = 0; i < MouseCount; ++i) {
         Mouse *mouse = new Mouse;
         mouse->setPos(::sin((i * 6.28) / MouseCount) * 200,
                       ::cos((i * 6.28) / MouseCount) * 200);
         scene.addItem(mouse);
     }

     QGraphicsView view(&scene);
     view.setRenderHint(QPainter::Antialiasing);
     view.setBackgroundBrush(QPixmap(":/images/cheese.jpg"));
     view.setCacheMode(QGraphicsView::CacheBackground);
     view.setViewportUpdateMode(QGraphicsView::BoundingRectViewportUpdate);
     view.setDragMode(QGraphicsView::ScrollHandDrag);
     view.setWindowTitle(QT_TRANSLATE_NOOP(QGraphicsView, "Colliding Mice"));
     view.resize(600, 600);
     view.show();

     setCentralView();
     QTimer timer;
     qsrand(QTime(0,0,0).secsTo(QTime::currentTime()));
     QObject::connect(&timer, SIGNAL(timeout()), &scene, SLOT(advance()));
     timer.start(1000 / 33);

}
:wink: [/b]

Verfasst: 13. Juli 2011 16:11
von Christian81
Ich würde erstmal mit Grundlagen C++ anfangen und überlegen wie lange die Scene, der View und alles andere, was im ctor erzeugt wird, leben.

Verfasst: 14. Juli 2011 09:42
von hardi
Danke für deinen Hinweis.
Ich habe auch das Szenario getestet mit Member-Variable
QGraphicsScene *scene;
in Klasse MyLabel. Aber auch hier erhalte ich bei Programmausführung nur ein graues Fenster ohne gewünschten Inhalt. Fehlermeldungen gab es keine!!!

Verfasst: 14. Juli 2011 09:49
von franzf
Die scene alleine reicht nicht, auch die view muss länger leben! Ebenso der Timer.
C++ Grundlagen, wie Christian schon sagte.

Außerdem erbst du von QWidget, machst dann ein "setCentralView()" im Konstruktor. QWidget bietet diese Methode nicht, und du selber bietest sie auch nicht an - wo kommt die her?

Zu guter letzt:
In C++ includiert man nicht "math.h" sondern "cmath". math.h ist deprecated, standardkonform ist cmath.

Verfasst: 14. Juli 2011 10:52
von hardi
Vielen Dank für eure Hinweise. Sie haben mir sehr weiter geholfen. Nach einem Programmupdate laufen die Mäuse nun umher.

Zu Euren Anmerkungen:
- setCentralView() war ein Artefakt meiner Ausprobiererei und ist nun aus dem Code verschwunden!
- include <cmath> macht mir auch mehr Sinn als include <math.h>. Ich habe diesen Code vom offiziellen Qt Example kopiert, somit liegt der "Fehler" eindeutig im Qt Beispiel selbst begraben.

Für mich bleibt nur noch eine offene Frage:
Warum öffnen sich 2 Fenster statt einem? Fenster 1 hat den Titel "collidingmice" und ist ohne Maus-Anzeige. Fenster 2 trägt den Titel "Colliding mice" mit Inhalt umherirrender Mäuse. Fenster 1 ist überflüssig und soll weg.

Vielen Dank für Eure Hilfe!!!

Verfasst: 14. Juli 2011 10:59
von hardi
Ich habe es durch Ausprobieren selbst herausgefunden:
Fenster1 öffnet sich wegen dem Befehl

Code: Alles auswählen

window.show();
Ist dieser auskommentiert, dann funktioniert das Programm wie gewünscht.

Danke nochmals für eure Hilfe. Ihr wart echt super! :lol:

Verfasst: 14. Juli 2011 14:38
von hardi
Eine weitere Frage zu diesem Beispiel:
Wie kann ich mir die Mauskoordinaten vom MousePressEvent bezogen auf die gesamte Szene ausgeben lassen? Ich habe nur die Möglichkeit gefunden für in der Szene vorhandene Items ... bezogen auf das Mäuse-Beispiel möchte ich mit einem beliebigen Click (nicht nur auf Mäuse) die Koordinaten meiner Computermaus erhalten.
Ich hoffe, ihr könnt mir nochmal helfen!!!
Viele Grüße,
hardi

Verfasst: 15. Juli 2011 08:36
von hardi
Ich habe das Problem selbst gelöst!
Einfach ein großes Hintergrundobjekt in der Szene einfügen und dann dessen scenePos() - Koordinaten zu dessen Computermaus pos() - Koordinaten addieren.
Danke nochmals für eure Mithilfe.