Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
eclipse
GitHub Repository: eclipse/sumo
Path: blob/main/src/utils/gui/globjects/GUICursorDialog.cpp
193678 views
1
/****************************************************************************/
2
// Eclipse SUMO, Simulation of Urban MObility; see https://eclipse.dev/sumo
3
// Copyright (C) 2001-2026 German Aerospace Center (DLR) and others.
4
// This program and the accompanying materials are made available under the
5
// terms of the Eclipse Public License 2.0 which is available at
6
// https://www.eclipse.org/legal/epl-2.0/
7
// This Source Code may also be made available under the following Secondary
8
// Licenses when the conditions for such availability set forth in the Eclipse
9
// Public License 2.0 are satisfied: GNU General Public License, version 2
10
// or later which is available at
11
// https://www.gnu.org/licenses/old-licenses/gpl-2.0-standalone.html
12
// SPDX-License-Identifier: EPL-2.0 OR GPL-2.0-or-later
13
/****************************************************************************/
14
/// @file GUICursorDialog.cpp
15
/// @author Pablo Alvarez Lopez
16
/// @date Sep 2022
17
///
18
// Dialog for edit element under cursor
19
/****************************************************************************/
20
#include <config.h>
21
22
#include <utils/gui/div/GUIDesigns.h>
23
#include <utils/gui/windows/GUIAppEnum.h>
24
#include <utils/gui/windows/GUIMainWindow.h>
25
#include <utils/gui/windows/GUISUMOAbstractView.h>
26
27
#include "GUICursorDialog.h"
28
29
30
#define NUM_VISIBLE_ITEMS 10
31
32
// ===========================================================================
33
// FOX callback mapping
34
// ===========================================================================
35
36
FXDEFMAP(GUICursorDialog) GUICursorDialogMap[] = {
37
FXMAPFUNC(SEL_COMMAND, MID_CURSORDIALOG_SETFRONTELEMENT, GUICursorDialog::onCmdSetFrontElement),
38
FXMAPFUNC(SEL_COMMAND, MID_CURSORDIALOG_DELETEELEMENT, GUICursorDialog::onCmdDeleteElement),
39
FXMAPFUNC(SEL_COMMAND, MID_CURSORDIALOG_SELECTELEMENT, GUICursorDialog::onCmdSelectElement),
40
FXMAPFUNC(SEL_COMMAND, MID_CURSORDIALOG_PROPERTIES, GUICursorDialog::onCmdOpenPropertiesPopUp),
41
FXMAPFUNC(SEL_COMMAND, MID_CURSORDIALOG_MOVEUP, GUICursorDialog::onCmdMoveListUp),
42
FXMAPFUNC(SEL_COMMAND, MID_CURSORDIALOG_MOVEDOWN, GUICursorDialog::onCmdMoveListDown),
43
FXMAPFUNC(SEL_COMMAND, MID_CURSORDIALOG_FRONT, GUICursorDialog::onCmdProcessFront),
44
FXMAPFUNC(SEL_COMMAND, FXWindow::ID_UNPOST, GUICursorDialog::onCmdUnpost),
45
};
46
47
// Object implementation
48
FXIMPLEMENT(GUICursorDialog, GUIGLObjectPopupMenu, GUICursorDialogMap, ARRAYNUMBER(GUICursorDialogMap))
49
50
// ===========================================================================
51
// member method definitions
52
// ===========================================================================
53
54
GUICursorDialog::GUICursorDialog(GUIGLObjectPopupMenu::PopupType type, GUISUMOAbstractView* view, const std::vector<GUIGlObject*>& objects) :
55
GUIGLObjectPopupMenu(view->getMainWindow(), view, type),
56
myType(type),
57
myView(view) {
58
// continue depending of properties
59
if (type == GUIGLObjectPopupMenu::PopupType::PROPERTIES) {
60
buildDialogElements(view, TL("Overlapped objects"), GUIIcon::MODEINSPECT, MID_CURSORDIALOG_PROPERTIES, objects);
61
} else if (type == GUIGLObjectPopupMenu::PopupType::DELETE_ELEMENT) {
62
buildDialogElements(view, TL("Delete element"), GUIIcon::MODEDELETE, MID_CURSORDIALOG_DELETEELEMENT, objects);
63
} else if (type == GUIGLObjectPopupMenu::PopupType::SELECT_ELEMENT) {
64
buildDialogElements(view, TL("Select element"), GUIIcon::MODESELECT, MID_CURSORDIALOG_SELECTELEMENT, objects);
65
} else if (type == GUIGLObjectPopupMenu::PopupType::FRONT_ELEMENT) {
66
buildDialogElements(view, TL("Mark front element"), GUIIcon::FRONTELEMENT, MID_CURSORDIALOG_SETFRONTELEMENT, objects);
67
}
68
}
69
70
71
GUICursorDialog::~GUICursorDialog() {
72
// delete all menu commands
73
for (const auto& GLObject : myMenuCommandGLObjects) {
74
delete GLObject.first;
75
}
76
}
77
78
79
long
80
GUICursorDialog::onCmdSetFrontElement(FXObject* obj, FXSelector, void*) {
81
// search element in myGLObjects
82
for (const auto& GLObject : myMenuCommandGLObjects) {
83
if (GLObject.first == obj) {
84
GLObject.second->markAsFrontElement();
85
}
86
}
87
// destroy popup
88
myView->destroyPopup();
89
return 1;
90
}
91
92
93
long
94
GUICursorDialog::onCmdDeleteElement(FXObject* obj, FXSelector, void*) {
95
// search element in myGLObjects
96
for (const auto& GLObject : myMenuCommandGLObjects) {
97
if (GLObject.first == obj) {
98
GLObject.second->deleteGLObject();
99
}
100
}
101
// destroy popup
102
myView->destroyPopup();
103
return 1;
104
}
105
106
107
long
108
GUICursorDialog::onCmdSelectElement(FXObject* obj, FXSelector, void*) {
109
// search element in myGLObjects
110
for (const auto& GLObject : myMenuCommandGLObjects) {
111
if (GLObject.first == obj) {
112
GLObject.second->selectGLObject();
113
}
114
}
115
// destroy popup
116
myView->destroyPopup();
117
return 1;
118
}
119
120
121
long
122
GUICursorDialog::onCmdOpenPropertiesPopUp(FXObject* obj, FXSelector, void*) {
123
// search element in myGLObjects
124
for (const auto& GLObject : myMenuCommandGLObjects) {
125
if (GLObject.first == obj) {
126
myView->replacePopup(GLObject.second->getPopUpMenu(*myView->getMainWindow(), *myView));
127
return 1;
128
}
129
}
130
return 0;
131
}
132
133
134
long
135
GUICursorDialog::onCmdMoveListUp(FXObject*, FXSelector, void*) {
136
myListIndex -= NUM_VISIBLE_ITEMS;
137
updateList();
138
show();
139
return 0;
140
}
141
142
143
long
144
GUICursorDialog::onCmdMoveListDown(FXObject*, FXSelector, void*) {
145
myListIndex += NUM_VISIBLE_ITEMS;
146
updateList();
147
show();
148
return 0;
149
}
150
151
152
long
153
GUICursorDialog::onCmdProcessFront(FXObject*, FXSelector, void*) {
154
if (myMenuCommandGLObjects.size() > 0) {
155
// continue depending of properties
156
if (myType == GUIGLObjectPopupMenu::PopupType::DELETE_ELEMENT) {
157
myMenuCommandGLObjects.front().second->deleteGLObject();
158
} else if (myType == GUIGLObjectPopupMenu::PopupType::SELECT_ELEMENT) {
159
myMenuCommandGLObjects.front().second->selectGLObject();
160
} else if (myType == GUIGLObjectPopupMenu::PopupType::FRONT_ELEMENT) {
161
myMenuCommandGLObjects.front().second->markAsFrontElement();
162
}
163
}
164
return 0;
165
}
166
167
168
long
169
GUICursorDialog::onCmdUnpost(FXObject* obj, FXSelector, void* ptr) {
170
// ignore move up, down and header
171
if ((obj == myMoveUpMenuCommand) || (obj == myMoveDownMenuCommand) || (obj == myMenuHeader)) {
172
return 1;
173
}
174
if (grabowner) {
175
grabowner->handle(this, FXSEL(SEL_COMMAND, ID_UNPOST), ptr);
176
} else {
177
popdown();
178
if (grabbed()) {
179
ungrab();
180
}
181
}
182
return 1;
183
}
184
185
186
void
187
GUICursorDialog::updateList() {
188
// first hide all menu commands
189
for (const auto& GLObject : myMenuCommandGLObjects) {
190
GLObject.first->hide();
191
}
192
// check if disable menu command up
193
if (myListIndex == 0) {
194
myMoveUpMenuCommand->disable();
195
} else {
196
myMoveUpMenuCommand->enable();
197
}
198
// show menu commands depending of myListIndex
199
if ((myListIndex + NUM_VISIBLE_ITEMS) > (int)myMenuCommandGLObjects.size()) {
200
for (int i = (int)myMenuCommandGLObjects.size() - NUM_VISIBLE_ITEMS; i < (int)myMenuCommandGLObjects.size(); i++) {
201
myMenuCommandGLObjects.at(i).first->show();
202
}
203
myMoveDownMenuCommand->disable();
204
} else {
205
for (int i = myListIndex; i < (myListIndex + NUM_VISIBLE_ITEMS); i++) {
206
myMenuCommandGLObjects.at(i).first->show();
207
}
208
myMoveDownMenuCommand->enable();
209
}
210
// recalc popup
211
recalc();
212
}
213
214
215
void
216
GUICursorDialog::buildDialogElements(GUISUMOAbstractView* view, const FXString text, GUIIcon icon, FXSelector sel, const std::vector<GUIGlObject*>& objects) {
217
// create header
218
myMenuHeader = new MFXMenuHeader(this, view->getMainWindow()->getBoldFont(), text, GUIIconSubSys::getIcon(icon), nullptr, 0);
219
new FXMenuSeparator(this);
220
// check if create move up menu command
221
if (objects.size() > NUM_VISIBLE_ITEMS) {
222
myMoveUpMenuCommand = GUIDesigns::buildFXMenuCommand(this, "Previous", GUIIconSubSys::getIcon(GUIIcon::ARROW_UP), this, MID_CURSORDIALOG_MOVEUP);
223
new FXMenuSeparator(this);
224
}
225
// create a menu command for every object
226
for (const auto& GLObject : objects) {
227
myMenuCommandGLObjects.push_back(std::make_pair(GUIDesigns::buildFXMenuCommand(this, GLObject->getMicrosimID(), GLObject->getGLIcon(), this, sel), GLObject));
228
}
229
// check if create move down menu command
230
if (objects.size() > NUM_VISIBLE_ITEMS) {
231
new FXMenuSeparator(this);
232
myMoveDownMenuCommand = GUIDesigns::buildFXMenuCommand(this, "Next", GUIIconSubSys::getIcon(GUIIcon::ARROW_DOWN), this, MID_CURSORDIALOG_MOVEDOWN);
233
updateList();
234
}
235
}
236
237
/****************************************************************************/
238
239