]> Shamusworld >> Repos - architektonas/blob - src/rotateaction.cpp
Added rotation tool.
[architektonas] / src / rotateaction.cpp
1 // rotateaction.cpp: Action class for rotating selected objects
2 //
3 // Part of the Architektonas Project
4 // (C) 2011 Underground Software
5 // See the README and GPLv3 files for licensing and warranty information
6 //
7 // JLH = James Hammons <jlhamm@acm.org>
8 //
9 // WHO  WHEN        WHAT
10 // ---  ----------  ------------------------------------------------------------
11 // JLH  09/03/2011  Created this file
12 //
13
14 #include "rotateaction.h"
15 #include "applicationwindow.h"
16 #include "container.h"
17 #include "drawingview.h"
18 #include "line.h"
19 #include "mathconstants.h"
20 #include "painter.h"
21 //#include "vector.h"
22
23
24 //#define FIRST_POINT 0
25 //#define NEXT_POINT 1
26 enum { FIRST_POINT, NEXT_POINT };
27
28
29 RotateAction::RotateAction(): state(FIRST_POINT), line(NULL),
30         shiftWasPressedOnNextPoint(false), spin(new Container(Vector()))
31 {
32 //      ApplicationWindow::drawing->document.CopySelectedContentsTo(selected);
33         ApplicationWindow::drawing->document.CopySelectedContentsTo(spin);
34
35 //      for(std::vector<Object *>::iterator i=spin->objects.begin(); i!=spin->objects.end(); i++)
36 //              (*i)->Save();
37         spin->Save();
38 }
39
40
41 RotateAction::~RotateAction()
42 {
43 }
44
45
46 /*virtual*/ void RotateAction::Draw(Painter * painter)
47 {
48         painter->SetPen(QPen(Qt::red, 2.0, Qt::DotLine));
49
50         // I think stuff like crosshairs should be done in the DrawingView, tho
51         // (and it's done there now...)
52         if (state == FIRST_POINT)
53         {
54                 painter->DrawHandle(p1);
55         }
56         else
57         {
58 //              Vector reflectedP2 = -(p2 - p1);
59 //              Point newP2 = p1 + reflectedP2;
60                 painter->DrawLine(p1, p2);
61                 painter->DrawHandle(p1);
62
63                 double absAngle = (Vector(p2 - p1).Angle()) * RADIANS_TO_DEGREES;
64
65                 // Keep the angle between 0 and 180 degrees
66 //              if (absAngle > 180.0)
67 //                      absAngle -= 180.0;
68
69                 QString text = QChar(0x2221) + QObject::tr(": %1");
70                 text = text.arg(absAngle);
71 //              QString text = tr("Length: %1 in.");
72 //              text = text.arg(Vector::Magnitude(p1, p2));
73                 painter->DrawInformativeText(text);
74
75                 // Draw the rotated objects only if there's been a line to spin around
76                 if (p1 != p2)
77                         spin->Draw(painter);
78         }
79 }
80
81
82 /*virtual*/ void RotateAction::MouseDown(Vector point)
83 {
84         // Clear our override...
85         shiftWasPressedOnNextPoint = false;
86
87         if (state == FIRST_POINT)
88                 p1 = point;
89         else
90                 p2 = point;
91 }
92
93
94 /*virtual*/ void RotateAction::MouseMoved(Vector point)
95 {
96         if (state == FIRST_POINT)
97                 p1 = point;
98         else
99         {
100                 p2 = point;
101                 double angle = Vector(p2, p1).Angle();
102
103                 for(std::vector<Object *>::iterator i=spin->objects.begin(); i!=spin->objects.end(); i++)
104                 {
105                         (*i)->Restore();
106                         (*i)->Rotate(p1, angle);
107                 }
108         }
109 }
110
111
112 /*virtual*/ void RotateAction::MouseReleased(void)
113 {
114         if (state == FIRST_POINT)
115         {
116                 p2 = p1;
117                 state = NEXT_POINT;
118         }
119         else if (state == NEXT_POINT)
120         {
121                 state = FIRST_POINT;
122
123                 std::vector<Object *> & objs = ApplicationWindow::drawing->document.objects;
124                 double angle = Vector(p2, p1).Angle();
125
126                 for(std::vector<Object *>::iterator i=objs.begin(); i!=objs.end(); i++)
127                 {
128                         if ((*i)->state == OSSelected)
129                                 (*i)->Rotate(p1, angle);
130                 }
131
132                 spin->Clear();
133                 ApplicationWindow::drawing->document.CopySelectedContentsTo(spin);
134                 spin->Save();
135         }
136 }
137
138
139 /*virtual*/ bool RotateAction::KeyDown(int key)
140 {
141         if ((key == Qt::Key_Shift) && (state == NEXT_POINT))
142         {
143                 shiftWasPressedOnNextPoint = true;
144                 p1Save = p1;
145                 p1 = p2;
146                 state = FIRST_POINT;
147                 return true;
148         }
149
150         return false;
151 }
152
153
154 /*virtual*/ bool RotateAction::KeyReleased(int key)
155 {
156         if ((key == Qt::Key_Shift) && shiftWasPressedOnNextPoint)
157         {
158                 shiftWasPressedOnNextPoint = false;
159                 p2 = p1;
160                 p1 = p1Save;
161                 state = NEXT_POINT;
162                 return true;
163         }
164
165         return false;
166 }
167