Мой класс C ++ Qt 4.8.1 для рисования перекрестия подклассов QGraphicsItem и реализует его paint () и boundingRect (). Метод paint () состоит из двух вызовов drawLine () и одного вызова drawText (). Источник находится в центре. boundingRect () также учитывает эти координаты (-, -, +, +), а также половину ширины пера в каждом направлении.
При создании, перемещении (или позиционировании) и последующем добавлении объекта в (видимую) сцену вид сдвигается на несколько пикселей, так что содержимое сцены немного перемещается в правый нижний угол. Если boundingRect () возвращает пустой QRectF (), этого сдвига не происходит.
- дополнительные элементы не вызывают дальнейшего движения сцены.
- предыдущее обновление () сцены не меняет поведения
- больший размер boundingRect, кажется, увеличивает движение
- изменение преобразования представления не меняет поведения
itemChange () вызывается много раз, но, похоже, не дает подсказки (на мой взгляд):
Crosshair::Crosshair being created, id= "1" at QPointF(63.6, 88.487) scenePos= QPointF(33.6, 58.487)
Crosshair::Crosshair position QPointF(63.6, 88.487)
Crosshair::itemChange ItemFlagsChange QVariant(uint, 1)
Crosshair::itemChange ItemFlagsHaveChanged QVariant(uint, 1)
Crosshair::itemChange ItemFlagsChange QVariant(uint, 33)
Crosshair::itemChange ItemFlagsHaveChanged QVariant(uint, 33)
Crosshair::itemChange ItemFlagsChange QVariant(uint, 2081)
Crosshair::itemChange ItemFlagsHaveChanged QVariant(uint, 2081)
[...]
Crosshair::itemChange ItemPositionChange QVariant(QPointF, QPointF(63.6, 88.487) )
Crosshair::itemChange ItemPositionHasChanged QVariant(QPointF, QPointF(63.6, 88.487) )
Crosshair::itemChange ItemSceneChange QVariant(QGraphicsScene*, )
Crosshair::itemChange ItemSceneHasChanged QVariant(QGraphicsScene*, )
[...]
Crosshair::boundingRect 20 3 QRectF(-11.5,-11.5 21.5x21.5)
Crosshair::boundingRect 20 3 QRectF(-11.5,-11.5 21.5x21.5)
Crosshair::itemChange ItemVisibleChange QVariant(bool, true)
Crosshair::itemChange ItemVisibleHasChanged QVariant(bool, true)
Crosshair::boundingRect 20 3 QRectF(-11.5,-11.5 21.5x21.5)
Crosshair::boundingRect 20 3 QRectF(-11.5,-11.5 21.5x21.5)
...
Возможно, завтра я смогу создать минимальный пример, но, возможно, кто-то сможет угадать мою ошибку даже по этому общему описанию проблемы. В качестве альтернативы, конечно же, приветствуются намеки на дальнейшую отладку!
Изменить Спасибо, Риатеш за совет. Некоторые дальнейшие результаты отладки показывают, что sceneRect () действительно изменен, он расширяет точно размер ограничивающего прямоугольника перекрестия, например с
QRectF(0,0 1680x636)
до QRectF(-11.5,-11.5 1691.5x647.5)
. ItemsBoundingRect сцены остается прежним. Я не упомянул ранее, что вид был масштабирован / преобразован с помощью fitInView(scene()->itemsBoundingRect(), Qt::KeepAspectRatio);
, и заметил, что сдвига действительно не происходит, когда сцена просматривается на 100% (например, resetTransform()
). Но я до сих пор не понимаю, как / почему меняется sceneRect (), когда я добавляю элемент в boundingRect (). Это должно быть связано с моей пользовательской реализацией, потому что добавление эллипса не вызывает сдвига сцены / вида. Хорошо, начнем: я также не упомянул, что использую setFlag(QGraphicsItem::ItemIgnoresTransformations);
, чтобы прицел оставался одинакового размера независимо от масштаба. Это, по-видимому, приводит к тому, что boundingrect "остается" в исходной точке сцены при добавлении, и игнорирует setPos ().
Продолжение следует ...