我有两个问题:
deviceTransform是应用于视图的转换,如果场景中包含忽略转换的项目,则需要提供该转换。
这是我的代码:
import sys
from PyQt5.QtGui import QTransform
from PyQt5.QtWidgets import QApplication, QGraphicsItem, QGraphicsScene, QGraphicsView
class Demo(QGraphicsView):
def __init__(self):
super(Demo, self).__init__()
self.resize(300, 300)
self.scene = QGraphicsScene()
self.scene.setSceneRect(0, 0, 300, 300)
self.rect = self.scene.addRect(100, 30, 100, 30)
self.ellipse = self.scene.addEllipse(100, 80, 50, 40)
self.rect.setFlags(QGraphicsItem.ItemIsMovable | QGraphicsItem.ItemIsSelectable)
self.ellipse.setFlags(QGraphicsItem.ItemIsMovable | QGraphicsItem.ItemIsSelectable)
self.setScene(self.scene)
# Question 1
print(self.scene.itemAt(110, 40, QTransform()))
# Question 2
self.scene.focusItemChanged.connect(self.my_slot)
def my_slot(self, new_item, old_item):
print(new_item)
print(old_item)
if __name__ == '__main__':
app = QApplication(sys.argv)
demo = Demo()
demo.show()
sys.exit(app.exec_())
任何帮助将不胜感激。
答案 0 :(得分:1)
1。 QTransform()在itemAt()中是什么意思?
由于它指示文档,只有在存在忽略转换的项目时才需要传递deviceTransform,那么如何进行操作以使该项目不支持转换?您必须启用标志Qt::ItemIgnoresTransformations
。
对于您的代码,您看不到差异,因此我实现了以下示例,其中有2个项目,其中一个项目的标志ItemIgnoresTransformations被激活,而另一个则没有。然后,当您按下任何项目时,预期该项目将在控制台中打印,但是如果您通过QTransform(),并且按下单选按钮以通过viewportTransform,则您将看到具有ItemIgnoresTransformations标志的项目返回None。 (),您将看到现在这两个项目都已打印在控制台上。因此,如果有任何启用了标志ItemIgnoresTransformations的项目,则必须通过deviceTransform。
import sys
from PyQt5 import QtCore, QtGui, QtWidgets
class Demo(QtWidgets.QGraphicsView):
def __init__(self):
super(Demo, self).__init__()
self._scene = QtWidgets.QGraphicsScene()
self._scene.setSceneRect(0, 0, 300, 300)
self.setScene(self._scene)
self.rect1 = self._scene.addRect(
100, 30, 100, 30, brush=QtGui.QBrush(QtGui.QColor("red"))
)
self.rect1.setFlag(QtWidgets.QGraphicsItem.ItemIgnoresTransformations)
self.rect2 = self._scene.addRect(
200, 30, 100, 30, brush=QtGui.QBrush(QtGui.QColor("green"))
)
self.rotate(50)
self._use_deviceTransform = False
def mousePressEvent(self, event):
sp = self.mapToScene(event.pos())
item = self._scene.itemAt(
sp,
self.viewportTransform()
if self._use_deviceTransform
else QtGui.QTransform(),
)
print(item)
def set_use_deviceTransform(self, t):
self._use_deviceTransform = t
if __name__ == "__main__":
app = QtWidgets.QApplication(sys.argv)
radiobutton = QtWidgets.QRadioButton("use deviceTransform")
demo = Demo()
radiobutton.toggled.connect(demo.set_use_deviceTransform)
w = QtWidgets.QWidget()
lay = QtWidgets.QVBoxLayout(w)
lay.addWidget(radiobutton)
lay.addWidget(demo)
w.show()
w.resize(640, 480)
sys.exit(app.exec_())
2。为什么focusItemChanged信号不起作用?
如果项目的焦点发生变化,则会触发信号,但是默认情况下,项目没有焦点,因此不会发出信号,解决方案是激活标志QGraphicsItem::ItemIsFocusable
:
import sys
from PyQt5.QtGui import QTransform
from PyQt5.QtWidgets import QApplication, QGraphicsItem, QGraphicsScene, QGraphicsView
from PyQt5.QtCore import pyqtSlot, Qt
class Demo(QGraphicsView):
def __init__(self):
super(Demo, self).__init__()
self.resize(300, 300)
self.scene = QGraphicsScene()
self.scene.setSceneRect(0, 0, 300, 300)
self.rect = self.scene.addRect(100, 30, 100, 30)
self.ellipse = self.scene.addEllipse(100, 80, 50, 40)
self.rect.setFlags(
QGraphicsItem.ItemIsMovable
| QGraphicsItem.ItemIsSelectable
| QGraphicsItem.ItemIsFocusable
)
self.ellipse.setFlags(
QGraphicsItem.ItemIsMovable
| QGraphicsItem.ItemIsSelectable
| QGraphicsItem.ItemIsFocusable
)
self.setScene(self.scene)
self.scene.focusItemChanged.connect(self.my_slot)
@pyqtSlot("QGraphicsItem*", "QGraphicsItem*", Qt.FocusReason)
def my_slot(self, new_item, old_item, reason):
print(old_item, new_item)