QtQuick矩形中心缩放与鼠标定位异常问题求助
QtQuick矩形中心缩放+鼠标定位问题解决
问题现象
- 注释
translate代码时:缩放生效,但矩形以左上角为原点缩放,而非中心 - 取消注释
translate代码时:缩放以中心进行,但矩形完全偏离鼠标点击位置
原因拆解
坐标转换逻辑混乱
你在mousePressEvent中先把鼠标像素坐标转成逻辑坐标m_x/m_y,又额外计算m_x1/m_y1 = m_x * m_rate / m_scale,相当于把逻辑坐标转成了缩放后的像素坐标,但后续绘制时叠加了世界变换和局部缩放,导致坐标完全错位。缩放平移的坐标基准错误
执行painter->translate(center)时,center是基于错误的m_x1/m_y1计算的,缩放后再平移回去,给矩形额外加了一次偏移,自然偏离鼠标位置。世界变换的作用没理清
你设置的trans矩阵已经完成逻辑坐标→像素坐标的映射:- 逻辑原点映射到控件中心(512,384)
- y轴反转(适配Qt像素坐标y向下的特性)
m_rate是逻辑单位到像素的基础缩放比例(51.2)
解决方案
1. 修正鼠标坐标存储
直接存储鼠标对应的逻辑坐标,无需提前计算缩放后的坐标:
void EaDrawArea::mousePressEvent(QMouseEvent *event) { // 像素坐标转逻辑坐标,这一步逻辑正确 m_x = (event->x() - 512.0) / m_rate; m_y = -(event->y() - 384.0) / m_rate; // 删除m_x1/m_y1的计算,直接用m_x/m_y作为矩形逻辑位置 this->update(); }
2. 重写paint函数的变换逻辑
先应用世界变换,再围绕矩形中心做局部缩放:
void EaDrawArea::paint(QPainter* painter) { painter->setRenderHint(QPainter::Antialiasing, true); painter->resetTransform(); // 先设置世界变换:完成逻辑坐标到像素坐标的映射 QTransform trans; trans.setMatrix(m_rate, 0.0, 0.0, 0.0, -m_rate, 0.0, 512.0, 384.0, 1.0); painter->setWorldTransform(trans); painter->save(); QPen redPen(Qt::red); redPen.setWidth(1); redPen.setCosmetic(true); painter->setPen(redPen); // 基于逻辑坐标创建矩形,初始大小为逻辑单位的10x5 QRectF rect(m_x, m_y, 10, 5); QPointF center = rect.center(); // 正确的中心缩放流程:平移到中心→缩放→平移回原点 painter->translate(center); painter->scale(m_scale, m_scale); painter->translate(-center); painter->drawRect(rect); painter->restore(); }
3. 修复QML的小错误
DrawingArea中的focus: trues多了个s,修正为:
DrawingArea { id: drawarea focus: true // 其他代码保持不变 }
核心逻辑说明
- 世界变换负责底层坐标映射,把逻辑坐标转换成控件上的像素位置
- 局部缩放在逻辑坐标层面进行,通过「平移-缩放-平移」的顺序,实现以矩形中心为原点的缩放
- 鼠标坐标直接用逻辑坐标存储,避免多次转换导致的错位
内容的提问来源于stack exchange,提问作者James Hao
相关产品推荐
相关产品推荐

