optimize editor route preview synchronization;add preview zoom

This commit is contained in:
baiYue 2026-06-01 16:26:02 +08:00
parent 8fa87baafc
commit ba2fb8211f
12 changed files with 235 additions and 260 deletions

View File

@ -2,6 +2,7 @@ project(diagramCavas)
set(DIAGRAMCAVAS_HEADER_FILES
include/baseScene.h
include/baseView.h
include/designerScene.h
include/designerView.h
include/diagramCavas.h
@ -168,6 +169,7 @@ set(DIAGRAMCAVAS_HEADER_FILES
set(DIAGRAMCAVAS_SOURCE_FILES
source/baseScene.cpp
source/baseView.cpp
source/designerScene.cpp
source/designerView.cpp
source/diagramCavas.cpp

View File

@ -0,0 +1,41 @@
#ifndef BASEVIEW_H
#define BASEVIEW_H
#include <QGraphicsView>
class BaseView : public QGraphicsView
{
Q_OBJECT
public:
explicit BaseView(QWidget *parent = 0);
virtual ~BaseView();
virtual void initialize();
//视图操作-外部调用
void zoomIn();
void zoomOut();
void zoomFit();
protected:
virtual void mousePressEvent(QMouseEvent*) override;
virtual void mouseMoveEvent(QMouseEvent*) override;
virtual void mouseReleaseEvent(QMouseEvent*) override;
virtual void wheelEvent(QWheelEvent*) override;
protected:
//视图操作相关
void zoom(const QPointF&, double);
bool zoomLimit(double&);
double getScaleFactor();
void translate(const QPointF&);
signals:
void onScaleChanged(double d);
protected:
bool m_bMousePress;
double m_dScale;
QPointF m_ptLatstMouse_view; //鼠标最后按下在view中的位置
int m_nLevel;
};
#endif

View File

@ -1,9 +1,9 @@
#ifndef DESIGNER_VIEW_H
#define DESIGNER_VIEW_H
#include <QGraphicsView>
#include "baseView.h"
class DesignerView : public QGraphicsView
class DesignerView : public BaseView
{
Q_OBJECT
@ -11,31 +11,7 @@ public:
explicit DesignerView(QWidget *parent = 0);
virtual ~DesignerView();
//视图操作-外部调用
void zoomIn();
void zoomOut();
void zoomFit();
protected:
//virtual void contextMenuEvent(QContextMenuEvent*) override;
virtual void mousePressEvent(QMouseEvent*) override;
virtual void mouseMoveEvent(QMouseEvent*) override;
virtual void mouseReleaseEvent(QMouseEvent*) override;
virtual void wheelEvent(QWheelEvent*) override;
private:
void initialize();
//视图操作相关
void zoom(const QPointF&, double);
bool zoomLimit(double&);
double getScaleFactor();
void translate(const QPointF&);
signals:
void onScaleChanged(double d);
private:
bool m_bMousePress;
double m_dScale;
QPointF m_ptLatstMouse_view; //鼠标最后按下在view中的位置
int m_nLevel;
void initialize() override;
};
#endif

View File

@ -1,9 +1,9 @@
#ifndef EDITVIEW_H
#define EDITVIEW_H
#include <QGraphicsView>
#include "baseView.h"
class EditView : public QGraphicsView
class EditView : public BaseView
{
Q_OBJECT
public:

View File

@ -28,10 +28,11 @@ BaseDrawingPanel::BaseDrawingPanel(PowerEntity* pEntity,QWidget *parent,DiagramM
m_pSelectorManager = new SelectorManager(_pModel,this);
m_pGraphicsScene = new DesignerScene(_pModel,this);
//设置场景大小.前两个参数为scene的坐标远点设置到view的中心点后无论view如何缩放secne的坐标原点都不会动方便后续的位置计算
m_pGraphicsScene->setSceneRect(0,0, Constants::SCENE_WIDTH*4, Constants::SCENE_HEIGHT*4);
m_pGraphicsScene->setSceneRect(0,0, Constants::SCENE_WIDTH*6, Constants::SCENE_HEIGHT*6);
m_pGraphicsScene->setGridVisible(true);
m_pGraphicsView = new DesignerView(this);
m_pGraphicsView->initialize();
m_pGraphicsView->setScene(m_pGraphicsScene);
m_pGraphicsView->setViewportUpdateMode(QGraphicsView::FullViewportUpdate);
m_pGraphicsScene->setView(m_pGraphicsView);

View File

@ -0,0 +1,171 @@
#include "baseView.h"
#include <QMouseEvent>
#define MAX_ZoomValue 50.0
#define MIN_ZoomValue 0.02
BaseView::BaseView(QWidget *parent)
: QGraphicsView(parent)
{
m_bMousePress = false;
m_dScale = 1.0;
initialize();
m_nLevel = 10;
this->setFocusPolicy(Qt::ClickFocus);
}
BaseView::~BaseView()
{
}
void BaseView::initialize()
{
}
void BaseView::mousePressEvent(QMouseEvent* event)
{
QGraphicsItem* item = scene()->itemAt(mapToScene(event->pos()), transform());
if (event->button() == Qt::MiddleButton /*&& !item*/) //在空白处按住中键进行拖动
{
m_bMousePress = true;
setCursor(Qt::ClosedHandCursor);
m_ptLatstMouse_view = event->pos();
}
else
QGraphicsView::mousePressEvent(event);
}
void BaseView::mouseMoveEvent(QMouseEvent* event)
{
if(m_bMousePress)
{
QPointF mouseMoveLength = event->pos() - m_ptLatstMouse_view.toPoint();
translate(mouseMoveLength);
m_ptLatstMouse_view = event->pos();
}
else
QGraphicsView::mouseMoveEvent(event);
}
void BaseView::mouseReleaseEvent(QMouseEvent* event)
{
if (event->button() == Qt::MiddleButton) //按住中键进行拖动
{
m_bMousePress = false;
setCursor(Qt::ArrowCursor);
}
else
QGraphicsView::mouseReleaseEvent(event);
}
void BaseView::wheelEvent(QWheelEvent* event) //滚轮进行放大缩小
{
QPointF mousePos = event->position();
double angleDeltaY = event->angleDelta().y();
double zoomFactor = qPow(1.0015, angleDeltaY); //可以实现更平滑的缩放
zoom(mousePos, zoomFactor);
//注意不要调用基类的滚轮函数,否则滚轮事件会映射到滚动条操作
//QGraphicsView::wheelEvent(event);
}
double BaseView::getScaleFactor()
{
//QTransform为一个3*3的矩阵m11和m22元素分别为水平和垂直的缩放值
return this->transform().m11();
}
bool BaseView::zoomLimit(double& value)
{
m_dScale *= value;
if(m_dScale >= MAX_ZoomValue)
{
m_dScale = MAX_ZoomValue;
value = m_dScale / getScaleFactor();
}
else if(m_dScale <= MIN_ZoomValue)
{
m_dScale = MIN_ZoomValue;
value = m_dScale / getScaleFactor();
}
if(qFabs(value - 1) < 0.01) //缩放因子近似为1
return true;
if(value > 1)
m_nLevel +=1;
else
m_nLevel -=1;
emit onScaleChanged(m_nLevel);
return false;
}
void BaseView::zoom(const QPointF& mousePos, double zoomFactor)
{
if(zoomLimit(zoomFactor))
return;
/*
* QGraphicsView的默认transformationAnchor()AnchorViewCenter,
* AnchorUnderMouse可以实现(translate)NoAnchor,
*/
ViewportAnchor lastAnchor = this->transformationAnchor();
setTransformationAnchor(QGraphicsView::NoAnchor);
QPointF targetScenePos = mapToScene(mousePos.toPoint());
QTransform trans = transform();
trans.translate(targetScenePos.x(), targetScenePos.y());
trans.scale(zoomFactor, zoomFactor);
trans.translate(-targetScenePos.x(), -targetScenePos.y());
setTransform(trans);
setTransformationAnchor(lastAnchor);
}
void BaseView::zoomIn()
{
//以view的中心点作为放大中心
double dWidth_View = viewport()->width();
double dHeight_View = viewport()->height();
QPoint pt(dWidth_View * 0.5, dHeight_View * 0.5);
zoom(pt, 1.1);
}
void BaseView::zoomOut()
{
//以view的中心点作为缩小中心
double dWidth_View = viewport()->width();
double dHeight_View = viewport()->height();
QPoint pt(dWidth_View * 0.5, dHeight_View * 0.5);
zoom(pt, 0.9);
}
void BaseView::zoomFit()
{
resetTransform();
double dWidth_View = viewport()->width();
double dHeight_View = viewport()->height();
double dWidth_Scene = scene()->sceneRect().width();
double dHeight_Scene = scene()->sceneRect().height();
double dWidthScale = dWidth_View / dWidth_Scene;
double dHeightScale = dHeight_View / dHeight_Scene;
m_dScale = qMin(dWidthScale, dHeightScale);
QTransform trans = transform();
trans.scale(m_dScale, m_dScale);
setTransform(trans);
centerOn(0, 0);
}
void BaseView::translate(const QPointF& delta)
{
ViewportAnchor lastAnchor = this->transformationAnchor();
setTransformationAnchor(QGraphicsView::NoAnchor);
QTransform trans = transform();
trans.translate(delta.x(), delta.y());
setTransform(trans);
setTransformationAnchor(lastAnchor);
}

View File

@ -1,19 +1,12 @@
#include "designerView.h"
#include "designerScene.h"
#include <QMouseEvent>
#define MAX_ZoomValue 50.0
#define MIN_ZoomValue 0.02
DesignerView::DesignerView(QWidget *parent)
: QGraphicsView(parent)
: BaseView(parent)
{
m_bMousePress = false;
m_dScale = 1.0;
initialize();
m_nLevel = 10;
this->setFocusPolicy(Qt::ClickFocus);
}
DesignerView::~DesignerView()
{
@ -35,160 +28,3 @@ void DesignerView::initialize()
centerOn(0, 0);
}
/*void DesignerView::contextMenuEvent(QContextMenuEvent* event)
{
/*Q_UNUSED(event);
m_bMousePress = false;
QMenu menu;
QAction *removeAction = menu.addAction(QString::fromWCharArray(L"删除"));
menu.exec(QCursor::pos());
}*/
void DesignerView::mousePressEvent(QMouseEvent* event)
{
QGraphicsItem* item = scene()->itemAt(mapToScene(event->pos()), transform());
if (event->button() == Qt::MiddleButton /*&& !item*/) //在空白处按住中键进行拖动
{
m_bMousePress = true;
setCursor(Qt::ClosedHandCursor);
m_ptLatstMouse_view = event->pos();
}
else
QGraphicsView::mousePressEvent(event);
}
void DesignerView::mouseMoveEvent(QMouseEvent* event)
{
if(m_bMousePress)
{
QPointF mouseMoveLength = event->pos() - m_ptLatstMouse_view.toPoint();
translate(mouseMoveLength);
m_ptLatstMouse_view = event->pos();
}
else
QGraphicsView::mouseMoveEvent(event);
}
void DesignerView::mouseReleaseEvent(QMouseEvent* event)
{
if (event->button() == Qt::MiddleButton) //按住中键进行拖动
{
m_bMousePress = false;
setCursor(Qt::ArrowCursor);
}
else
QGraphicsView::mouseReleaseEvent(event);
}
void DesignerView::wheelEvent(QWheelEvent* event) //滚轮进行放大缩小
{
QPointF mousePos = event->position();
double angleDeltaY = event->angleDelta().y();
double zoomFactor = qPow(1.0015, angleDeltaY); //可以实现更平滑的缩放
zoom(mousePos, zoomFactor);
//注意不要调用基类的滚轮函数,否则滚轮事件会映射到滚动条操作
//QGraphicsView::wheelEvent(event);
}
double DesignerView::getScaleFactor()
{
//QTransform为一个3*3的矩阵m11和m22元素分别为水平和垂直的缩放值
return this->transform().m11();
}
bool DesignerView::zoomLimit(double& value)
{
m_dScale *= value;
if(m_dScale >= MAX_ZoomValue)
{
m_dScale = MAX_ZoomValue;
value = m_dScale / getScaleFactor();
}
else if(m_dScale <= MIN_ZoomValue)
{
m_dScale = MIN_ZoomValue;
value = m_dScale / getScaleFactor();
}
if(qFabs(value - 1) < 0.01) //缩放因子近似为1
return true;
if(value > 1)
m_nLevel +=1;
else
m_nLevel -=1;
emit onScaleChanged(m_nLevel);
return false;
}
void DesignerView::zoom(const QPointF& mousePos, double zoomFactor)
{
if(zoomLimit(zoomFactor))
return;
/*
* QGraphicsView的默认transformationAnchor()AnchorViewCenter,
* AnchorUnderMouse可以实现(translate)NoAnchor,
*/
ViewportAnchor lastAnchor = this->transformationAnchor();
setTransformationAnchor(QGraphicsView::NoAnchor);
QPointF targetScenePos = mapToScene(mousePos.toPoint());
QTransform trans = transform();
trans.translate(targetScenePos.x(), targetScenePos.y());
trans.scale(zoomFactor, zoomFactor);
trans.translate(-targetScenePos.x(), -targetScenePos.y());
setTransform(trans);
setTransformationAnchor(lastAnchor);
//emit onScaleChanged(m_nLevel);
}
void DesignerView::zoomIn()
{
//以view的中心点作为放大中心
double dWidth_View = viewport()->width();
double dHeight_View = viewport()->height();
QPoint pt(dWidth_View * 0.5, dHeight_View * 0.5);
zoom(pt, 1.1);
}
void DesignerView::zoomOut()
{
//以view的中心点作为缩小中心
double dWidth_View = viewport()->width();
double dHeight_View = viewport()->height();
QPoint pt(dWidth_View * 0.5, dHeight_View * 0.5);
zoom(pt, 0.9);
}
void DesignerView::zoomFit()
{
resetTransform();
double dWidth_View = viewport()->width();
double dHeight_View = viewport()->height();
double dWidth_Scene = scene()->sceneRect().width();
double dHeight_Scene = scene()->sceneRect().height();
double dWidthScale = dWidth_View / dWidth_Scene;
double dHeightScale = dHeight_View / dHeight_Scene;
m_dScale = qMin(dWidthScale, dHeightScale);
QTransform trans = transform();
trans.scale(m_dScale, m_dScale);
setTransform(trans);
centerOn(0, 0);
}
void DesignerView::translate(const QPointF& delta)
{
ViewportAnchor lastAnchor = this->transformationAnchor();
setTransformationAnchor(QGraphicsView::NoAnchor);
QTransform trans = transform();
trans.translate(delta.x(), delta.y());
setTransform(trans);
setTransformationAnchor(lastAnchor);
}

View File

@ -304,6 +304,7 @@ void DiagramEditorBayDetailSettingDlg::onOkClicked()
void DiagramEditorBayDetailSettingDlg::onCancelClicked()
{
_pModel->clearCurPreview();
hide();
}
@ -363,6 +364,9 @@ void DiagramEditorBayDetailSettingDlg::onRouteDeleteClicked()
}
}
}
_pModel->clearCurPreview();
showPreview();
}
void DiagramEditorBayDetailSettingDlg::onRouteRbtnClicked(const QPoint &pos)

View File

@ -308,6 +308,8 @@ void DiagramEditorTransDetailSettingDlg::onOkClicked()
void DiagramEditorTransDetailSettingDlg::onCancelClicked()
{
_pModel->clearCurPreview();
showPreview();
hide();
}
@ -353,6 +355,9 @@ void DiagramEditorTransDetailSettingDlg::onRouteDeleteClicked()
}
removeRouteUsageFromDevices(lst,sName);
_transInfo.mapNeutral.value(n).mapRoute.remove(sName); //同步移除数据
_pModel->clearCurPreview();
showPreview();
}
void DiagramEditorTransDetailSettingDlg::onRouteRbtnClicked(const QPoint &pos)

View File

@ -45,7 +45,7 @@ EditPanel::EditPanel(QWidget *parent)
m_pEditScene = new EditScene(this);
m_pEditScene->setModel(_pModel);
//设置场景大小.前两个参数为scene的坐标远点设置到view的中心点后无论view如何缩放secne的坐标原点都不会动方便后续的位置计算
m_pEditScene->setSceneRect(0, 0, Constants::SCENE_WIDTH*4, Constants::SCENE_HEIGHT*4);
m_pEditScene->setSceneRect(0, 0, Constants::SCENE_WIDTH*6, Constants::SCENE_HEIGHT*6);
m_pEditView = new EditView(this);
m_pEditView->setScene(m_pEditScene);

View File

@ -2,7 +2,7 @@
EditView::EditView(QWidget *parent)
: QGraphicsView(parent)
: BaseView(parent)
{
this->setFocusPolicy(Qt::ClickFocus);
}

View File

@ -34,67 +34,6 @@
<property name="bottomMargin">
<number>0</number>
</property>
<item>
<widget class="QWidget" name="widget" native="true">
<property name="sizePolicy">
<sizepolicy hsizetype="Preferred" vsizetype="Fixed">
<horstretch>0</horstretch>
<verstretch>0</verstretch>
</sizepolicy>
</property>
<property name="minimumSize">
<size>
<width>0</width>
<height>22</height>
</size>
</property>
<property name="styleSheet">
<string notr="true">QWidget {
background: #2c5282;
color: white;
border: none;
}
QWidget QLabel {
color: white;
font-size: 12px;
background: transparent;
}</string>
</property>
<layout class="QHBoxLayout" name="horizontalLayout_3">
<property name="spacing">
<number>0</number>
</property>
<property name="leftMargin">
<number>6</number>
</property>
<property name="topMargin">
<number>0</number>
</property>
<property name="rightMargin">
<number>0</number>
</property>
<property name="bottomMargin">
<number>0</number>
</property>
<item>
<widget class="QLabel" name="label">
<property name="font">
<font>
<pointsize>-1</pointsize>
</font>
</property>
<property name="styleSheet">
<string notr="true"/>
</property>
<property name="text">
<string>工程模配置</string>
</property>
</widget>
</item>
</layout>
</widget>
</item>
<item>
<widget class="QTabWidget" name="tabWidget">
<property name="styleSheet">