| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| namespace { |
| |
| class SchematicZoomer final : public ImageUtils::ShortcutZoomer { |
| public: |
| SchematicZoomer(QWidget *parent) : ShortcutZoomer(parent) {} |
| |
| bool zoom(bool zoomin, bool resetView) override { |
| static_cast<SchematicSceneViewer *>(getWidget())->zoomQt(zoomin, resetView); |
| return true; |
| } |
| bool resetZoom() override { |
| static_cast<SchematicSceneViewer *>(getWidget())->normalizeScene(); |
| return true; |
| } |
| bool fit() override { |
| static_cast<SchematicSceneViewer *>(getWidget())->fitScene(); |
| return true; |
| } |
| }; |
| |
| const int snapDistance = 15; |
| } |
| |
| int SchematicScene::snapHSpacing = 50; |
| int SchematicScene::snapVInterval = 75; |
| |
| |
| |
| |
| |
| |
| |
| SchematicScene::SchematicScene(QWidget *parent) : QGraphicsScene(parent) { |
| setSceneRect(0, 0, 50000, 50000); |
| setItemIndexMethod(NoIndex); |
| } |
| |
| |
| |
| SchematicScene::~SchematicScene() { clearAllItems(); } |
| |
| |
| |
| void SchematicScene::showEvent(QShowEvent *se) { |
| TSelectionHandle *selHandle = TSelectionHandle::getCurrent(); |
| connect(selHandle, SIGNAL(selectionSwitched(TSelection *, TSelection *)), |
| this, SLOT(onSelectionSwitched(TSelection *, TSelection *))); |
| clearSelection(); |
| } |
| |
| |
| |
| void SchematicScene::hideEvent(QHideEvent *se) { |
| TSelectionHandle *selHandle = TSelectionHandle::getCurrent(); |
| disconnect(selHandle, SIGNAL(selectionSwitched(TSelection *, TSelection *)), |
| this, SLOT(onSelectionSwitched(TSelection *, TSelection *))); |
| } |
| |
| |
| |
| |
| |
| |
| void SchematicScene::clearAllItems() { |
| clearSelection(); |
| m_highlightedLinks.clear(); |
| QList<SchematicWindowEditor *> editors; |
| QList<SchematicNode *> nodes; |
| QList<SchematicLink *> links; |
| int i; |
| QList<QGraphicsItem *> sceneItems = items(); |
| int size = sceneItems.size(); |
| |
| for (i = 0; i < size; i++) { |
| QGraphicsItem *item = sceneItems.at(i); |
| SchematicWindowEditor *editor = dynamic_cast<SchematicWindowEditor *>(item); |
| SchematicNode *node = dynamic_cast<SchematicNode *>(item); |
| SchematicLink *link = dynamic_cast<SchematicLink *>(item); |
| if (editor) editors.append(editor); |
| if (node) nodes.append(node); |
| if (link) links.append(link); |
| } |
| while (links.size() > 0) { |
| SchematicLink *link = links.back(); |
| removeItem(link); |
| links.removeLast(); |
| SchematicPort *startPort = link->getStartPort(); |
| SchematicPort *endPort = link->getEndPort(); |
| if (startPort) startPort->removeLink(link); |
| if (endPort) endPort->removeLink(link); |
| delete link; |
| } |
| while (editors.size() > 0) { |
| SchematicWindowEditor *editor = editors.back(); |
| removeItem(editor); |
| editors.removeLast(); |
| delete editor; |
| } |
| while (nodes.size() > 0) { |
| SchematicNode *node = nodes.back(); |
| removeItem(node); |
| nodes.removeLast(); |
| delete node; |
| } |
| assert(items().size() == 0); |
| } |
| |
| |
| |
| |
| bool SchematicScene::isAnEmptyZone(const QRectF &rect) { |
| QList<QGraphicsItem *> allItems = items(); |
| for (auto const level : allItems) { |
| SchematicNode *node = dynamic_cast<SchematicNode *>(level); |
| if (!node) continue; |
| FxSchematicNode *fxNode = dynamic_cast<FxSchematicNode *>(node); |
| if (fxNode && fxNode->isA(eXSheetFx)) continue; |
| if (node->boundingRect().translated(node->scenePos()).intersects(rect)) |
| return false; |
| } |
| return true; |
| } |
| |
| |
| |
| QVector<SchematicNode *> SchematicScene::getPlacedNode(SchematicNode *node) { |
| QRectF rect = node->boundingRect().translated(node->scenePos()); |
| QList<QGraphicsItem *> allItems = items(); |
| QVector<SchematicNode *> nodes; |
| for (auto const item : allItems) { |
| SchematicNode *placedNode = dynamic_cast<SchematicNode *>(item); |
| if (!placedNode || placedNode == node) continue; |
| QRectF nodeRect = |
| placedNode->boundingRect().translated(placedNode->scenePos()); |
| QRectF enlargedRect = rect.adjusted(-10, -10, 10, 10); |
| if (enlargedRect.contains(nodeRect)) nodes.push_back(placedNode); |
| } |
| return nodes; |
| } |
| |
| |
| |
| void SchematicScene::addSnapTarget(const QPointF &pos, const QRectF &rect, |
| const QPointF &theOtherEndPos, |
| const QPointF &endPosOffset) { |
| |
| QRectF nodeRect = rect.adjusted(5, 5, -5, -5); |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| SnapTargetItem *item = |
| new SnapTargetItem(pos, nodeRect, theOtherEndPos, endPosOffset); |
| addItem(item); |
| m_snapTargets.append(item); |
| } |
| |
| |
| |
| void SchematicScene::clearSnapTargets() { |
| for (auto item : m_snapTargets) { |
| removeItem(item); |
| delete item; |
| } |
| m_snapTargets.clear(); |
| } |
| |
| |
| |
| void SchematicScene::computeSnap(SchematicNode *node, QPointF &delta, |
| bool enable) { |
| if (m_snapTargets.isEmpty()) return; |
| |
| if (!enable) { |
| |
| if (m_snapTargets[0]->isVisible()) { |
| for (auto item : m_snapTargets) item->setVisible(false); |
| } |
| return; |
| } |
| |
| if (!m_snapTargets[0]->isVisible()) { |
| for (auto item : m_snapTargets) item->setVisible(true); |
| } |
| |
| QPointF newScenePos = node->scenePos() + delta; |
| QPointF newPos = views()[0]->mapFromScene(newScenePos); |
| |
| for (auto target : m_snapTargets) { |
| QPointF targetPos = target->scenePos(); |
| int snapIndex = std::nearbyint((newScenePos.y() - targetPos.y()) / |
| (double)SchematicScene::snapVInterval); |
| targetPos.setY(targetPos.y() + |
| (double)(snapIndex * SchematicScene::snapVInterval)); |
| target->setPos(targetPos); |
| if ((newPos - views()[0]->mapFromScene(targetPos)).manhattanLength() < |
| snapDistance) { |
| delta = targetPos - node->scenePos(); |
| return; |
| } |
| } |
| } |
| |
| |
| |
| |
| |
| |
| |
| SchematicSceneViewer::SchematicSceneViewer(QWidget *parent) |
| : QGraphicsView(parent) |
| , m_buttonState(Qt::NoButton) |
| , m_oldWinPos() |
| , m_oldScenePos() |
| , m_firstShowing(true) { |
| setObjectName("SchematicSceneViewer"); |
| |
| setHorizontalScrollBarPolicy(Qt::ScrollBarAlwaysOff); |
| setVerticalScrollBarPolicy(Qt::ScrollBarAlwaysOff); |
| setDragMode(QGraphicsView::NoDrag); |
| setTransformationAnchor(QGraphicsView::NoAnchor); |
| setRenderHint(QPainter::SmoothPixmapTransform); |
| setRenderHint(QPainter::TextAntialiasing); |
| setRenderHint(QPainter::Antialiasing); |
| setInteractive(true); |
| setViewportUpdateMode(QGraphicsView::SmartViewportUpdate); |
| show(); |
| |
| setAttribute(Qt::WA_AcceptTouchEvents); |
| grabGesture(Qt::SwipeGesture); |
| grabGesture(Qt::PanGesture); |
| grabGesture(Qt::PinchGesture); |
| } |
| |
| |
| |
| SchematicSceneViewer::~SchematicSceneViewer() {} |
| |
| |
| |
| |
| |
| void SchematicSceneViewer::mousePressEvent(QMouseEvent *me) { |
| |
| if (m_gestureActive && m_touchDevice == QTouchDevice::TouchScreen && |
| !m_stylusUsed) { |
| return; |
| } |
| |
| m_buttonState = me->button(); |
| m_oldWinPos = me->pos(); |
| m_oldScenePos = mapToScene(m_oldWinPos); |
| |
| if (m_buttonState == Qt::LeftButton) { |
| if (m_cursorMode == CursorMode::Zoom) { |
| m_zoomPoint = me->pos(); |
| m_zooming = true; |
| return; |
| } else if (m_cursorMode == CursorMode::Hand) { |
| m_mousePanPoint = m_touchDevice == QTouchDevice::TouchScreen |
| ? mapToScene(me->pos()) |
| : me->pos() * getDevicePixelRatio(this); |
| m_panning = true; |
| return; |
| } |
| } else if (m_buttonState == Qt::MiddleButton) { |
| m_mousePanPoint = m_touchDevice == QTouchDevice::TouchScreen |
| ? mapToScene(me->pos()) |
| : me->pos() * getDevicePixelRatio(this); |
| } |
| bool drawRect = true; |
| QList<QGraphicsItem *> pointedItems = items(me->pos()); |
| int i; |
| for (i = 0; i < pointedItems.size(); i++) { |
| SchematicWindowEditor *editor = |
| dynamic_cast<SchematicWindowEditor *>(pointedItems[i]); |
| if (!editor) { |
| drawRect = false; |
| break; |
| } |
| } |
| |
| if (m_buttonState == Qt::LeftButton && drawRect) |
| setDragMode(QGraphicsView::RubberBandDrag); |
| QGraphicsView::mousePressEvent(me); |
| } |
| |
| |
| |
| |
| |
| void SchematicSceneViewer::mouseMoveEvent(QMouseEvent *me) { |
| if (m_gestureActive && m_touchDevice == QTouchDevice::TouchScreen && |
| !m_stylusUsed) { |
| return; |
| } |
| |
| QPoint currWinPos = me->pos(); |
| QPointF currScenePos = mapToScene(currWinPos); |
| if ((m_cursorMode == CursorMode::Hand && m_panning) || |
| m_buttonState == Qt::MiddleButton) { |
| QPointF usePos = m_touchDevice == QTouchDevice::TouchScreen |
| ? mapToScene(me->pos()) |
| : me->pos() * getDevicePixelRatio(this); |
| QPointF deltaPoint = usePos - m_mousePanPoint; |
| panQt(deltaPoint); |
| m_mousePanPoint = m_touchDevice == QTouchDevice::TouchScreen |
| ? mapToScene(me->pos()) |
| : me->pos() * getDevicePixelRatio(this); |
| } else { |
| if (m_cursorMode == CursorMode::Zoom && m_zooming) { |
| int deltaY = (m_oldWinPos.y() - me->pos().y()) * 10; |
| double factorY = exp(deltaY * 0.001); |
| changeScale(m_zoomPoint, factorY); |
| m_panning = false; |
| } |
| m_oldWinPos = currWinPos; |
| m_oldScenePos = currScenePos; |
| } |
| QGraphicsView::mouseMoveEvent(me); |
| } |
| |
| |
| |
| |
| |
| void SchematicSceneViewer::mouseReleaseEvent(QMouseEvent *me) { |
| |
| m_gestureActive = false; |
| m_zooming = false; |
| m_panning = false; |
| m_stylusUsed = false; |
| m_scaleFactor = 0.0; |
| |
| m_buttonState = Qt::NoButton; |
| QGraphicsView::mouseReleaseEvent(me); |
| setDragMode(QGraphicsView::NoDrag); |
| |
| } |
| |
| |
| |
| void SchematicSceneViewer::mouseDoubleClickEvent(QMouseEvent *event) { |
| |
| if (m_gestureActive && !m_stylusUsed) { |
| m_gestureActive = false; |
| QGraphicsItem *item = |
| scene()->itemAt(mapToScene(event->pos()), QTransform()); |
| if (!item) { |
| fitScene(); |
| return; |
| } |
| |
| mousePressEvent(event); |
| } |
| |
| QGraphicsView::mouseDoubleClickEvent(event); |
| } |
| |
| |
| |
| void SchematicSceneViewer::keyPressEvent(QKeyEvent *ke) { |
| ke->ignore(); |
| QGraphicsView::keyPressEvent(ke); |
| if (!ke->isAccepted()) SchematicZoomer(this).exec(ke); |
| } |
| |
| |
| |
| |
| |
| void SchematicSceneViewer::wheelEvent(QWheelEvent *me) { |
| |
| |
| int delta = 0; |
| switch (me->source()) { |
| case Qt::MouseEventNotSynthesized: { |
| if (me->modifiers() & Qt::AltModifier) |
| delta = me->angleDelta().x(); |
| else |
| delta = me->angleDelta().y(); |
| break; |
| } |
| |
| case Qt::MouseEventSynthesizedBySystem: { |
| QPoint numPixels = me->pixelDelta(); |
| QPoint numDegrees = me->angleDelta() / 8; |
| if (!numPixels.isNull()) { |
| delta = me->pixelDelta().y(); |
| } else if (!numDegrees.isNull()) { |
| QPoint numSteps = numDegrees / 15; |
| delta = numSteps.y(); |
| } |
| break; |
| } |
| |
| default: |
| |
| { |
| std::cout << "not supported event: Qt::MouseEventSynthesizedByQt, " |
| "Qt::MouseEventSynthesizedByApplication" |
| << std::endl; |
| break; |
| } |
| |
| } |
| |
| if (abs(delta) > 0) { |
| if ((m_gestureActive == true && |
| m_touchDevice == QTouchDevice::TouchScreen) || |
| m_gestureActive == false) { |
| double factor = exp(delta * 0.001); |
| |
| changeScale(me->position().toPoint(), factor); |
| |
| changeScale(me->pos(), factor); |
| |
| m_panning = false; |
| } |
| } |
| me->accept(); |
| } |
| |
| |
| |
| void SchematicSceneViewer::zoomQt(bool zoomin, bool resetView) { |
| if (resetView) { |
| resetTransform(); |
| |
| centerOn(scene()->itemsBoundingRect().center()); |
| return; |
| } |
| |
| double scale2 = transform().determinant(); |
| if ((scale2 < 100000 || !zoomin) && (scale2 > 0.001 * 0.05 || zoomin)) { |
| double oldZoomScale = sqrt(scale2); |
| double zoomScale = |
| resetView ? 1 |
| : ImageUtils::getQuantizedZoomFactor(oldZoomScale, zoomin); |
| QTransform scale = |
| QTransform().scale(zoomScale / oldZoomScale, zoomScale / oldZoomScale); |
| |
| |
| QPointF sceneCenter(mapToScene(rect().center())); |
| setTransform(scale, true); |
| centerOn(sceneCenter); |
| } |
| } |
| |
| |
| |
| |
| |
| void SchematicSceneViewer::changeScale(const QPoint &winPos, |
| qreal scaleFactor) { |
| QPointF startScenePos = mapToScene(winPos); |
| QTransform scale = QTransform().scale(scaleFactor, scaleFactor); |
| setTransform(scale, true); |
| QPointF endScenePos = mapToScene(winPos); |
| QPointF delta = endScenePos - startScenePos; |
| translate(delta.x(), delta.y()); |
| } |
| |
| |
| |
| void SchematicSceneViewer::fitScene() { |
| if (scene()) { |
| QRectF rect = scene()->itemsBoundingRect(); |
| fitInView(rect, Qt::KeepAspectRatio); |
| } |
| } |
| |
| |
| |
| void SchematicSceneViewer::centerOnCurrent() { |
| SchematicScene *schematicScene = dynamic_cast<SchematicScene *>(scene()); |
| QGraphicsItem *node = schematicScene->getCurrentNode(); |
| if (node) centerOn(node); |
| } |
| |
| |
| |
| void SchematicSceneViewer::reorderScene() { |
| SchematicScene *schematicScene = dynamic_cast<SchematicScene *>(scene()); |
| schematicScene->reorderScene(); |
| } |
| |
| |
| |
| void SchematicSceneViewer::normalizeScene() { |
| |
| QPointF sceneCenter(mapToScene(rect().center())); |
| resetTransform(); |
| |
| scale(1.32, 1.32); |
| |
| centerOn(sceneCenter); |
| } |
| |
| |
| void SchematicSceneViewer::panQt(const QPointF &delta) { |
| if (delta == QPointF()) return; |
| setInteractive(false); |
| |
| |
| translate(delta.x(), delta.y()); |
| |
| |
| setInteractive(true); |
| } |
| |
| void SchematicSceneViewer::showEvent(QShowEvent *se) { |
| QGraphicsView::showEvent(se); |
| if (m_firstShowing) { |
| m_firstShowing = false; |
| QRectF rect = scene()->itemsBoundingRect(); |
| resetTransform(); |
| centerOn(rect.center()); |
| } |
| } |
| |
| |
| |
| void SchematicSceneViewer::enterEvent(QEvent *e) { |
| switch (m_cursorMode) { |
| case CursorMode::Hand: |
| setToolCursor(this, ToolCursor::PanCursor); |
| break; |
| case CursorMode::Zoom: |
| setToolCursor(this, ToolCursor::ZoomCursor); |
| break; |
| default: |
| setToolCursor(this, ToolCursor::StrokeSelectCursor); |
| break; |
| } |
| } |
| |
| |
| |
| void SchematicSceneViewer::leaveEvent(QEvent *e) { setCursor(Qt::ArrowCursor); } |
| |
| |
| |
| void SchematicSceneViewer::tabletEvent(QTabletEvent *e) { |
| |
| if (e->type() == QTabletEvent::TabletPress) { |
| m_stylusUsed = e->pointerType() ? true : false; |
| } else if (e->type() == QTabletEvent::TabletRelease) { |
| m_stylusUsed = false; |
| } |
| |
| e->accept(); |
| } |
| |
| |
| |
| void SchematicSceneViewer::gestureEvent(QGestureEvent *e) { |
| |
| m_gestureActive = false; |
| if (QGesture *swipe = e->gesture(Qt::SwipeGesture)) { |
| m_gestureActive = true; |
| } else if (QGesture *pan = e->gesture(Qt::PanGesture)) { |
| m_gestureActive = true; |
| } |
| if (QGesture *pinch = e->gesture(Qt::PinchGesture)) { |
| QPinchGesture *gesture = static_cast<QPinchGesture *>(pinch); |
| QPinchGesture::ChangeFlags changeFlags = gesture->changeFlags(); |
| QPoint firstCenter = gesture->centerPoint().toPoint(); |
| if (m_touchDevice == QTouchDevice::TouchScreen) |
| firstCenter = mapFromGlobal(firstCenter); |
| |
| if (gesture->state() == Qt::GestureStarted) { |
| m_gestureActive = true; |
| } else if (gesture->state() == Qt::GestureFinished) { |
| m_gestureActive = false; |
| m_zooming = false; |
| m_scaleFactor = 0.0; |
| } else { |
| if (changeFlags & QPinchGesture::ScaleFactorChanged) { |
| double scaleFactor = gesture->scaleFactor(); |
| |
| |
| if (scaleFactor > 1) { |
| double decimalValue = scaleFactor - 1; |
| decimalValue /= 1.5; |
| scaleFactor = 1 + decimalValue; |
| } else if (scaleFactor < 1) { |
| double decimalValue = 1 - scaleFactor; |
| decimalValue /= 1.5; |
| scaleFactor = 1 - decimalValue; |
| } |
| if (!m_zooming) { |
| double delta = scaleFactor - 1; |
| m_scaleFactor += delta; |
| if (m_scaleFactor > .2 || m_scaleFactor < -.2) { |
| m_zooming = true; |
| } |
| } |
| if (m_zooming) { |
| changeScale(firstCenter, scaleFactor); |
| m_panning = false; |
| } |
| m_gestureActive = true; |
| } |
| |
| if (changeFlags & QPinchGesture::CenterPointChanged) { |
| QPointF centerDelta = |
| (gesture->centerPoint() * getDevicePixelRatio(this)) - |
| (gesture->lastCenterPoint() * getDevicePixelRatio(this)); |
| if (centerDelta.manhattanLength() > 1) { |
| |
| } |
| m_gestureActive = true; |
| } |
| } |
| } |
| e->accept(); |
| } |
| |
| void SchematicSceneViewer::touchEvent(QTouchEvent *e, int type) { |
| |
| if (type == QEvent::TouchBegin) { |
| m_touchActive = true; |
| m_firstPanPoint = e->touchPoints().at(0).pos(); |
| |
| m_touchDevice = e->device()->type(); |
| } else if (m_touchActive) { |
| |
| |
| if ((e->touchPoints().count() == 2 && |
| m_touchDevice == QTouchDevice::TouchPad) || |
| (e->touchPoints().count() == 1 && |
| m_touchDevice == QTouchDevice::TouchScreen)) { |
| QTouchEvent::TouchPoint panPoint = e->touchPoints().at(0); |
| if (!m_panning) { |
| QPointF deltaPoint = panPoint.pos() - m_firstPanPoint; |
| |
| |
| if ((deltaPoint.manhattanLength() > 100) && !m_zooming) { |
| m_panning = true; |
| } |
| } |
| if (m_panning) { |
| QPointF curPos = m_touchDevice == QTouchDevice::TouchScreen |
| ? mapToScene(panPoint.pos().toPoint()) |
| : mapToScene(panPoint.pos().toPoint()) * |
| getDevicePixelRatio(this); |
| QPointF lastPos = m_touchDevice == QTouchDevice::TouchScreen |
| ? mapToScene(panPoint.lastPos().toPoint()) |
| : mapToScene(panPoint.lastPos().toPoint()) * |
| getDevicePixelRatio(this); |
| QPointF centerDelta = curPos - lastPos; |
| panQt(centerDelta); |
| } |
| } |
| } |
| if (type == QEvent::TouchEnd || type == QEvent::TouchCancel) { |
| m_touchActive = false; |
| m_panning = false; |
| } |
| e->accept(); |
| } |
| |
| bool SchematicSceneViewer::event(QEvent *e) { |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| if (e->type() == QEvent::Gesture && CommandManager::instance() |
| ->getAction(MI_TouchGestureControl) |
| ->isChecked()) { |
| gestureEvent(static_cast<QGestureEvent *>(e)); |
| return true; |
| } |
| if ((e->type() == QEvent::TouchBegin || e->type() == QEvent::TouchEnd || |
| e->type() == QEvent::TouchCancel || e->type() == QEvent::TouchUpdate) && |
| CommandManager::instance() |
| ->getAction(MI_TouchGestureControl) |
| ->isChecked()) { |
| touchEvent(static_cast<QTouchEvent *>(e), e->type()); |
| m_gestureActive = true; |
| return true; |
| } |
| return QGraphicsView::event(e); |
| } |
| |
| |
| |
| void SchematicSceneViewer::setCursorMode(CursorMode cursorMode) { |
| m_cursorMode = cursorMode; |
| } |
| |
| |
| |
| |
| |
| |
| |
| SchematicViewer::SchematicViewer(QWidget *parent) |
| : QWidget(parent) |
| , m_fullSchematic(true) |
| , m_maximizedNode(false) |
| , m_sceneHandle(0) |
| , m_cursorMode(CursorMode::Select) { |
| m_viewer = new SchematicSceneViewer(this); |
| m_stageScene = new StageSchematicScene(this); |
| m_fxScene = new FxSchematicScene(this); |
| |
| m_commonToolbar = new QToolBar(m_viewer); |
| m_stageToolbar = new QToolBar(m_viewer); |
| m_fxToolbar = new QToolBar(m_viewer); |
| m_swapToolbar = new QToolBar(m_viewer); |
| |
| m_commonToolbar->setObjectName("MediumPaddingToolBar"); |
| m_stageToolbar->setObjectName("MediumPaddingToolBar"); |
| m_fxToolbar->setObjectName("MediumPaddingToolBar"); |
| m_swapToolbar->setObjectName("MediumPaddingToolBar"); |
| |
| createToolbars(); |
| createActions(); |
| |
| |
| QVBoxLayout *mainLayout = new QVBoxLayout(); |
| mainLayout->setMargin(0); |
| mainLayout->setSpacing(0); |
| { |
| mainLayout->addWidget(m_viewer, 1); |
| |
| QFrame *bottomFrame = new QFrame(this); |
| bottomFrame->setObjectName("SchematicBottomFrame"); |
| QHBoxLayout *horizontalLayout = new QHBoxLayout(); |
| horizontalLayout->setMargin(0); |
| horizontalLayout->setSpacing(0); |
| { |
| horizontalLayout->addWidget(m_commonToolbar); |
| horizontalLayout->addStretch(); |
| horizontalLayout->addWidget(m_fxToolbar); |
| horizontalLayout->addWidget(m_stageToolbar); |
| horizontalLayout->addWidget(m_swapToolbar); |
| } |
| bottomFrame->setLayout(horizontalLayout); |
| |
| mainLayout->addWidget(bottomFrame, 0); |
| } |
| setLayout(mainLayout); |
| |
| connect(m_fxScene, SIGNAL(showPreview(TFxP)), this, |
| SIGNAL(showPreview(TFxP))); |
| connect(m_fxScene, SIGNAL(doCollapse(const QList<TFxP> &)), this, |
| SIGNAL(doCollapse(const QList<TFxP> &))); |
| connect(m_stageScene, SIGNAL(doCollapse(QList<TStageObjectId>)), this, |
| SIGNAL(doCollapse(QList<TStageObjectId>))); |
| connect(m_fxScene, SIGNAL(doExplodeChild(const QList<TFxP> &)), this, |
| SIGNAL(doExplodeChild(const QList<TFxP> &))); |
| connect(m_stageScene, SIGNAL(doExplodeChild(QList<TStageObjectId>)), this, |
| SIGNAL(doExplodeChild(QList<TStageObjectId>))); |
| connect(m_stageScene, SIGNAL(editObject()), this, SIGNAL(editObject())); |
| connect(m_fxScene, SIGNAL(editObject()), this, SIGNAL(editObject())); |
| |
| connect(m_fxScene->getFxSelection(), SIGNAL(doDelete()), this, |
| SLOT(deleteFxs())); |
| connect(m_stageScene->getStageSelection(), SIGNAL(doDelete()), this, |
| SLOT(deleteStageObjects())); |
| |
| connect(m_fxScene->getFxSelection(), |
| SIGNAL(columnPasted(const QList<TXshColumnP> &)), this, |
| SIGNAL(columnPasted(const QList<TXshColumnP> &))); |
| connect(m_stageScene->getStageSelection(), |
| SIGNAL(columnPasted(const QList<TXshColumnP> &)), this, |
| SIGNAL(columnPasted(const QList<TXshColumnP> &))); |
| |
| m_viewer->setScene(m_stageScene); |
| m_fxToolbar->hide(); |
| |
| setFocusProxy(m_viewer); |
| } |
| |
| |
| |
| SchematicViewer::~SchematicViewer() {} |
| |
| |
| |
| void SchematicViewer::getNodeColor(int ltype, QColor &nodeColor) { |
| switch (ltype) { |
| case TZI_XSHLEVEL: |
| case OVL_XSHLEVEL: |
| nodeColor = getFullcolorColumnColor(); |
| break; |
| case PLI_XSHLEVEL: |
| nodeColor = getVectorColumnColor(); |
| break; |
| case TZP_XSHLEVEL: |
| nodeColor = getLevelColumnColor(); |
| break; |
| case ZERARYFX_XSHLEVEL: |
| nodeColor = getFxColumnColor(); |
| break; |
| case CHILD_XSHLEVEL: |
| nodeColor = getChildColumnColor(); |
| break; |
| case MESH_XSHLEVEL: |
| nodeColor = getMeshColumnColor(); |
| break; |
| case PLT_XSHLEVEL: |
| nodeColor = getPaletteColumnColor(); |
| break; |
| case eNormalFx: |
| nodeColor = getNormalFxColor(); |
| break; |
| case eZeraryFx: |
| nodeColor = getFxColumnColor(); |
| break; |
| case eMacroFx: |
| nodeColor = getMacroFxColor(); |
| break; |
| case eGroupedFx: |
| nodeColor = getGroupColor(); |
| break; |
| case eNormalImageAdjustFx: |
| nodeColor = getImageAdjustFxColor(); |
| break; |
| case eNormalLayerBlendingFx: |
| nodeColor = getLayerBlendingFxColor(); |
| break; |
| case eNormalMatteFx: |
| nodeColor = getMatteFxColor(); |
| break; |
| default: |
| nodeColor = grey210; |
| break; |
| } |
| } |
| |
| |
| |
| void SchematicViewer::setApplication(TApplication *app) { |
| m_stageScene->setXsheetHandle(app->getCurrentXsheet()); |
| m_stageScene->setObjectHandle(app->getCurrentObject()); |
| m_stageScene->setFxHandle(app->getCurrentFx()); |
| m_stageScene->setColumnHandle(app->getCurrentColumn()); |
| m_stageScene->setSceneHandle(app->getCurrentScene()); |
| m_stageScene->setFrameHandle(app->getCurrentFrame()); |
| |
| m_fxScene->setApplication(app); |
| } |
| |
| |
| |
| void SchematicViewer::updateSchematic() { |
| m_stageScene->updateScene(); |
| m_fxScene->updateScene(); |
| } |
| |
| |
| |
| void SchematicViewer::setSchematicScene(SchematicScene *scene) { |
| if (scene) { |
| m_viewer->setScene(scene); |
| m_viewer->centerOn(scene->sceneRect().center()); |
| } |
| } |
| |
| |
| |
| void SchematicViewer::createToolbars() { |
| |
| m_stageToolbar->setMovable(false); |
| m_stageToolbar->setIconSize(QSize(20, 20)); |
| m_stageToolbar->setLayoutDirection(Qt::RightToLeft); |
| m_stageToolbar->setSizePolicy(QSizePolicy::Fixed, QSizePolicy::Fixed); |
| |
| m_commonToolbar->setMovable(false); |
| m_commonToolbar->setIconSize(QSize(20, 20)); |
| m_commonToolbar->setLayoutDirection(Qt::RightToLeft); |
| m_commonToolbar->setSizePolicy(QSizePolicy::Fixed, QSizePolicy::Fixed); |
| |
| m_fxToolbar->setMovable(false); |
| m_fxToolbar->setIconSize(QSize(20, 20)); |
| m_fxToolbar->setLayoutDirection(Qt::RightToLeft); |
| m_fxToolbar->setSizePolicy(QSizePolicy::Fixed, QSizePolicy::Fixed); |
| |
| m_swapToolbar->setMovable(false); |
| m_swapToolbar->setIconSize(QSize(20, 20)); |
| m_swapToolbar->setLayoutDirection(Qt::RightToLeft); |
| m_swapToolbar->setSizePolicy(QSizePolicy::Fixed, QSizePolicy::Fixed); |
| } |
| |
| |
| |
| void SchematicViewer::createActions() { |
| |
| QAction *addPegbar = 0, *addSpline = 0, *addCamera = 0, *insertFx = 0, |
| *addOutputFx = 0, *switchPort = 0, *iconifyNodes = 0; |
| { |
| |
| QIcon fitSchematicIcon = createQIcon("fit_to_window"); |
| m_fitSchematic = |
| new QAction(fitSchematicIcon, tr("&Fit to Window"), m_commonToolbar); |
| connect(m_fitSchematic, SIGNAL(triggered()), m_viewer, SLOT(fitScene())); |
| |
| |
| QIcon centerOnIcon = createQIcon("focus"); |
| m_centerOn = |
| new QAction(centerOnIcon, tr("&Focus on Current"), m_commonToolbar); |
| connect(m_centerOn, SIGNAL(triggered()), m_viewer, SLOT(centerOnCurrent())); |
| |
| |
| QIcon reorderIcon = createQIcon("reorder", false); |
| m_reorder = new QAction(reorderIcon, tr("&Reorder Nodes"), m_commonToolbar); |
| connect(m_reorder, SIGNAL(triggered()), m_viewer, SLOT(reorderScene())); |
| |
| |
| QIcon normalizeIcon = createQIcon("actual_pixel_size"); |
| m_normalize = |
| new QAction(normalizeIcon, tr("&Reset Size"), m_commonToolbar); |
| connect(m_normalize, SIGNAL(triggered()), m_viewer, SLOT(normalizeScene())); |
| |
| QIcon nodeSizeIcon = |
| createQIcon(m_maximizedNode ? "minimizenodes" : "maximizenodes"); |
| m_nodeSize = new QAction( |
| nodeSizeIcon, |
| m_maximizedNode ? tr("&Minimize Nodes") : tr("&Maximize Nodes"), |
| m_commonToolbar); |
| connect(m_nodeSize, SIGNAL(triggered()), this, SLOT(changeNodeSize())); |
| |
| QIcon selectModeIcon = createQIcon("selection_schematic"); |
| m_selectMode = |
| new QAction(selectModeIcon, tr("&Selection Mode"), m_commonToolbar); |
| m_selectMode->setCheckable(true); |
| connect(m_selectMode, SIGNAL(triggered()), this, SLOT(selectModeEnabled())); |
| |
| QIcon zoomModeIcon = createQIcon("zoom_schematic"); |
| m_zoomMode = new QAction(zoomModeIcon, tr("&Zoom Mode"), m_commonToolbar); |
| m_zoomMode->setCheckable(true); |
| connect(m_zoomMode, SIGNAL(triggered()), this, SLOT(zoomModeEnabled())); |
| |
| QIcon handModeIcon = createQIcon("hand_schematic"); |
| m_handMode = new QAction(handModeIcon, tr("&Hand Mode"), m_commonToolbar); |
| m_handMode->setCheckable(true); |
| connect(m_handMode, SIGNAL(triggered()), this, SLOT(handModeEnabled())); |
| |
| setCursorMode(m_cursorMode); |
| |
| if (m_fullSchematic) { |
| |
| addPegbar = new QAction(tr("&New Pegbar"), m_stageToolbar); |
| QIcon addPegbarIcon = createQIcon("pegbar"); |
| addPegbar->setIcon(addPegbarIcon); |
| connect(addPegbar, SIGNAL(triggered()), m_stageScene, |
| SLOT(onPegbarAdded())); |
| |
| |
| addCamera = new QAction(tr("&New Camera"), m_stageToolbar); |
| QIcon addCameraIcon = createQIcon("camera"); |
| addCamera->setIcon(addCameraIcon); |
| connect(addCamera, SIGNAL(triggered()), m_stageScene, |
| SLOT(onCameraAdded())); |
| |
| |
| addSpline = new QAction(tr("&New Motion Path"), m_stageToolbar); |
| QIcon addSplineIcon = createQIcon("motionpath"); |
| addSpline->setIcon(addSplineIcon); |
| connect(addSpline, SIGNAL(triggered()), m_stageScene, |
| SLOT(onSplineAdded())); |
| |
| |
| switchPort = |
| new QAction(tr("&Switch output port display mode"), m_stageToolbar); |
| switchPort->setCheckable(true); |
| switchPort->setChecked(m_stageScene->isShowLetterOnPortFlagEnabled()); |
| QIcon switchPortIcon = createQIcon("switchport"); |
| switchPort->setIcon(switchPortIcon); |
| connect(switchPort, SIGNAL(toggled(bool)), m_stageScene, |
| SLOT(onSwitchPortModeToggled(bool))); |
| |
| |
| insertFx = CommandManager::instance()->getAction("MI_InsertFx"); |
| if (insertFx) { |
| QIcon insertFxIcon = createQIcon("fx_logo"); |
| insertFx->setIcon(insertFxIcon); |
| } |
| |
| |
| addOutputFx = CommandManager::instance()->getAction("MI_NewOutputFx"); |
| |
| |
| iconifyNodes = new QAction(tr("&Toggle node icons"), m_fxToolbar); |
| iconifyNodes->setCheckable(true); |
| iconifyNodes->setChecked(!m_fxScene->isNormalIconView()); |
| QIcon iconifyNodesIcon = createQIcon("iconifynodes"); |
| iconifyNodes->setIcon(iconifyNodesIcon); |
| connect(iconifyNodes, SIGNAL(toggled(bool)), m_fxScene, |
| SLOT(onIconifyNodesToggled(bool))); |
| |
| |
| QIcon changeSchematicIcon = createQIcon("swap"); |
| m_changeScene = |
| CommandManager::instance()->getAction("A_FxSchematicToggle", true); |
| if (m_changeScene) { |
| m_changeScene->setIcon(changeSchematicIcon); |
| connect(m_changeScene, SIGNAL(triggered()), this, |
| SLOT(onSceneChanged())); |
| } else |
| m_changeScene = 0; |
| } |
| } |
| |
| |
| |
| m_commonToolbar->addSeparator(); |
| m_commonToolbar->addAction(m_nodeSize); |
| m_commonToolbar->addAction(m_normalize); |
| m_commonToolbar->addAction(m_reorder); |
| m_commonToolbar->addAction(m_centerOn); |
| m_commonToolbar->addAction(m_fitSchematic); |
| m_commonToolbar->addSeparator(); |
| m_commonToolbar->addAction(m_handMode); |
| m_commonToolbar->addAction(m_zoomMode); |
| m_commonToolbar->addAction(m_selectMode); |
| |
| if (m_fullSchematic) { |
| m_stageToolbar->addSeparator(); |
| m_stageToolbar->addAction(switchPort); |
| m_stageToolbar->addSeparator(); |
| m_stageToolbar->addAction(addSpline); |
| m_stageToolbar->addAction(addCamera); |
| m_stageToolbar->addAction(addPegbar); |
| |
| m_fxToolbar->addSeparator(); |
| m_fxToolbar->addAction(iconifyNodes); |
| m_fxToolbar->addSeparator(); |
| m_fxToolbar->addAction(addOutputFx); |
| m_fxToolbar->addAction(insertFx); |
| |
| if (m_changeScene) m_swapToolbar->addAction(m_changeScene); |
| } |
| } |
| |
| |
| |
| void SchematicViewer::setStageSchematic() { |
| if (m_viewer->scene() != m_stageScene) { |
| m_viewer->setScene(m_stageScene); |
| QRectF rect = m_stageScene->itemsBoundingRect(); |
| |
| m_viewer->resetTransform(); |
| m_viewer->centerOn(rect.center()); |
| |
| m_fxToolbar->hide(); |
| m_stageToolbar->show(); |
| |
| m_viewer->update(); |
| } |
| |
| parentWidget()->setWindowTitle(QObject::tr("Stage Schematic")); |
| } |
| |
| |
| |
| void SchematicViewer::setFxSchematic() { |
| if (m_viewer->scene() != m_fxScene) { |
| m_viewer->setScene(m_fxScene); |
| QRectF rect = m_fxScene->itemsBoundingRect(); |
| |
| m_viewer->resetTransform(); |
| m_viewer->centerOn(rect.center()); |
| |
| m_stageToolbar->hide(); |
| m_fxToolbar->show(); |
| |
| |
| if (!m_fxScene->isNormalIconView()) m_fxScene->updateScene(); |
| |
| m_viewer->update(); |
| } |
| |
| parentWidget()->setWindowTitle(QObject::tr("FX Schematic")); |
| } |
| |
| |
| |
| void SchematicViewer::onSceneChanged() { |
| if (!hasFocus()) return; |
| |
| QGraphicsScene *scene = m_viewer->scene(); |
| if (scene == m_fxScene) |
| setStageSchematic(); |
| else if (scene == m_stageScene) |
| setFxSchematic(); |
| } |
| |
| |
| |
| void SchematicViewer::onSceneSwitched() { |
| m_maximizedNode = m_fxScene->getXsheetHandle() |
| ->getXsheet() |
| ->getFxDag() |
| ->getDagGridDimension() == 0; |
| QIcon nodeSizeIcon = |
| createQIcon(m_maximizedNode ? "minimizenodes" : "maximizenodes"); |
| m_nodeSize->setIcon(nodeSizeIcon); |
| QString label(m_maximizedNode ? tr("&Minimize Nodes") |
| : tr("&Maximize Nodes")); |
| m_nodeSize->setText(label); |
| |
| |
| m_viewer->resetTransform(); |
| m_viewer->centerOn(m_viewer->scene()->itemsBoundingRect().center()); |
| if (m_viewer->scene() == m_fxScene && !m_fxScene->isNormalIconView()) |
| m_fxScene->updateScene(); |
| } |
| |
| |
| |
| bool SchematicViewer::isStageSchematicViewed() { |
| QGraphicsScene *scene = m_viewer->scene(); |
| return scene == m_stageScene; |
| } |
| |
| |
| |
| void SchematicViewer::setStageSchematicViewed(bool isStageSchematic) { |
| if (!m_fullSchematic) isStageSchematic = true; |
| |
| if (isStageSchematic == isStageSchematicViewed()) return; |
| if (isStageSchematic) |
| setStageSchematic(); |
| else |
| setFxSchematic(); |
| } |
| |
| |
| |
| void SchematicViewer::updateScenes() { |
| TStageObjectId id = m_stageScene->getCurrentObject(); |
| if (id.isColumn()) { |
| m_stageScene->update(); |
| TXsheet *xsh = m_stageScene->getXsheetHandle()->getXsheet(); |
| if (!xsh) return; |
| TXshColumn *column = xsh->getColumn(id.getIndex()); |
| if (!column || !column->getZeraryFxColumn()) return; |
| TFx *fx = column->getZeraryFxColumn()->getZeraryColumnFx(); |
| m_fxScene->getFxHandle()->setFx(fx); |
| m_fxScene->update(); |
| } |
| } |
| |
| |
| |
| void SchematicViewer::changeNodeSize() { |
| m_maximizedNode = !m_maximizedNode; |
| |
| m_fxScene->resizeNodes(m_maximizedNode); |
| m_stageScene->resizeNodes(m_maximizedNode); |
| QIcon nodeSizeIcon = |
| createQIcon(m_maximizedNode ? "minimizenodes" : "maximizenodes"); |
| m_nodeSize->setIcon(nodeSizeIcon); |
| QString label(m_maximizedNode ? tr("&Minimize Nodes") |
| : tr("&Maximize Nodes")); |
| m_nodeSize->setText(label); |
| } |
| |
| |
| |
| QColor SchematicViewer::getSelectedNodeTextColor() { |
| |
| TPixel currentColumnPixel; |
| Preferences::instance()->getCurrentColumnData(currentColumnPixel); |
| QColor currentColumnColor((int)currentColumnPixel.r, |
| (int)currentColumnPixel.g, |
| (int)currentColumnPixel.b, 255); |
| return currentColumnColor; |
| } |
| |
| |
| |
| void SchematicViewer::setCursorMode(CursorMode cursorMode) { |
| m_cursorMode = cursorMode; |
| m_viewer->setCursorMode(m_cursorMode); |
| |
| m_selectMode->setChecked((m_cursorMode == CursorMode::Select)); |
| m_zoomMode->setChecked((m_cursorMode == CursorMode::Zoom)); |
| m_handMode->setChecked((m_cursorMode == CursorMode::Hand)); |
| } |
| |
| |
| |
| void SchematicViewer::selectModeEnabled() { setCursorMode(CursorMode::Select); } |
| |
| |
| |
| void SchematicViewer::zoomModeEnabled() { setCursorMode(CursorMode::Zoom); } |
| |
| |
| |
| void SchematicViewer::handModeEnabled() { setCursorMode(CursorMode::Hand); } |
| |
| |
| |
| void SchematicViewer::deleteFxs() { |
| emit doDeleteFxs(m_fxScene->getFxSelection()); |
| } |
| |
| |
| |
| void SchematicViewer::deleteStageObjects() { |
| emit doDeleteStageObjects(m_stageScene->getStageSelection()); |
| } |