Finden Sie die Bildschirmposition ein QGraphicsItem

Anwendungsfall: sollte Dies ein Recht häufiges problem. In einem normalen QMainWindow mit QMdiArea Leben ein mdiChild mit QGraphicsView. Diese Ansicht zeigt eine QGraphicsScene mit QGraphicsItems innen. Ein rechts-Klick auf einen dieser Einträge auswählt (konzentriert sich) auf das Element und öffnet ein Kontext-Menü, das bequem auf den Bildschirm-Koordinaten QGraphicsSceneMouseEvent::screenPos(). Dies funktioniert wie erwartet.

Nun möchte ich zeigen das gleiche Kontext-Menü, wenn der Benutzer eine Taste drückt (z.B. Qt::Key_Menu). Ich weiß, das ausgewählt (fokussiert) posten, ich weiß, die Ansicht, die zeigt die Szene.

Also meine Frage ist:

Was ist der richtige Weg, um die position (in globalen Bildschirmkoordinaten) der sichtbaren Darstellung einer QGraphicsItem innerhalb einer Szene?

Hier ist was nicht funktioniert:

QGraphicsItem *item = ...; //is the currently selected item next to which the context menu shall be opened
QGraphicsScene *scene = ...; //is the scene that hosts the item
QGraphicsView *graphicsView = ...; //is the view displaying the scene, this inherits from QWidget

//get the position relative to the scene
QPointF sp = item->scenePos();
//or use
QPointF sp = item->mapToScene(item->pos());

//find the global (screen) position of the item
QPoint global = graphicsView->mapToGlobal(graphicsView->mapFromScene(sp));

//now
myContextMenu.exec(global);
//should open the context menu at the top left corner of the QGraphicsItem item, but it goes anywhere

Der doc sagt:
Wenn Sie wissen wollen, wo sich im Ansichtsfenster ein Objekt befindet, können Sie rufen Sie QGraphicsItem::mapToScene() auf das Element, dann QGraphicsView::mapFromScene() auf die Ansicht.

Das ist genau das, was ich Tue, richtig?


Stolperte über ein thread in einem deutschen forum, die Hinweise auf:

QGraphicsView *view = item->scene()->views().last();

oder noch schöner:

QGraphicsView *view;
foreach (view,  this->scene()->views())
{
    if (view->underMouse() || view->hasFocus()) break;
}
//(use case in the forum thread:) //QMenu *menu = new QMenu(view);

Verwenden, die es erlauben würde, eine mehr generalisierte Antwort auf meine Frage...

  • Ich war über eine Antwort zu posten, aber aus re-Lektüre des docs-ich glaube, ich Stimme mit Ihrer Analyse: QGraphicsView::mapFromScene geben soll viewport-Koordinaten (lohnt sich). Wäre nur die Frage, ob es eine latente Fehler in mapToGlobal auf widgets innerhalb von MDI-Kinder.
  • Also, was wäre Ihre erste Vermutung (die Sie geschrieben haben, in der Antwort)?
Schreibe einen Kommentar