1 /****************************************************************************
2 **
3 ** This file is part of the LibreCAD project, a 2D CAD program
4 **
5 ** Copyright (C) 2010 R. van Twisk (librecad@rvt.dds.nl)
6 ** Copyright (C) 2001-2003 RibbonSoft. All rights reserved.
7 **
8 **
9 ** This file may be distributed and/or modified under the terms of the
10 ** GNU General Public License version 2 as published by the Free Software
11 ** Foundation and appearing in the file gpl-2.0.txt included in the
12 ** packaging of this file.
13 **
14 ** This program is distributed in the hope that it will be useful,
15 ** but WITHOUT ANY WARRANTY; without even the implied warranty of
16 ** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
17 ** GNU General Public License for more details.
18 **
19 ** You should have received a copy of the GNU General Public License
20 ** along with this program; if not, write to the Free Software
21 ** Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301  USA
22 **
23 ** This copyright notice MUST APPEAR in all copies of the script!
24 **
25 **********************************************************************/
26 
27 #include<QAction>
28 #include <QMouseEvent>
29 #include "rs_actiondrawlinetangent1.h"
30 
31 #include "rs_dialogfactory.h"
32 #include "rs_graphicview.h"
33 #include "rs_creation.h"
34 #include "rs_line.h"
35 #include "rs_coordinateevent.h"
36 #include "rs_preview.h"
37 #include "rs_debug.h"
38 
RS_ActionDrawLineTangent1(RS_EntityContainer & container,RS_GraphicView & graphicView)39 RS_ActionDrawLineTangent1::RS_ActionDrawLineTangent1(
40 		RS_EntityContainer& container,
41 		RS_GraphicView& graphicView)
42 	:RS_PreviewActionInterface("Draw Tangents 1", container, graphicView)
43 	,tangent(nullptr)
44 	,point(new RS_Vector{})
45 	,circle(nullptr)
46 {
47 	actionType=RS2::ActionDrawLineTangent1;
48 }
49 
50 RS_ActionDrawLineTangent1::~RS_ActionDrawLineTangent1() = default;
51 
trigger()52 void RS_ActionDrawLineTangent1::trigger() {
53 	RS_PreviewActionInterface::trigger();
54 
55 	if (tangent) {
56 		RS_Entity* newEntity = nullptr;
57 
58 		newEntity = new RS_Line(container,
59 								tangent->getData());
60 
61 		if (newEntity) {
62 			if(circle){
63 				circle->setHighlighted(false);
64 				graphicView->drawEntity(circle);
65 			}
66 
67 			newEntity->setLayerToActive();
68 			newEntity->setPenToActive();
69 			container->addEntity(newEntity);
70 
71 			// upd. undo list:
72 			if (document) {
73 				document->startUndoCycle();
74 				document->addUndoable(newEntity);
75 				document->endUndoCycle();
76 			}
77 
78 			graphicView->redraw(RS2::RedrawDrawing);
79 
80 			setStatus(SetPoint);
81 		}
82 		tangent.reset();
83 	} else {
84 		RS_DEBUG->print("RS_ActionDrawLineTangent1::trigger:"
85 						" Entity is nullptr\n");
86 	}
87 }
88 
89 
90 
mouseMoveEvent(QMouseEvent * e)91 void RS_ActionDrawLineTangent1::mouseMoveEvent(QMouseEvent* e) {
92 	RS_DEBUG->print("RS_ActionDrawLineTangent1::mouseMoveEvent begin");
93 
94 	RS_Vector mouse(graphicView->toGraphX(e->x()),
95 					graphicView->toGraphY(e->y()));
96 
97 	switch (getStatus()) {
98 	case SetPoint:
99 		*point = snapPoint(e);
100 		break;
101 
102 	case SetCircle: {
103 		RS_Entity* en = catchEntity(e, circleType, RS2::ResolveAll);
104 		if (en && (en->isArc() ||
105 				   en->rtti()==RS2::EntitySplinePoints)) {
106 			if(circle){
107 				circle->setHighlighted(false);
108 				graphicView->drawEntity(en);
109 			}
110 			circle = en;
111 			circle->setHighlighted(true);
112 			graphicView->drawEntity(en);
113 
114 
115 			RS_Creation creation(nullptr, nullptr);
116 			tangent.reset(
117 						creation.createTangent1(mouse,
118 												*point,
119 												circle)
120 						);
121 
122 			if (tangent) {
123 				deletePreview();
124 				preview->addEntity(tangent->clone());
125 				drawPreview();
126 			}
127 		}
128 	}
129 		break;
130 
131 	default:
132 		break;
133 	}
134 
135 	RS_DEBUG->print("RS_ActionDrawLineTangent1::mouseMoveEvent end");
136 }
137 
mouseReleaseEvent(QMouseEvent * e)138 void RS_ActionDrawLineTangent1::mouseReleaseEvent(QMouseEvent* e) {
139 
140 	if (e->button()==Qt::RightButton) {
141 		deletePreview();
142 		if(circle){
143 			circle->setHighlighted(false);
144 			graphicView->drawEntity(circle);
145 		}
146 		init(getStatus()-1);
147 	} else {
148 		switch (getStatus()) {
149 		case SetPoint: {
150 			RS_CoordinateEvent ce(snapPoint(e));
151 			coordinateEvent(&ce);
152 		}
153 			break;
154 
155 		case SetCircle:
156 			if(tangent){
157 				trigger();
158 			}
159 			break;
160 		}
161 	}
162 }
163 
coordinateEvent(RS_CoordinateEvent * e)164 void RS_ActionDrawLineTangent1::coordinateEvent(RS_CoordinateEvent* e) {
165 	if (!e) return;
166 	switch (getStatus()) {
167 	case SetPoint:
168 		*point = e->getCoordinate();
169 		graphicView->moveRelativeZero(*point);
170 		setStatus(SetCircle);
171 		break;
172 
173 	default:
174 		break;
175 	}
176 }
177 
updateMouseButtonHints()178 void RS_ActionDrawLineTangent1::updateMouseButtonHints() {
179 	switch (getStatus()) {
180 	case SetPoint:
181 		RS_DIALOGFACTORY->updateMouseWidget(tr("Specify point"),
182 											tr("Cancel"));
183 		break;
184 	case SetCircle:
185 		RS_DIALOGFACTORY->updateMouseWidget(tr("Select circle, arc or ellipse"),
186 											tr("Back"));
187 		break;
188 	default:
189 		RS_DIALOGFACTORY->updateMouseWidget();
190 		break;
191 	}
192 }
193 
updateMouseCursor()194 void RS_ActionDrawLineTangent1::updateMouseCursor()
195 {
196     switch (getStatus())
197     {
198         case SetPoint:
199             graphicView->setMouseCursor(RS2::CadCursor);
200             break;
201         case SetCircle:
202             graphicView->setMouseCursor(RS2::SelectCursor);
203             break;
204     }
205 }
206 
207 // EOF
208