我有一个自定义的QGraphicsItem实现。我需要能够限制项目的移动位置 - 即e。将其限制在某个区域。当我检查Qt文档时,这就是它的建议:
QVariant Component::itemChange(GraphicsItemChange change, const QVariant &value)
{
if (change == ItemPositionChange && scene()) {
// value is the new position.
QPointF newPos = value.toPointF();
QRectF rect = scene()->sceneRect();
if (!rect.contains(newPos)) {
// Keep the item inside the scene rect.
newPos.setX(qMin(rect.right(), qMax(newPos.x(), rect.left())));
newPos.setY(qMin(rect.bottom(), qMax(newPos.y(), rect.top())));
return newPos;
}
}
return QGraphicsItem::itemChange(change, value);
}
所以基本上,检查传递给itemChange的位置,如果你不喜欢它,改变它并返回新值。
看起来很简单,除了它实际上没有用。当我检查调用堆栈时,我看到从QGraphicsItem :: setPos调用了itemChange,但它甚至没有查看返回值。所以没有任何目的让我返回一个改变的位置,没有人在看它。请参阅QGraphicsItem.cpp
中的代码// Notify the item that the position is changing.
const QVariant newPosVariant(itemChange(ItemPositionChange, qVariantFromValue<QPointF>(pos)));
QPointF newPos = newPosVariant.toPointF();
if (newPos == d_ptr->pos)
return;
// Update and repositition.
d_ptr->setPosHelper(newPos);
// Send post-notification.
itemChange(QGraphicsItem::ItemPositionHasChanged, newPosVariant);
d_ptr->sendScenePosChange();
有什么建议吗?我希望避免使用鼠标按下鼠标移动等来重新实现整个点击和拖动行为......但是我想如果我找不到更好的主意我将不得不这样做。
答案 0 :(得分:4)
我实际上没有尝试过,但它看起来正在检查返回位置。返回的受限位置在newPosVariant
的构造函数中用于转换为newPos
。然后,它用于设置项目的位置,如果它与当前项目的位置不同。