38#include <wx/datetime.h>
39#include <wx/clipbrd.h>
41#include "model/route.h"
42#include "model/routeman.h"
43#include "model/select.h"
48#include "ocpn_frame.h"
49#include "routemanagerdialog.h"
63 isInsideUndoableAction =
false;
68 for (
unsigned int i = 0; i < undoStack.size(); i++) {
77wxString UndoAction::Description() {
80 case Undo_CreateWaypoint:
81 descr = _(
"Create Mark");
83 case Undo_DeleteWaypoint:
84 descr = _(
"Delete Mark");
86 case Undo_MoveWaypoint:
87 descr = _(
"Move Waypoint");
89 case Undo_AppendWaypoint:
90 descr = _(
"Append Waypoint");
102 wxRealPoint* lastPoint = (wxRealPoint*)action->before[0];
103 lat = currentPoint->m_lat;
104 lon = currentPoint->m_lon;
105 currentPoint->m_lat = lastPoint->y;
106 currentPoint->m_lon = lastPoint->x;
110 selectable->m_slat = currentPoint->m_lat;
111 selectable->m_slon = currentPoint->m_lon;
113 if ((NULL != g_pMarkInfoDialog) && (g_pMarkInfoDialog->IsShown())) {
114 if (currentPoint == g_pMarkInfoDialog->GetRoutePoint())
115 g_pMarkInfoDialog->UpdateProperties(
true);
118 wxArrayPtrVoid* routeArray =
119 g_pRouteMan->GetRouteArrayContaining(currentPoint);
121 for (
unsigned int ir = 0; ir < routeArray->GetCount(); ir++) {
123 pr->FinalizeForRendering();
124 pr->UpdateSegmentDistances();
125 pConfig->UpdateRoute(pr);
133 pSelect->AddSelectableRoutePoint(point->m_lat, point->m_lon, point);
134 pConfig->AddNewWayPoint(point, -1);
137 if (NULL != pWayPointMan) pWayPointMan->
AddRoutePoint(point);
138 if (pRouteManagerDialog && pRouteManagerDialog->IsShown())
139 pRouteManagerDialog->UpdateWptListCtrl();
144 pConfig->DeleteWayPoint(point);
145 pSelect->DeleteSelectablePoint(point, SELTYPE_ROUTEPOINT);
147 if (pRouteManagerDialog && pRouteManagerDialog->IsShown())
148 pRouteManagerDialog->UpdateWptListCtrl();
155 bool noRouteLeftToRedo =
false;
156 if ((route->GetnPoints() == 2) && (cc->m_routeState == 0))
157 noRouteLeftToRedo =
true;
159 g_pRouteMan->RemovePointFromRoute(point, route, cc->m_routeState);
160 gFrame->InvalidateAllGL();
162 if (action->beforeType[0] == Undo_IsOrphanded) {
163 pConfig->DeleteWayPoint(point);
164 pSelect->DeleteSelectablePoint(point, SELTYPE_ROUTEPOINT);
168 if (noRouteLeftToRedo) {
169 cc->undo->InvalidateRedo();
172 if (RouteManagerDialog::getInstanceFlag()) {
173 if (pRouteManagerDialog && pRouteManagerDialog->IsShown())
174 pRouteManagerDialog->UpdateWptListCtrl();
177 if (cc->m_routeState > 1) {
179 cc->m_prev_pMousePoint = route->GetLastPoint();
180 cc->m_prev_rlat = cc->m_prev_pMousePoint->m_lat;
181 cc->m_prev_rlon = cc->m_prev_pMousePoint->m_lon;
182 route->m_lastMousePointIndex = route->GetnPoints();
190 if (action->beforeType[0] == Undo_IsOrphanded) {
191 pConfig->AddNewWayPoint(point, -1);
192 pSelect->AddSelectableRoutePoint(point->m_lat, point->m_lon, point);
195 RoutePoint* prevpoint = route->GetLastPoint();
197 route->AddPoint(point);
198 pSelect->AddSelectableRouteSegment(prevpoint->m_lat, prevpoint->m_lon,
199 point->m_lat, point->m_lon, prevpoint,
202 if (pRouteManagerDialog && pRouteManagerDialog->IsShown())
203 pRouteManagerDialog->UpdateWptListCtrl();
205 if (cc->m_routeState > 1) {
207 cc->m_prev_pMousePoint = route->GetLastPoint();
208 cc->m_prev_rlat = cc->m_prev_pMousePoint->m_lat;
209 cc->m_prev_rlon = cc->m_prev_pMousePoint->m_lon;
210 route->m_lastMousePointIndex = route->GetnPoints();
214bool Undo::AnythingToUndo() {
return undoStack.size() > stackpointer; }
216bool Undo::AnythingToRedo() {
return stackpointer > 0; }
218UndoAction* Undo::GetNextUndoableAction() {
return undoStack[stackpointer]; }
221 return undoStack[stackpointer - 1];
224void Undo::InvalidateRedo() {
225 if (stackpointer == 0)
return;
230 for (
unsigned int i = 0; i < stackpointer; i++) {
231 switch (undoStack[i]->type) {
232 case Undo_DeleteWaypoint:
233 undoStack[i]->before[0] = NULL;
235 case Undo_CreateWaypoint:
236 case Undo_MoveWaypoint:
237 case Undo_AppendWaypoint:
243 undoStack.erase(undoStack.begin(), undoStack.begin() + stackpointer);
247void Undo::InvalidateUndo() {
252bool Undo::UndoLastAction() {
253 if (!AnythingToUndo())
return false;
256 switch (action->type) {
257 case Undo_CreateWaypoint:
258 doRedoDeleteWaypoint(action,
263 case Undo_MoveWaypoint:
264 doUndoMoveWaypoint(action, GetParent());
268 case Undo_DeleteWaypoint:
269 doUndoDeleteWaypoint(action, GetParent());
273 case Undo_AppendWaypoint:
275 doUndoAppendWaypoint(action, GetParent());
281bool Undo::RedoNextAction() {
282 if (!AnythingToRedo())
return false;
285 switch (action->type) {
286 case Undo_CreateWaypoint:
287 doUndoDeleteWaypoint(action,
292 case Undo_MoveWaypoint:
299 case Undo_DeleteWaypoint:
300 doRedoDeleteWaypoint(action, GetParent());
304 case Undo_AppendWaypoint:
305 doRedoAppendWaypoint(action, GetParent());
312bool Undo::BeforeUndoableAction(UndoType type, UndoItemPointer before,
313 UndoBeforePointerType beforeType,
314 UndoItemPointer selectable) {
315 if (CancelUndoableAction())
return false;
320 candidate->before.clear();
321 candidate->beforeType.clear();
322 candidate->selectable.clear();
323 candidate->after.clear();
325 candidate->type = type;
326 UndoItemPointer subject = before;
328 switch (beforeType) {
329 case Undo_NeedsCopy: {
330 switch (candidate->type) {
331 case Undo_MoveWaypoint: {
332 wxRealPoint* point =
new wxRealPoint;
334 point->x = rp->m_lon;
335 point->y = rp->m_lat;
339 case Undo_CreateWaypoint:
341 case Undo_DeleteWaypoint:
343 case Undo_AppendWaypoint:
348 case Undo_IsOrphanded:
354 candidate->before.push_back(subject);
355 candidate->beforeType.push_back(beforeType);
356 candidate->selectable.push_back(selectable);
358 isInsideUndoableAction =
true;
362bool Undo::AfterUndoableAction(UndoItemPointer after) {
363 if (!isInsideUndoableAction)
return false;
365 candidate->after.push_back(after);
366 undoStack.push_front(candidate);
368 if (undoStack.size() > depthSetting) {
369 undoStack.pop_back();
372 isInsideUndoableAction =
false;
376bool Undo::CancelUndoableAction(
bool noDataDelete) {
377 if (isInsideUndoableAction) {
379 for (
unsigned int i = 0; i < candidate->beforeType.size(); i++) {
380 if (candidate->beforeType[i] == Undo_IsOrphanded) {
381 candidate->beforeType[i] = Undo_HasParent;
385 if (candidate)
delete candidate;
387 isInsideUndoableAction =
false;
395UndoAction::~UndoAction() {
396 assert(before.size() == beforeType.size());
398 for (
unsigned int i = 0; i < before.size(); i++) {
399 switch (beforeType[i]) {
400 case Undo_NeedsCopy: {
402 case Undo_MoveWaypoint:
404 delete (wxRealPoint*)before[i];
408 case Undo_DeleteWaypoint:
410 case Undo_CreateWaypoint:
412 case Undo_AppendWaypoint:
417 case Undo_IsOrphanded: {
419 case Undo_DeleteWaypoint:
424 case Undo_CreateWaypoint:
426 case Undo_MoveWaypoint:
428 case Undo_AppendWaypoint:
Dialog for displaying and editing waypoint properties.
bool AddRoutePoint(RoutePoint *prp)
Add a point to list which owns it.
bool RemoveRoutePoint(RoutePoint *prp)
Remove a routepoint from list if present, deallocate it all cases.