File indexing completed on 2024-05-19 04:36:38
0001 /* This file is part of the TikZKit project. 0002 * 0003 * Copyright (C) 2014 Dominik Haumann <dhaumann@kde.org> 0004 * 0005 * This library is free software; you can redistribute it and/or modify 0006 * it under the terms of the GNU Library General Public License as published 0007 * by the Free Software Foundation, either version 2 of the License, or 0008 * (at your option) any later version. 0009 * 0010 * This library is distributed in the hope that it will be useful, 0011 * but WITHOUT ANY WARRANTY; without even the implied warranty of 0012 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 0013 * GNU Library General Public License for more details. 0014 * 0015 * You should have received a copy of the GNU Library General Public License 0016 * along with this library; see the file COPYING.LIB. If not, see 0017 * <http://www.gnu.org/licenses/>. 0018 */ 0019 0020 #include "LineTool.h" 0021 #include "ResizeHandle.h" 0022 #include "RotateHandle.h" 0023 #include "MoveHandle.h" 0024 #include "EdgePathItem.h" 0025 #include "AnchorManager.h" 0026 #include "DocumentPrivate.h" 0027 #include "ViewPrivate.h" 0028 #include "Renderer.h" 0029 0030 #include <tikz/core/Style.h> 0031 #include <tikz/core/EdgePath.h> 0032 #include <tikz/core/Transaction.h> 0033 0034 #include <QApplication> 0035 #include <QGraphicsScene> 0036 0037 #include <QDebug> 0038 0039 namespace tikz { 0040 namespace ui { 0041 0042 LineTool::LineTool(tikz::ui::PathItem * path, QGraphicsScene * scene) 0043 : AbstractTool(path->document(), scene) 0044 , m_path(qobject_cast<tikz::ui::EdgePathItem *>(path)) 0045 , m_anchorManager(new AnchorManager(scene, path->document(), this)) 0046 , m_transaction(nullptr) 0047 { 0048 // show all path handles 0049 createPathHandles(); 0050 0051 connect(m_path->path(), SIGNAL(changed()), this, SLOT(updateHandlePositions())); 0052 } 0053 0054 LineTool::~LineTool() 0055 { 0056 qDeleteAll(m_handles); 0057 m_handles.clear(); 0058 } 0059 0060 void LineTool::mouseMoveEvent(QGraphicsSceneMouseEvent * event) 0061 { 0062 } 0063 0064 void LineTool::mousePressEvent(QGraphicsSceneMouseEvent * event) 0065 { 0066 } 0067 0068 void LineTool::mouseReleaseEvent(QGraphicsSceneMouseEvent * event) 0069 { 0070 } 0071 0072 void LineTool::createPathHandles() 0073 { 0074 // on hide, just delte all handles 0075 qDeleteAll(m_handles); 0076 m_handles.clear(); 0077 0078 // create and show handles 0079 m_handles.append(new ResizeHandle(Handle::StartPos)); 0080 m_handles.append(new ResizeHandle(Handle::EndPos)); 0081 0082 // make sure the handles are positioned correctly 0083 updateHandlePositions(); 0084 0085 // show and connect to get handle movements 0086 for (Handle * handle : qAsConst(m_handles)) { 0087 scene()->addItem(handle); 0088 handle->show(); 0089 connect(handle, SIGNAL(positionChanged(tikz::ui::Handle *, const QPointF &, QGraphicsView *)), 0090 this, SLOT(handleMoved(tikz::ui::Handle *, const QPointF &, QGraphicsView *))); 0091 connect(handle, SIGNAL(mousePressed(tikz::ui::Handle *, const QPointF &, QGraphicsView *)), 0092 this, SLOT(handleMousePressed(tikz::ui::Handle *, const QPointF &, QGraphicsView *))); 0093 connect(handle, SIGNAL(mouseReleased(tikz::ui::Handle *, const QPointF &, QGraphicsView *)), 0094 this, SLOT(handleMouseReleased(tikz::ui::Handle *, const QPointF &, QGraphicsView *))); 0095 } 0096 } 0097 0098 void LineTool::updateHandlePositions() 0099 { 0100 for (Handle * handle : qAsConst(m_handles)) { 0101 handle->setPos(handlePos(handle->handlePos())); 0102 handle->setRotation(-m_path->style()->rotation()); 0103 } 0104 } 0105 0106 QPointF LineTool::handlePos(Handle::Position pos) 0107 { 0108 if (pos == Handle::StartPos) { 0109 return m_path->startPos(); 0110 } else { 0111 return m_path->endPos(); 0112 } 0113 } 0114 0115 void LineTool::handleMoved(Handle * handle, const QPointF & scenePos, QGraphicsView * view) 0116 { 0117 auto tikzView = qobject_cast<Renderer *>(view); 0118 0119 // later: preferred unit 0120 const tikz::Unit unit = tikz::Unit::Centimeter; 0121 0122 // try to attach to anchor 0123 tikz::core::MetaPos metaPos = m_anchorManager->anchorAt(scenePos, view); 0124 0125 if (! metaPos.node()) { 0126 tikz::Pos p = tikz::Pos(scenePos).convertTo(unit); 0127 p = tikzView->snapPos(p); 0128 metaPos.setPos(p); 0129 } 0130 0131 // 0132 // move start / end 0133 // 0134 tikz::core::EdgePath * ep = m_path->edgePath(); 0135 switch (handle->handlePos()) { 0136 case Handle::StartPos: { 0137 ep->setStartMetaPos(metaPos); 0138 break; 0139 } 0140 case Handle::EndPos: { 0141 ep->setEndMetaPos(metaPos); 0142 break; 0143 } 0144 default: Q_ASSERT(false); 0145 } 0146 } 0147 0148 void LineTool::handleMousePressed(Handle * handle, const QPointF & scenePos, QGraphicsView * view) 0149 { 0150 // qDebug() << "line tool: mouse handle pressed " << scenePos; 0151 m_transaction.reset(new tikz::core::Transaction(document(), "Move Line")); 0152 m_anchorManager->addAllNodes(); 0153 } 0154 0155 void LineTool::handleMouseReleased(Handle * handle, const QPointF & scenePos, QGraphicsView * view) 0156 { 0157 // qDebug() << "line tool: mouse handle released" << scenePos; 0158 0159 m_anchorManager->clear(); 0160 m_transaction->finish(); 0161 } 0162 0163 } 0164 } 0165 0166 // kate: indent-width 4; replace-tabs on;