Eclipse SUMO - Simulation of Urban MObility
Loading...
Searching...
No Matches
GNEFixNetworkElements.cpp
Go to the documentation of this file.
1/****************************************************************************/
2// Eclipse SUMO, Simulation of Urban MObility; see https://eclipse.dev/sumo
3// Copyright (C) 2001-2024 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/****************************************************************************/
18// Dialog used to fix network elements during saving
19/****************************************************************************/
20
23#include <netedit/GNENet.h>
24#include <netedit/GNEViewNet.h>
25#include <netedit/GNEUndoList.h>
26
28
29
30// ===========================================================================
31// FOX callback mapping
32// ===========================================================================
33
39
40// Object implementation
41FXIMPLEMENT(GNEFixNetworkElements, FXDialogBox, GNEFixNetworkElementsMap, ARRAYNUMBER(GNEFixNetworkElementsMap))
42
43// ===========================================================================
44// member method definitions
45// ===========================================================================
46
47// ---------------------------------------------------------------------------
48// GNEFixNetworkElements - methods
49// ---------------------------------------------------------------------------
50
51GNEFixNetworkElements::GNEFixNetworkElements(GNEViewNet* viewNet, const std::vector<GNENetworkElement*>& invalidNetworkElements) :
52 FXDialogBox(viewNet->getApp(), TL("Fix network elements problems"), GUIDesignDialogBoxExplicitStretchable(600, 620)),
53 myViewNet(viewNet) {
54 // set busStop icon for this dialog
56 // create main frame
57 myMainFrame = new FXVerticalFrame(this, GUIDesignAuxiliarFrame);
58 // create frames for options
59 FXHorizontalFrame* optionsFrame = new FXHorizontalFrame(myMainFrame, GUIDesignAuxiliarFrame);
60 myLeftFrame = new FXVerticalFrame(optionsFrame, GUIDesignAuxiliarFrame);
61 myRightFrame = new FXVerticalFrame(optionsFrame, GUIDesignAuxiliarFrame);
62 // create fix edge options
63 myFixEdgeOptions = new FixEdgeOptions(this, viewNet);
64 // create fix crossing options
65 myFixCrossingOptions = new FixCrossingOptions(this, viewNet);
66 // create buttons
67 myButtons = new Buttons(this);
68 // split invalidNetworkElements in four groups
69 std::vector<GNENetworkElement*> invalidEdges, invalidCrossings;
70 // fill groups
71 for (const auto& invalidNetworkElement : invalidNetworkElements) {
72 if (invalidNetworkElement->getTagProperty().getTag() == SUMO_TAG_EDGE) {
73 invalidEdges.push_back(invalidNetworkElement);
74 } else if (invalidNetworkElement->getTagProperty().getTag() == SUMO_TAG_CROSSING) {
75 invalidCrossings.push_back(invalidNetworkElement);
76 }
77 }
78 // fill options
79 myFixEdgeOptions->setInvalidElements(invalidEdges);
80 myFixCrossingOptions->setInvalidElements(invalidCrossings);
81}
82
83
86
87
88long
89GNEFixNetworkElements::onCmdSelectOption(FXObject* obj, FXSelector, void*) {
90 // select options
93 return 1;
94}
95
96
97long
98GNEFixNetworkElements::onCmdAccept(FXObject*, FXSelector, void*) {
99 bool abortSaving = false;
100 // fix elements
101 myFixEdgeOptions->fixElements(abortSaving);
102 myFixCrossingOptions->fixElements(abortSaving);
103 // check if abort saving
104 if (abortSaving) {
105 // stop modal with TRUE (abort saving)
106 getApp()->stopModal(this, FALSE);
107 } else {
108 // stop modal with TRUE (continue saving)
109 getApp()->stopModal(this, TRUE);
110 }
111 return 1;
112}
113
114
115long
116GNEFixNetworkElements::onCmdCancel(FXObject*, FXSelector, void*) {
117 // Stop Modal (abort saving)
118 getApp()->stopModal(this, FALSE);
119 return 1;
120}
121
122// ---------------------------------------------------------------------------
123// GNEFixNetworkElements::FixOptions - methods
124// ---------------------------------------------------------------------------
125
126GNEFixNetworkElements::FixOptions::FixOptions(FXVerticalFrame* frameParent, const std::string& title, GNEViewNet* viewNet) :
127 MFXGroupBoxModule(frameParent, title, MFXGroupBoxModule::Options::SAVE),
128 myViewNet(viewNet) {
129 // Create table
130 myTable = new FXTable(this, this, MID_TABLE, GUIDesignTableFixElements);
131 myTable->disable();
132 // create horizontal frame
133 FXHorizontalFrame* horizontalFrame = new FXHorizontalFrame(this, GUIDesignAuxiliarHorizontalFrame);
134 // create vertical frames
135 myLeftFrame = new FXVerticalFrame(horizontalFrame, GUIDesignAuxiliarVerticalFrame);
136 myRightFrame = new FXVerticalFrame(horizontalFrame, GUIDesignAuxiliarVerticalFrame);
137}
138
139
140void
141GNEFixNetworkElements::FixOptions::setInvalidElements(const std::vector<GNENetworkElement*>& invalidElements) {
142 // update invalid elements
143 myInvalidElements = invalidElements;
144 // configure table
145 myTable->setTableSize((int)(myInvalidElements.size()), 3);
146 myTable->setSelBackColor(FXRGBA(255, 255, 255, 255));
147 myTable->setSelTextColor(FXRGBA(0, 0, 0, 255));
148 myTable->setEditable(false);
149 // configure header
150 myTable->setVisibleColumns(4);
151 myTable->setColumnWidth(0, GUIDesignHeight);
152 myTable->setColumnWidth(1, 150);
153 myTable->setColumnWidth(2, 390);
154 myTable->setColumnText(0, "");
155 myTable->setColumnText(1, toString(SUMO_ATTR_ID).c_str());
156 myTable->setColumnText(2, TL("Conflict"));
157 myTable->getRowHeader()->setWidth(0);
158 // Declare pointer to FXTableItem
159 FXTableItem* item = nullptr;
160 // iterate over invalid edges
161 for (int i = 0; i < (int)myInvalidElements.size(); i++) {
162 // Set icon
163 item = new FXTableItem("", myInvalidElements.at(i)->getACIcon());
164 item->setIconPosition(FXTableItem::CENTER_X);
165 myTable->setItem(i, 0, item);
166 // Set ID
167 item = new FXTableItem(myInvalidElements.at(i)->getID().c_str());
168 item->setJustify(FXTableItem::LEFT | FXTableItem::CENTER_Y);
169 myTable->setItem(i, 1, item);
170 // Set conflict
171 item = new FXTableItem(myInvalidElements.at(i)->getNetworkElementProblem().c_str());
172 item->setJustify(FXTableItem::LEFT | FXTableItem::CENTER_Y);
173 myTable->setItem(i, 2, item);
174 }
175 // check if enable or disable options
176 if (invalidElements.size() > 0) {
177 enableOptions();
178 toggleSaveButton(true);
179 } else {
180 disableOptions();
181 toggleSaveButton(false);
182 }
183}
184
185
186bool
188 const FXString file = MFXUtils::getFilename2Write(myTable,
189 TL("Save list of conflicted items"), ".txt",
191 if (file == "") {
192 return false;
193 }
194 try {
195 // open output device
196 OutputDevice& dev = OutputDevice::getDevice(file.text());
197 // get invalid element ID and problem
198 for (const auto& invalidElement : myInvalidElements) {
199 dev << invalidElement->getID() << ":" << invalidElement->getNetworkElementProblem() << "\n";
200 }
201 // close output device
202 dev.close();
203 // write warning if netedit is running in testing mode
204 WRITE_DEBUG("Opening FXMessageBox 'Saving list of conflicted items successfully'");
205 // open message box error
206 FXMessageBox::information(myTable, MBOX_OK, TL("Saving successfully"), "%s", "List of conflicted items was successfully saved");
207 // write warning if netedit is running in testing mode
208 WRITE_DEBUG("Closed FXMessageBox 'Saving list of conflicted items successfully' with 'OK'");
209 } catch (IOError& e) {
210 // write warning if netedit is running in testing mode
211 WRITE_DEBUG("Opening FXMessageBox 'error saving list of conflicted items'");
212 // open message box error
213 FXMessageBox::error(myTable, MBOX_OK, TL("Saving list of conflicted items failed"), "%s", e.what());
214 // write warning if netedit is running in testing mode
215 WRITE_DEBUG("Closed FXMessageBox 'error saving list of conflicted items' with 'OK'");
216 }
217 return true;
218}
219
220// ---------------------------------------------------------------------------
221// GNEFixNetworkElements::FixEdgeOptions - methods
222// ---------------------------------------------------------------------------
223
225 FixOptions(fixNetworkElementsParent->myLeftFrame, "Edges", viewNet) {
226 // Remove invalid edges
227 removeInvalidEdges = new FXRadioButton(myLeftFrame, TL("Remove invalid edges"),
228 fixNetworkElementsParent, MID_CHOOSEN_OPERATION, GUIDesignRadioButtonFix);
229 // Save invalid edges
230 saveInvalidEdges = new FXRadioButton(myLeftFrame, TL("Save invalid edges"),
231 fixNetworkElementsParent, MID_CHOOSEN_OPERATION, GUIDesignRadioButtonFix);
232 // Select invalid edges
233 selectInvalidEdgesAndCancel = new FXRadioButton(myRightFrame, TL("Select conflicted edges"),
234 fixNetworkElementsParent, MID_CHOOSEN_OPERATION, GUIDesignRadioButtonFix);
235 // leave option "removeInvalidEdges" as default
236 removeInvalidEdges->setCheck(true);
237}
238
239
240void
242 if (option == removeInvalidEdges) {
243 removeInvalidEdges->setCheck(true);
244 saveInvalidEdges->setCheck(false);
245 selectInvalidEdgesAndCancel->setCheck(false);
246 } else if (option == saveInvalidEdges) {
247 removeInvalidEdges->setCheck(false);
248 saveInvalidEdges->setCheck(true);
249 selectInvalidEdgesAndCancel->setCheck(false);
250 } else if (option == selectInvalidEdgesAndCancel) {
251 removeInvalidEdges->setCheck(false);
252 saveInvalidEdges->setCheck(false);
253 selectInvalidEdgesAndCancel->setCheck(true);
254 }
255}
256
257
258void
260 if (myInvalidElements.size() > 0) {
261 if (removeInvalidEdges->getCheck() == TRUE) {
262 // begin undo list
263 myViewNet->getUndoList()->begin(GUIIcon::EDGE, TL("delete invalid edges"));
264 // iterate over invalid edges to delete it
265 for (const auto& invalidEdge : myInvalidElements) {
267 }
268 // end undo list
270 } else if (selectInvalidEdgesAndCancel->getCheck() == TRUE) {
271 // begin undo list
272 myViewNet->getUndoList()->begin(GUIIcon::EDGE, TL("select invalid edges"));
273 // iterate over invalid single lane elements to select all elements
274 for (const auto& invalidEdge : myInvalidElements) {
275 invalidEdge->setAttribute(GNE_ATTR_SELECTED, "true", myViewNet->getUndoList());
276 }
277 // end undo list
279 // abort saving
280 abortSaving = true;
281 }
282 }
283}
284
285
286void
288 removeInvalidEdges->enable();
289 saveInvalidEdges->enable();
290 selectInvalidEdgesAndCancel->enable();
291}
292
293
294void
296 removeInvalidEdges->disable();
297 saveInvalidEdges->disable();
298 selectInvalidEdgesAndCancel->disable();
299}
300
301// ---------------------------------------------------------------------------
302// GNEFixNetworkElements::FixCrossingOptions - methods
303// ---------------------------------------------------------------------------
304
306 FixOptions(fixNetworkElementsParent->myLeftFrame, "Crossings", viewNet) {
307 // Remove invalid crossings
308 removeInvalidCrossings = new FXRadioButton(myLeftFrame, TL("Remove invalid crossings"),
309 fixNetworkElementsParent, MID_CHOOSEN_OPERATION, GUIDesignRadioButtonFix);
310 // Save invalid crossings
311 saveInvalidCrossings = new FXRadioButton(myLeftFrame, TL("Save invalid crossings"),
312 fixNetworkElementsParent, MID_CHOOSEN_OPERATION, GUIDesignRadioButtonFix);
313 // Select invalid crossing
314 selectInvalidCrossingsAndCancel = new FXRadioButton(myRightFrame, TL("Select conflicted crossing"),
315 fixNetworkElementsParent, MID_CHOOSEN_OPERATION, GUIDesignRadioButtonFix);
316 // by default remove invalid crossings
317 removeInvalidCrossings->setCheck(TRUE);
318}
319
320
321void
323 if (option == removeInvalidCrossings) {
324 removeInvalidCrossings->setCheck(true);
325 saveInvalidCrossings->setCheck(false);
326 selectInvalidCrossingsAndCancel->setCheck(false);
327 } else if (option == saveInvalidCrossings) {
328 removeInvalidCrossings->setCheck(false);
329 saveInvalidCrossings->setCheck(true);
330 selectInvalidCrossingsAndCancel->setCheck(false);
331 } else if (option == selectInvalidCrossingsAndCancel) {
332 removeInvalidCrossings->setCheck(false);
333 saveInvalidCrossings->setCheck(false);
334 selectInvalidCrossingsAndCancel->setCheck(true);
335 }
336}
337
338
339void
341 if (myInvalidElements.size() > 0) {
342 if (removeInvalidCrossings->getCheck() == TRUE) {
343 // begin undo list
344 myViewNet->getUndoList()->begin(GUIIcon::CROSSING, TL("delete invalid crossings"));
345 // iterate over invalid crossings to delete it
346 for (const auto& invalidCrossing : myInvalidElements) {
348 }
349 // end undo list
351 } else if (selectInvalidCrossingsAndCancel->getCheck() == TRUE) {
352 // begin undo list
353 myViewNet->getUndoList()->begin(GUIIcon::CROSSING, TL("select invalid crossings"));
354 // iterate over invalid single lane elements to select all elements
355 for (const auto& invalidCrossing : myInvalidElements) {
356 invalidCrossing->setAttribute(GNE_ATTR_SELECTED, "true", myViewNet->getUndoList());
357 }
358 // end undo list
360 // abort saving
361 abortSaving = true;
362 }
363 }
364}
365
366
367void
369 removeInvalidCrossings->enable();
370 saveInvalidCrossings->enable();
371 selectInvalidCrossingsAndCancel->enable();
372}
373
374
375void
377 removeInvalidCrossings->disable();
378 saveInvalidCrossings->disable();
379 selectInvalidCrossingsAndCancel->disable();
380}
381
382// ---------------------------------------------------------------------------
383// GNEFixNetworkElements::Buttons - methods
384// ---------------------------------------------------------------------------
385
387 FXHorizontalFrame(fixNetworkElementsParent->myMainFrame, GUIDesignHorizontalFrame) {
388 new FXHorizontalFrame(this, GUIDesignAuxiliarHorizontalFrame);
391 new FXHorizontalFrame(this, GUIDesignAuxiliarHorizontalFrame);
392 // set focus in accept button
393 myKeepOldButton->setFocus();
394}
395
396/****************************************************************************/
FXDEFMAP(GNEFixNetworkElements) GNEFixNetworkElementsMap[]
@ MID_GNE_BUTTON_CANCEL
cancel button
@ MID_TABLE
The Table.
Definition GUIAppEnum.h:539
@ MID_CHOOSEN_OPERATION
set type of selection
Definition GUIAppEnum.h:597
@ MID_GNE_BUTTON_ACCEPT
accept button
#define GUIDesignRadioButtonFix
design for radio button with fixed height (used in fix elements dialogs)
Definition GUIDesigns.h:235
#define GUIDesignButtonAccept
Accept Button.
Definition GUIDesigns.h:156
#define GUIDesignButtonCancel
Cancel Button.
Definition GUIDesigns.h:162
#define GUIDesignAuxiliarHorizontalFrame
design for auxiliar (Without borders) horizontal frame used to pack another frames
Definition GUIDesigns.h:399
#define GUIDesignAuxiliarVerticalFrame
design for auxiliar (Without borders) horizontal frame used to pack another frames
Definition GUIDesigns.h:408
#define GUIDesignTableFixElements
design for tables used in GNEFixDemandElements dialogs
Definition GUIDesigns.h:637
#define GUIDesignAuxiliarFrame
design for auxiliar (Without borders) frame extended in all directions
Definition GUIDesigns.h:390
#define GUIDesignHorizontalFrame
Horizontal frame extended over frame parent with padding and spacing.
Definition GUIDesigns.h:328
#define GUIDesignDialogBoxExplicitStretchable(width, height)
design for dialog box with specific width and height that can be stretched (But not shrunk)
Definition GUIDesigns.h:617
FXString gCurrentFolder
The folder used as last.
@ SUPERMODEDEMAND
@ SAVE
save icons
#define WRITE_DEBUG(msg)
Definition MsgHandler.h:306
#define TL(string)
Definition MsgHandler.h:315
@ SUMO_TAG_CROSSING
crossing between edges for pedestrians
@ SUMO_TAG_EDGE
begin/end of the description of an edge
@ GNE_ATTR_SELECTED
element is selected
@ SUMO_ATTR_ID
int GUIDesignHeight
the default size for GUI elements
Definition StdDefs.cpp:35
std::string toString(const T &t, std::streamsize accuracy=gPrecision)
Definition ToString.h:46
horizontal frame for buttons
FXButton * myCancelButton
cancel button
FXButton * myKeepOldButton
accept button
Buttons(GNEFixNetworkElements *fixNetworkElementsParent)
build Position Options
groupbox for all radio buttons related with fix crossing options
FXRadioButton * saveInvalidCrossings
Option "save invalid crossings".
FixCrossingOptions(GNEFixNetworkElements *fixNetworkElementsParent, GNEViewNet *viewNet)
constructor
void fixElements(bool &abortSaving)
fix elements
FXRadioButton * removeInvalidCrossings
Option "remove invalid elements".
void selectOption(FXObject *option)
select option
FXRadioButton * selectInvalidCrossingsAndCancel
Option "Select invalid crossings and cancel".
groupbox for all radio buttons related with fix edges options
void selectOption(FXObject *option)
select option
FXRadioButton * selectInvalidEdgesAndCancel
Option "Select invalid edges and cancel".
void fixElements(bool &abortSaving)
fix elements
FXRadioButton * saveInvalidEdges
Option "Save invalid edges".
FXRadioButton * removeInvalidEdges
Option "Remove invalid edges".
FixEdgeOptions(GNEFixNetworkElements *fixNetworkElementsParent, GNEViewNet *viewNet)
constructor
FixOptions(FXVerticalFrame *frameParent, const std::string &title, GNEViewNet *viewNet)
constructor
FXTable * myTable
Table with the network elements.
FXVerticalFrame * myLeftFrame
vertical left frame
void setInvalidElements(const std::vector< GNENetworkElement * > &invalidElements)
set invalid network elements
FXVerticalFrame * myRightFrame
vertical right frame
Dialog fix network elements.
FXVerticalFrame * myMainFrame
main frame
long onCmdCancel(FXObject *, FXSelector, void *)
event after press cancel button
FixEdgeOptions * myFixEdgeOptions
fix edge options
FixCrossingOptions * myFixCrossingOptions
fix crossing options
GNEViewNet * myViewNet
view net
long onCmdSelectOption(FXObject *obj, FXSelector, void *)
FXVerticalFrame * myLeftFrame
vertical left frame
long onCmdAccept(FXObject *, FXSelector, void *)
event after press accept button
GNECrossing * retrieveCrossing(const GUIGlObject *glObject, bool hardFail=true) const
get Crossing by AC
GNEEdge * retrieveEdge(const std::string &id, bool hardFail=true) const
get edge by id
void deleteEdge(GNEEdge *edge, GNEUndoList *undoList, bool recomputeConnections)
removes edge
Definition GNENet.cpp:433
void deleteCrossing(GNECrossing *crossing, GNEUndoList *undoList)
remove crossing
Definition GNENet.cpp:658
GNENetHelper::AttributeCarriers * getAttributeCarriers() const
get all attribute carriers used in this net
Definition GNENet.cpp:127
void end()
End undo command sub-group. If the sub-group is still empty, it will be deleted; otherwise,...
void begin(GUIIcon icon, const std::string &description)
Begin undo command sub-group with current supermode. This begins a new group of commands that are tre...
GNENet * getNet() const
get the net object
GNEUndoList * getUndoList() const
get the undoList object
static FXButton * buildFXButton(FXComposite *p, const std::string &text, const std::string &tip, const std::string &help, FXIcon *ic, FXObject *tgt, FXSelector sel, FXuint opts=BUTTON_NORMAL, FXint x=0, FXint y=0, FXint w=0, FXint h=0, FXint pl=DEFAULT_PAD, FXint pr=DEFAULT_PAD, FXint pt=DEFAULT_PAD, FXint pb=DEFAULT_PAD)
build button
static FXIcon * getIcon(const GUIIcon which)
returns a icon previously defined in the enum GUIIcon
MFXGroupBoxModule (based on FXGroupBox)
Options
GroupBoxModule options.
static FXString getFilename2Write(FXWindow *parent, const FXString &header, const FXString &extension, FXIcon *icon, FXString &currentFolder)
Returns the file name to write.
Definition MFXUtils.cpp:82
Static storage of an output device and its base (abstract) implementation.
void close()
Closes the device and removes it from the dictionary.
static OutputDevice & getDevice(const std::string &name, bool usePrefix=true)
Returns the described OutputDevice.
Definition json.hpp:4471