Python QGraphicsItemGroup';在它被销毁后发送的翻译?

Python QGraphicsItemGroup';在它被销毁后发送的翻译?,python,pyqt,pyqt5,qgraphicsitemgroup,Python,Pyqt,Pyqt5,Qgraphicsitemgroup,我在场景中有QGraphicsItem对象,我使用QGraphicsItemGroup共同移动这些对象,如所示 当团队还活着时,它会保持自己的转换。现在,一旦它被破坏,这些转换就不再存在,必须被分派。我的问题是如何做到这一点——特别是在翻译方面 我做了一个小例子,其中显示一个矩形,然后在暂停5秒后缩放和转换。对象的变换将在每个步骤后显示 from PyQt5.QtCore import Qt, QThread from PyQt5.QtGui import QTransform from PyQ

我在场景中有
QGraphicsItem
对象,我使用
QGraphicsItemGroup
共同移动这些对象,如所示

当团队还活着时,它会保持自己的转换。现在,一旦它被破坏,这些转换就不再存在,必须被分派。我的问题是如何做到这一点——特别是在翻译方面

我做了一个小例子,其中显示一个矩形,然后在暂停5秒后缩放和转换。对象的变换将在每个步骤后显示

from PyQt5.QtCore import Qt, QThread
from PyQt5.QtGui import QTransform
from PyQt5.QtWidgets import QApplication, QGraphicsRectItem, QGraphicsScene, QGraphicsView, QMainWindow
import sys
import time


def print_transforms(obj):
  t = obj.transform()
  print(t.m11(), t.m12(), t.m13(), t.m21(), t.m22(), t.m23(), t.m31(), t.m32(), t.m33(), t.dx(), t.dy())
  assert len(obj.transformations()) == 0
  print(obj.rotation(), obj.scale())


class Thread(QThread):

  def run(self):
    print('initial transforms')
    print_transforms(rect)
    time.sleep(5)

    group = scene.createItemGroup([rect])
    group.setTransform(QTransform().scale(1.5, 1.5))
    scene.destroyItemGroup(group)
    print('after scaling')
    print_transforms(rect)
    time.sleep(5)

    group = scene.createItemGroup([rect])
    group.setTransform(QTransform().translate(100., 100.))
    scene.destroyItemGroup(group)
    print('after translation')
    print_transforms(rect)
    time.sleep(5)


app = QApplication([])
window = QMainWindow()
window.setGeometry(100, 100, 400, 400)
view = QGraphicsView()
scene = QGraphicsScene()
view.setHorizontalScrollBarPolicy(Qt.ScrollBarAlwaysOff)
view.setVerticalScrollBarPolicy(Qt.ScrollBarAlwaysOff)

rect = QGraphicsRectItem(0, 0, 150, 150)
scene.addItem(rect)

view.setScene(scene)
window.setCentralWidget(view)
window.show()
thread = Thread()
thread.finished.connect(app.exit)
thread.start()
sys.exit(app.exec_())
它打印以下内容:

PyQt5.QtCore.QPointF()
initial transforms
1.0 0.0 0.0 0.0 1.0 0.0 0.0 0.0 1.0 0.0 0.0
0.0 1.0
PyQt5.QtCore.QPointF()
after scaling
1.5 0.0 0.0 0.0 1.5 0.0 0.0 0.0 1.0 0.0 0.0
0.0 1.0
PyQt5.QtCore.QPointF()
PyQt5.QtCore.QPointF()
PyQt5.QtCore.QPointF()
after translation
1.5 0.0 0.0 0.0 1.5 0.0 0.0 0.0 1.0 0.0 0.0
0.0 1.0
PyQt5.QtCore.QPointF(100.0, 100.0)
初始转换
1.0 0.0 0.0 0.0 1.0 0.0 0.0 0.0 1.0 0.0 0.0
0.0 1.0
缩放后
1.5 0.0 0.0 0.0 1.5 0.0 0.0 0.0 1.0 0.0 0.0
0.0 1.0
翻译后
1.5 0.0 0.0 0.0 1.5 0.0 0.0 0.0 1.0 0.0 0.0
0.0 1.0
因此,我们从一个单位变换矩阵开始,在缩放之后,它被更改为一个缩放矩阵来保持缩放因子

但是,在平移之后,变换矩阵不会改变,尽管矩形确实已经移动了


因此,我的问题是,组的翻译在销毁后发送到哪里?

首先不要使用QThread+sleep进行延迟,因为您可能有奇怪的行为,Qt会通过指向控制台上的警告来提醒您:

initial transforms
1.0 0.0 0.0 0.0 1.0 0.0 0.0 0.0 1.0 0.0 0.0
0.0 1.0
QObject::startTimer: Timers cannot be started from another thread
QObject::startTimer: Timers cannot be started from another thread
after scaling
1.5 0.0 0.0 0.0 1.5 0.0 0.0 0.0 1.0 0.0 0.0
0.0 1.0
QObject::startTimer: Timers cannot be started from another thread
QObject::startTimer: Timers cannot be started from another thread
after translation
1.5 0.0 0.0 0.0 1.5 0.0 0.0 0.0 1.0 0.0 0.0
0.0 1.0
你会得到以下结果:

PyQt5.QtCore.QPointF()
initial transforms
1.0 0.0 0.0 0.0 1.0 0.0 0.0 0.0 1.0 0.0 0.0
0.0 1.0
PyQt5.QtCore.QPointF()
after scaling
1.5 0.0 0.0 0.0 1.5 0.0 0.0 0.0 1.0 0.0 0.0
0.0 1.0
PyQt5.QtCore.QPointF()
PyQt5.QtCore.QPointF()
PyQt5.QtCore.QPointF()
after translation
1.5 0.0 0.0 0.0 1.5 0.0 0.0 0.0 1.0 0.0 0.0
0.0 1.0
PyQt5.QtCore.QPointF(100.0, 100.0)
当使用
destroyItemGroup()
时,可以看到转换应用于项目的位置,而不是
q转换
,这表明:

将组中的所有项重新分配到组的父项,然后删除 组,并最终将其删除项目的位置和位置 转换从组映射到组的父级。

(强调矿山)

总之:当组被销毁时,所有的转换都会传递给项目,除了转换,因为项目是使用setPos移动的