Hello,
Im fairly new to the GraphicsScene and GraphicsView in PyQt5, im trying to wrap my head around how to use it efficiently, and i have just bumped into an issue.
I am looking for a way to change the default mousebutton that moves the items in the GraphicsView.
This is the way i would like the graphicsScene UI to work :
LeftMouse button click on Item = ItemClick signal (like a regular button widget would do)
RightMouse button click on Item = ItemLeftClick signal (open a context menu with a few options specific to the item)
RightMouse button click on Empty space = Open's context menu for GraphicsView (so far so good).
#here
LeftMouse button click on Empty space and drag select rubberband = This Can stay as currently is, clears selection on click then it selects any of the items inside the rubberband rectangle on mouse click release.
MiddleMouse button drag = If items selected, i want this button to be moving my items position.
so far im kinda unable to do this..
this is a snippet of my current mouse logic inside the QtWidgets.QGraphicsView class , im not sure what i would need to do to replace the default leftMouse drag behaviour.
def mousePressEvent(self, event):
if event.button() == QtCore.Qt.MiddleButton and event.modifiers() == QtCore.Qt.AltModifier:
self.drag = True
self.prev_pos = event.pos()
self.setCursor(QtCore.Qt.SizeAllCursor)
elif event.button() == QtCore.Qt.LeftButton:
# This does not work as i wanted, it is only changing the mouse icon
elif event.button() == QtCore.Qt.MiddleButton:
# set hand icon..
self.
setDragMode(QtWidgets.
QGraphicsView.
DragMode.
ScrollHandDrag) # print selected item position in scene.
for x in self.scene().selectedItems() :
print( x.scenePos() )
super(View, self).mousePressEvent(event)
def mouseMoveEvent(self, event):
if self.drag:
new_scale = self.matrix().m11()
delta = (self.mapToScene(event.pos()) - self.mapToScene(self.prev_pos)) * -1.0 * new_scale
center
= QtCore.
QPoint(self.
viewport().
width() / 2 + delta.
x(), self.
viewport().
height() / 2 + delta.
y()) new_center = self.mapToScene(center)
self.centerOn(new_center)
self.prev_pos = event.pos()
return
super(View, self).mouseMoveEvent(event)
def mouseReleaseEvent(self, event):
if self.drag:
self.drag = False
self.setCursor(QtCore.Qt.ArrowCursor)
super(View, self).mouseReleaseEvent(event)
if event.button() == QtCore.Qt.RightButton:
# Context Menu
save = menu.addAction('save')
load = menu.addAction('load')
selectedAction = menu.exec_(event.globalPos())
if selectedAction == save:
common.scene_save(self)
if selectedAction == load:
common.scene_load(self)
def mousePressEvent(self, event):
if event.button() == QtCore.Qt.MiddleButton and event.modifiers() == QtCore.Qt.AltModifier:
self.setDragMode(QtWidgets.QGraphicsView.NoDrag)
self.drag = True
self.prev_pos = event.pos()
self.setCursor(QtCore.Qt.SizeAllCursor)
elif event.button() == QtCore.Qt.LeftButton:
self.setDragMode(QtWidgets.QGraphicsView.RubberBandDrag)
# This does not work as i wanted, it is only changing the mouse icon
elif event.button() == QtCore.Qt.MiddleButton:
# set hand icon..
self.setDragMode(QtWidgets.QGraphicsView.DragMode.ScrollHandDrag)
# print selected item position in scene.
for x in self.scene().selectedItems() :
print( x.scenePos() )
super(View, self).mousePressEvent(event)
def mouseMoveEvent(self, event):
if self.drag:
new_scale = self.matrix().m11()
delta = (self.mapToScene(event.pos()) - self.mapToScene(self.prev_pos)) * -1.0 * new_scale
center = QtCore.QPoint(self.viewport().width() / 2 + delta.x(), self.viewport().height() / 2 + delta.y())
new_center = self.mapToScene(center)
self.centerOn(new_center)
self.prev_pos = event.pos()
return
super(View, self).mouseMoveEvent(event)
def mouseReleaseEvent(self, event):
if self.drag:
self.drag = False
self.setCursor(QtCore.Qt.ArrowCursor)
super(View, self).mouseReleaseEvent(event)
if event.button() == QtCore.Qt.RightButton:
# Context Menu
menu = QtWidgets.QMenu()
save = menu.addAction('save')
load = menu.addAction('load')
selectedAction = menu.exec_(event.globalPos())
if selectedAction == save:
common.scene_save(self)
if selectedAction == load:
common.scene_load(self)
To copy to clipboard, switch view to plain text mode
Bookmarks