Path: blob/main/src/netedit/elements/GNEAttributeCarrier.cpp
193674 views
/****************************************************************************/1// Eclipse SUMO, Simulation of Urban MObility; see https://eclipse.dev/sumo2// Copyright (C) 2001-2026 German Aerospace Center (DLR) and others.3// This program and the accompanying materials are made available under the4// terms of the Eclipse Public License 2.0 which is available at5// https://www.eclipse.org/legal/epl-2.0/6// This Source Code may also be made available under the following Secondary7// Licenses when the conditions for such availability set forth in the Eclipse8// Public License 2.0 are satisfied: GNU General Public License, version 29// or later which is available at10// https://www.gnu.org/licenses/old-licenses/gpl-2.0-standalone.html11// SPDX-License-Identifier: EPL-2.0 OR GPL-2.0-or-later12/****************************************************************************/13/// @file GNEAttributeCarrier.cpp14/// @author Jakob Erdmann15/// @date Feb 201116///17// Abstract Base class for gui objects which carry attributes18/****************************************************************************/1920#include <netedit/changes/GNEChange_Attribute.h>21#include <netedit/GNEApplicationWindow.h>22#include <netedit/GNENet.h>23#include <netedit/GNETagPropertiesDatabase.h>24#include <netedit/GNEUndoList.h>25#include <netedit/GNEViewNet.h>26#include <netedit/GNEViewParent.h>27#include <utils/common/StringTokenizer.h>28#include <utils/common/ToString.h>29#include <utils/emissions/PollutantsInterface.h>30#include <utils/geom/GeomConvHelper.h>31#include <utils/gui/div/GUIGlobalSelection.h>32#include <utils/gui/images/VClassIcons.h>33#include <utils/iodevices/OutputDevice.h>34#include <utils/options/OptionsCont.h>35#include <utils/shapes/PointOfInterest.h>3637#include "GNEAttributeCarrier.h"3839// ===========================================================================40// static members41// ===========================================================================4243const std::string GNEAttributeCarrier::FEATURE_LOADED = "loaded";44const std::string GNEAttributeCarrier::FEATURE_GUESSED = "guessed";45const std::string GNEAttributeCarrier::FEATURE_MODIFIED = "modified";46const std::string GNEAttributeCarrier::FEATURE_APPROVED = "approved";47const std::string GNEAttributeCarrier::TRUE_STR = toString(true);48const std::string GNEAttributeCarrier::FALSE_STR = toString(false);4950// ===========================================================================51// method definitions52// ===========================================================================5354GNEAttributeCarrier::GNEAttributeCarrier(const SumoXMLTag tag, GNENet* net) :55myTagProperty(net->getTagPropertiesDatabase()->getTagProperty(tag, true)),56myNet(net),57myIsTemplate(true) {58// set default bucket for template elements59auto savingFilesHandler = net->getGNEApplicationWindow()->getFileBucketHandler();60if (myTagProperty->saveInNetworkFile()) {61myFileBucket = savingFilesHandler->getDefaultBucket(FileBucket::Type::NETWORK);62} else if (myTagProperty->saveInDataFile()) {63myFileBucket = savingFilesHandler->getDefaultBucket(FileBucket::Type::DATA);64} else if (myTagProperty->saveInDemandFile()) {65myFileBucket = savingFilesHandler->getDefaultBucket(FileBucket::Type::DEMAND);66} else if (myTagProperty->saveInMeanDataFile()) {67myFileBucket = savingFilesHandler->getDefaultBucket(FileBucket::Type::MEANDATA);68} else if (myTagProperty->saveInAdditionalFile()) {69// additional MUST be the last, because demand and data elements can be saved in additional files70myFileBucket = savingFilesHandler->getDefaultBucket(FileBucket::Type::ADDITIONAL);71}72// update counter in filebucket73if (myFileBucket) {74myFileBucket->addElement(true);75}76}7778GNEAttributeCarrier::GNEAttributeCarrier(const SumoXMLTag tag, GNENet* net, FileBucket* fileBucket) :79myTagProperty(net->getTagPropertiesDatabase()->getTagProperty(tag, true)),80myNet(net),81myFileBucket(fileBucket) {82}838485GNEAttributeCarrier::~GNEAttributeCarrier() {86// update counter in filebucket87if (myIsTemplate && myFileBucket) {88myFileBucket->removeElement(true);89}90}919293const std::string94GNEAttributeCarrier::getID() const {95return getAttribute(SUMO_ATTR_ID);96}979899GNENet*100GNEAttributeCarrier::getNet() const {101return myNet;102}103104105void106GNEAttributeCarrier::selectAttributeCarrier() {107auto glObject = getGUIGlObject();108if (glObject && myTagProperty->isSelectable()) {109gSelected.select(glObject->getGlID());110mySelected = true;111}112}113114115void116GNEAttributeCarrier::unselectAttributeCarrier() {117auto glObject = getGUIGlObject();118if (glObject && myTagProperty->isSelectable()) {119gSelected.deselect(glObject->getGlID());120mySelected = false;121}122}123124125bool126GNEAttributeCarrier::isAttributeCarrierSelected() const {127return mySelected;128}129130131bool132GNEAttributeCarrier::drawUsingSelectColor() const {133// first check if element is selected134if (mySelected) {135// get flag for network element136const bool networkElement = myTagProperty->isNetworkElement() || myTagProperty->isAdditionalElement();137// check current supermode138if (networkElement && myNet->getViewNet()->getEditModes().isCurrentSupermodeNetwork()) {139return true;140} else if (myTagProperty->isDemandElement() && myNet->getViewNet()->getEditModes().isCurrentSupermodeDemand()) {141return true;142} else if (myTagProperty->isGenericData() && myNet->getViewNet()->getEditModes().isCurrentSupermodeData()) {143return true;144} else {145return false;146}147} else {148return false;149}150}151152153bool154GNEAttributeCarrier::drawMovingGeometryPoints() const {155// get modes156const auto& modes = myNet->getViewNet()->getEditModes();157// check conditions158if (!myNet->getViewNet()->getMouseButtonKeyPressed().shiftKeyPressed()) {159return false;160} else if (modes.isCurrentSupermodeNetwork() && (modes.networkEditMode == NetworkEditMode::NETWORK_MOVE)) {161return true;162} else if (modes.isCurrentSupermodeDemand() && (modes.demandEditMode == DemandEditMode::DEMAND_MOVE)) {163return true;164} else {165return false;166}167}168169170void171GNEAttributeCarrier::markForDrawingFront() {172myNet->getViewNet()->getMarkFrontElements().markAC(this);173myDrawInFront = true;174}175176177void178GNEAttributeCarrier::unmarkForDrawingFront() {179myNet->getViewNet()->getMarkFrontElements().unmarkAC(this);180myDrawInFront = false;181}182183184bool185GNEAttributeCarrier::isMarkedForDrawingFront() const {186return myDrawInFront;187}188189190void191GNEAttributeCarrier::drawInLayer(double typeOrLayer, const double extraOffset) const {192if (myDrawInFront) {193glTranslated(0, 0, GLO_FRONTELEMENT + extraOffset);194} else {195glTranslated(0, 0, typeOrLayer + extraOffset);196}197}198199200void201GNEAttributeCarrier::setInGrid(bool value) {202myInGrid = value;203}204205206bool207GNEAttributeCarrier::inGrid() const {208return myInGrid;209}210211212bool213GNEAttributeCarrier::checkDrawInspectContour() const {214return myNet->getViewNet()->getInspectedElements().isACInspected(this);215}216217218bool219GNEAttributeCarrier::checkDrawFrontContour() const {220return myDrawInFront;221}222223224void225GNEAttributeCarrier::resetDefaultValues(const bool allowUndoRedo) {226if (allowUndoRedo) {227// reset within undo-redo228const auto undoList = myNet->getUndoList();229undoList->begin(myTagProperty->getGUIIcon(), TLF("reset %", myTagProperty->getTagStr()));230for (const auto& attrProperty : myTagProperty->getAttributeProperties()) {231if ((attrProperty->getAttr() != GNE_ATTR_SAVEFILE) && !attrProperty->isUnique() && attrProperty->hasDefaultValue()) {232setAttribute(attrProperty->getAttr(), attrProperty->getDefaultStringValue(), undoList);233if (attrProperty->isActivatable()) {234if (attrProperty->getDefaultActivated()) {235enableAttribute(attrProperty->getAttr(), undoList);236} else {237disableAttribute(attrProperty->getAttr(), undoList);238}239}240}241}242undoList->end();243} else {244// simply reset every245for (const auto& attrProperty : myTagProperty->getAttributeProperties()) {246if ((attrProperty->getAttr() != GNE_ATTR_SAVEFILE) && attrProperty->hasDefaultValue()) {247setAttribute(attrProperty->getAttr(), attrProperty->getDefaultStringValue());248if (attrProperty->isActivatable()) {249toggleAttribute(attrProperty->getAttr(), attrProperty->getDefaultActivated());250}251}252}253}254}255256257void258GNEAttributeCarrier::enableAttribute(SumoXMLAttr /*key*/, GNEUndoList* /*undoList*/) {259throw ProcessError(TL("Nothing to enable, implement in Children"));260261}262263264void265GNEAttributeCarrier::disableAttribute(SumoXMLAttr /*key*/, GNEUndoList* /*undoList*/) {266throw ProcessError(TL("Nothing to disable, implement in Children"));267}268269270bool271GNEAttributeCarrier::isAttributeEnabled(SumoXMLAttr key) const {272switch (key) {273case GNE_ATTR_SAVEFILE:274if (myTagProperty->saveInNetworkFile() || myTagProperty->saveInParentFile()) {275return false;276} else {277return (myFileBucket != nullptr);278}279default:280return true;281}282}283284285bool286GNEAttributeCarrier::isAttributeComputed(SumoXMLAttr /*key*/) const {287// by default, all attributes aren't computed288return false;289}290291292bool293GNEAttributeCarrier::hasAttribute(SumoXMLAttr key) const {294return myTagProperty->hasAttribute(key);295}296297// canParse functions298299template<> bool300GNEAttributeCarrier::canParse<int>(const std::string& string) {301if (string == "INVALID_INT") {302return true;303} else {304return StringUtils::isInt(string);305}306}307308309template<> bool310GNEAttributeCarrier::canParse<double>(const std::string& string) {311if (string == "INVALID_DOUBLE") {312return true;313} else {314return StringUtils::isDouble(string);315}316}317318319template<> bool320GNEAttributeCarrier::canParse<SUMOTime>(const std::string& string) {321return isTime(string);322}323324325template<> bool326GNEAttributeCarrier::canParse<bool>(const std::string& string) {327return StringUtils::isBool(string);328}329330331template<> bool332GNEAttributeCarrier::canParse<Position>(const std::string& string) {333bool ok = true;334GeomConvHelper::parseShapeReporting(string, "position", 0, ok, true, false);335return ok;336}337338339template<> bool340GNEAttributeCarrier::canParse<SUMOVehicleClass>(const std::string& string) {341return SumoVehicleClassStrings.hasString(string);342}343344345template<> bool346GNEAttributeCarrier::canParse<RGBColor>(const std::string& string) {347return RGBColor::isColor(string);348}349350351template<> bool352GNEAttributeCarrier::canParse<SumoXMLAttr>(const std::string& string) {353return SUMOXMLDefinitions::Attrs.hasString(string);354}355356357template<> bool358GNEAttributeCarrier::canParse<SUMOVehicleShape>(const std::string& string) {359if (string.empty()) {360return true;361} else {362return SumoVehicleShapeStrings.hasString(string);363}364}365366367template<> bool368GNEAttributeCarrier::canParse<PositionVector>(const std::string& string) {369bool ok = true;370GeomConvHelper::parseShapeReporting(string, "shape", 0, ok, true, false);371return ok;372}373374375template<> bool376GNEAttributeCarrier::canParse<std::vector<int> >(const std::string& string) {377if (string.empty()) {378return true;379}380const auto values = StringTokenizer(string).getVector();381for (const auto& value : values) {382if (!canParse<int>(value)) {383return false;384}385}386return true;387}388389390template<> bool391GNEAttributeCarrier::canParse<std::vector<double> >(const std::string& string) {392if (string.empty()) {393return true;394}395const auto values = StringTokenizer(string).getVector();396for (const auto& value : values) {397if (!canParse<double>(value)) {398return false;399}400}401return true;402}403404405template<> bool406GNEAttributeCarrier::canParse<std::vector<bool> >(const std::string& string) {407if (string.empty()) {408return true;409}410const auto values = StringTokenizer(string).getVector();411for (const auto& value : values) {412if (!canParse<bool>(value)) {413return false;414}415}416return true;417}418419420template<> bool421GNEAttributeCarrier::canParse<std::vector<SumoXMLAttr> >(const std::string& string) {422if (string.empty()) {423return true;424}425const auto values = StringTokenizer(string).getVector();426for (const auto& value : values) {427if (!canParse<SumoXMLAttr>(value)) {428return false;429}430}431return true;432}433434// parse functions435436template<> int437GNEAttributeCarrier::parse(const std::string& string) {438if (string == "INVALID_INT") {439return INVALID_INT;440} else {441return StringUtils::toInt(string);442}443}444445446template<> double447GNEAttributeCarrier::parse(const std::string& string) {448if (string == "INVALID_DOUBLE") {449return INVALID_DOUBLE;450} else {451return StringUtils::toDouble(string);452}453}454455456template<> SUMOTime457GNEAttributeCarrier::parse(const std::string& string) {458return string2time(string);459}460461462template<> bool463GNEAttributeCarrier::parse(const std::string& string) {464return StringUtils::toBool(string);465}466467468template<> SUMOVehicleClass469GNEAttributeCarrier::parse(const std::string& string) {470if (string.size() == 0) {471throw EmptyData();472} else if (!SumoVehicleClassStrings.hasString(string)) {473return SVC_IGNORING;474} else {475return SumoVehicleClassStrings.get(string);476}477}478479480template<> RGBColor481GNEAttributeCarrier::parse(const std::string& string) {482if (string.empty()) {483return RGBColor::INVISIBLE;484} else {485return RGBColor::parseColor(string);486}487}488489490template<> Position491GNEAttributeCarrier::parse(const std::string& string) {492// we handle empty strings as position invalids493if (string.size() == 0) {494return Position::INVALID;495} else {496bool ok = true;497PositionVector pos = GeomConvHelper::parseShapeReporting(string, "user-supplied position", 0, ok, false, false);498if (!ok || (pos.size() != 1)) {499throw NumberFormatException("(Position) " + string);500} else {501return pos[0];502}503}504}505506507template<> PositionVector508GNEAttributeCarrier::parse(const std::string& string) {509PositionVector posVector;510// empty string are allowed (It means empty position vector)511if (string.empty()) {512return posVector;513} else {514bool ok = true;515posVector = GeomConvHelper::parseShapeReporting(string, "user-supplied shape", 0, ok, false, true);516if (!ok) {517throw NumberFormatException("(Position List) " + string);518} else {519return posVector;520}521}522}523524525template<> SUMOVehicleShape526GNEAttributeCarrier::parse(const std::string& string) {527if (string.empty()) {528return SUMOVehicleShape::UNKNOWN;529} else {530return SumoVehicleShapeStrings.get(string);531}532}533534535template<> std::vector<std::string>536GNEAttributeCarrier::parse(const std::string& string) {537return StringTokenizer(string).getVector();538}539540541template<> std::set<std::string>542GNEAttributeCarrier::parse(const std::string& string) {543const auto vectorString = StringTokenizer(string).getVector();544std::set<std::string> solution;545for (const auto& stringValue : vectorString) {546solution.insert(stringValue);547}548return solution;549}550551552template<> std::vector<int>553GNEAttributeCarrier::parse(const std::string& string) {554const auto vectorInt = parse<std::vector<std::string> >(string);555std::vector<int> parsedIntValues;556for (const auto& intValue : vectorInt) {557parsedIntValues.push_back(parse<int>(intValue));558}559return parsedIntValues;560}561562563template<> std::vector<double>564GNEAttributeCarrier::parse(const std::string& string) {565const auto vectorDouble = parse<std::vector<std::string> >(string);566std::vector<double> parsedDoubleValues;567for (const auto& doubleValue : vectorDouble) {568parsedDoubleValues.push_back(parse<double>(doubleValue));569}570return parsedDoubleValues;571}572573574template<> std::vector<bool>575GNEAttributeCarrier::parse(const std::string& string) {576const auto vectorBool = parse<std::vector<std::string> >(string);577std::vector<bool> parsedBoolValues;578for (const auto& boolValue : vectorBool) {579parsedBoolValues.push_back(parse<bool>(boolValue));580}581return parsedBoolValues;582}583584585template<> std::vector<SumoXMLAttr>586GNEAttributeCarrier::parse(const std::string& value) {587// Declare string vector588const auto attributesStr = parse<std::vector<std::string> > (value);589std::vector<SumoXMLAttr> attributes;590// Iterate over lanes IDs, retrieve Lanes and add it into parsedLanes591for (const auto& attributeStr : attributesStr) {592if (SUMOXMLDefinitions::Attrs.hasString(attributeStr)) {593attributes.push_back(static_cast<SumoXMLAttr>(SUMOXMLDefinitions::Attrs.get(attributeStr)));594} else {595throw FormatException("Error parsing attributes. Attribute '" + attributeStr + "' doesn't exist");596}597}598return attributes;599}600601// can parse (network) functions602603template<> bool604GNEAttributeCarrier::canParse<std::vector<GNEEdge*> >(const GNENet* net, const std::string& value, const bool checkConsecutivity) {605// Declare string vector606const auto edgeIds = parse<std::vector<std::string> > (value);607std::vector<GNEEdge*> parsedEdges;608parsedEdges.reserve(edgeIds.size());609for (const auto& edgeID : edgeIds) {610const auto edge = net->getAttributeCarriers()->retrieveEdge(edgeID, false);611if (edge == nullptr) {612return false;613} else if (checkConsecutivity) {614if ((parsedEdges.size() > 0) && (parsedEdges.back()->getToJunction() != edge->getFromJunction())) {615return false;616}617parsedEdges.push_back(edge);618}619}620return true;621}622623624template<> bool625GNEAttributeCarrier::canParse<std::vector<GNELane*> >(const GNENet* net, const std::string& value, const bool checkConsecutivity) {626// Declare string vector627const auto laneIds = parse<std::vector<std::string> > (value);628std::vector<GNELane*> parsedLanes;629parsedLanes.reserve(laneIds.size());630// Iterate over lanes IDs, retrieve Lanes and add it into parsedLanes631for (const auto& laneID : laneIds) {632const auto lane = net->getAttributeCarriers()->retrieveLane(laneID, false);633if (lane == nullptr) {634return false;635} else if (checkConsecutivity) {636if ((parsedLanes.size() > 0) && (parsedLanes.back()->getParentEdge()->getToJunction() != lane->getParentEdge()->getFromJunction())) {637return false;638}639parsedLanes.push_back(lane);640}641}642return true;643}644645// parse (network) functions646647template<> std::vector<GNEEdge*>648GNEAttributeCarrier::parse(const GNENet* net, const std::string& value) {649// Declare string vector650const auto edgeIds = parse<std::vector<std::string> > (value);651std::vector<GNEEdge*> parsedEdges;652parsedEdges.reserve(edgeIds.size());653// Iterate over edges IDs, retrieve Edges and add it into parsedEdges654for (const auto& edgeID : edgeIds) {655parsedEdges.push_back(net->getAttributeCarriers()->retrieveEdge(edgeID));656}657return parsedEdges;658}659660661template<> std::vector<GNELane*>662GNEAttributeCarrier::parse(const GNENet* net, const std::string& value) {663// Declare string vector664const auto laneIds = parse<std::vector<std::string> > (value);665std::vector<GNELane*> parsedLanes;666parsedLanes.reserve(laneIds.size());667// Iterate over lanes IDs, retrieve Lanes and add it into parsedLanes668for (const auto& laneID : laneIds) {669parsedLanes.push_back(net->getAttributeCarriers()->retrieveLane(laneID));670}671return parsedLanes;672}673674// parse ID functions675676template<> std::string677GNEAttributeCarrier::parseIDs(const std::vector<GNEEdge*>& ACs) {678// obtain ID's of edges and return their join679std::vector<std::string> edgeIDs;680for (const auto& AC : ACs) {681edgeIDs.push_back(AC->getID());682}683return joinToString(edgeIDs, " ");684}685686687template<> std::string688GNEAttributeCarrier::parseIDs(const std::vector<GNELane*>& ACs) {689// obtain ID's of lanes and return their join690std::vector<std::string> laneIDs;691for (const auto& AC : ACs) {692laneIDs.push_back(AC->getID());693}694return joinToString(laneIDs, " ");695}696697void698GNEAttributeCarrier::setACParameters(const std::vector<std::pair<std::string, std::string> >& parameters) {699// declare result string700std::string paramsStr;701// Generate an string using the following structure: "key1=value1|key2=value2|...702for (const auto& parameter : parameters) {703paramsStr += parameter.first + "=" + parameter.second + "|";704}705// remove the last "|"706if (!paramsStr.empty()) {707paramsStr.pop_back();708}709// set parameters710setAttribute(GNE_ATTR_PARAMETERS, paramsStr);711}712713714void715GNEAttributeCarrier::setACParameters(const std::vector<std::pair<std::string, std::string> >& parameters, GNEUndoList* undoList) {716// declare parametersMap717Parameterised::Map parametersMap;718// Generate an string using the following structure: "key1=value1|key2=value2|...719for (const auto& parameter : parameters) {720parametersMap[parameter.first] = parameter.second;721}722// set setACParameters map723setACParameters(parametersMap, undoList);724}725726727void728GNEAttributeCarrier::setACParameters(const Parameterised::Map& parameters, GNEUndoList* undoList) {729// declare result string730std::string paramsStr;731// Generate an string using the following structure: "key1=value1|key2=value2|...732for (const auto& parameter : parameters) {733paramsStr += parameter.first + "=" + parameter.second + "|";734}735// remove the last "|"736if (!paramsStr.empty()) {737paramsStr.pop_back();738}739// set parameters740setAttribute(GNE_ATTR_PARAMETERS, paramsStr, undoList);741}742743744std::string745GNEAttributeCarrier::getAlternativeValueForDisabledAttributes(SumoXMLAttr key) const {746switch (key) {747// Crossings748case SUMO_ATTR_TLLINKINDEX:749case SUMO_ATTR_TLLINKINDEX2:750return "No TLS";751// connections752case SUMO_ATTR_DIR: {753// special case for connection directions754std::string direction = getAttribute(key);755if (direction == "s") {756return "Straight (s)";757} else if (direction == "t") {758return "Turn (t))";759} else if (direction == "l") {760return "Left (l)";761} else if (direction == "r") {762return "Right (r)";763} else if (direction == "L") {764return "Partially left (L)";765} else if (direction == "R") {766return "Partially right (R)";767} else if (direction == "invalid") {768return "No direction (Invalid))";769} else {770return "undefined";771}772}773case SUMO_ATTR_STATE: {774// special case for connection states775std::string state = getAttribute(key);776if (state == "-") {777return "Dead end (-)";778} else if (state == "=") {779return "equal (=)";780} else if (state == "m") {781return "Minor link (m)";782} else if (state == "M") {783return "Major link (M)";784} else if (state == "O") {785return "TLS controller off (O)";786} else if (state == "o") {787return "TLS yellow flashing (o)";788} else if (state == "y") {789return "TLS yellow minor link (y)";790} else if (state == "Y") {791return "TLS yellow major link (Y)";792} else if (state == "r") {793return "TLS red (r)";794} else if (state == "g") {795return "TLS green minor (g)";796} else if (state == "G") {797return "TLS green major (G)";798} else if (state == "Z") {799return "Zipper (Z)";800} else {801return "undefined";802}803}804default:805return getAttribute(key);806}807}808809810std::string811GNEAttributeCarrier::getAttributeForSelection(SumoXMLAttr key) const {812return getAttribute(key);813}814815816const std::string&817GNEAttributeCarrier::getTagStr() const {818return myTagProperty->getTagStr();819}820821822FXIcon*823GNEAttributeCarrier::getACIcon() const {824// special case for vClass icons825if (myTagProperty->vClassIcon()) {826return VClassIcons::getVClassIcon(SumoVehicleClassStrings.get(getAttribute(SUMO_ATTR_VCLASS)));827} else {828return GUIIconSubSys::getIcon(myTagProperty->getGUIIcon());829}830}831832833bool834GNEAttributeCarrier::isTemplate() const {835return myIsTemplate;836}837838839const GNETagProperties*840GNEAttributeCarrier::getTagProperty() const {841return myTagProperty;842}843844845std::string846GNEAttributeCarrier::getCommonAttribute(SumoXMLAttr key) const {847switch (key) {848case GNE_ATTR_SAVEFILE:849if (myFileBucket) {850return getFileBucket()->getFilename();851} else {852return TL("Parent filename");853}854case GNE_ATTR_CENTER_AFTER_CREATION:855return toString(myCenterAfterCreation);856case GNE_ATTR_SELECTED:857if (mySelected) {858return TRUE_STR;859} else {860return FALSE_STR;861}862case GNE_ATTR_FRONTELEMENT:863if (myDrawInFront) {864return TRUE_STR;865} else {866return FALSE_STR;867}868case GNE_ATTR_PARAMETERS:869if (getParameters()) {870return getParameters()->getParametersStr();871} else {872throw InvalidArgument(getTagStr() + " doesn't support parameters");873}874default:875throw InvalidArgument(getTagStr() + " doesn't have a common attribute of type '" + toString(key) + "'");876}877}878879880double881GNEAttributeCarrier::getCommonAttributeDouble(SumoXMLAttr key) const {882throw InvalidArgument(getTagStr() + " doesn't have a common double attribute of type '" + toString(key) + "'");883}884885886Position887GNEAttributeCarrier::getCommonAttributePosition(SumoXMLAttr key) const {888throw InvalidArgument(getTagStr() + " doesn't have a common position attribute of type '" + toString(key) + "'");889}890891892PositionVector893GNEAttributeCarrier::getCommonAttributePositionVector(SumoXMLAttr key) const {894throw InvalidArgument(getTagStr() + " doesn't have a common positionVector attribute of type '" + toString(key) + "'");895}896897898void899GNEAttributeCarrier::setCommonAttribute(SumoXMLAttr key, const std::string& value, GNEUndoList* undoList) {900switch (key) {901case GNE_ATTR_SAVEFILE:902case GNE_ATTR_CENTER_AFTER_CREATION:903case GNE_ATTR_SELECTED:904case GNE_ATTR_PARAMETERS:905GNEChange_Attribute::changeAttribute(this, key, value, undoList);906break;907default:908throw InvalidArgument(getTagStr() + " doesn't have an attribute of type '" + toString(key) + "'");909}910}911912913bool914GNEAttributeCarrier::isCommonAttributeValid(SumoXMLAttr key, const std::string& value) const {915switch (key) {916case GNE_ATTR_SAVEFILE:917if (SUMOXMLDefinitions::isValidFilename(value)) {918return myNet->getGNEApplicationWindow()->getFileBucketHandler()->checkFilename(this, value);919} else {920return false;921}922case GNE_ATTR_CENTER_AFTER_CREATION:923case GNE_ATTR_SELECTED:924return canParse<bool>(value);925case GNE_ATTR_PARAMETERS:926return Parameterised::areParametersValid(value);927default:928throw InvalidArgument(getTagStr() + " doesn't have an attribute of type '" + toString(key) + "'");929}930}931932933void934GNEAttributeCarrier::setCommonAttribute(SumoXMLAttr key, const std::string& value) {935switch (key) {936case GNE_ATTR_SAVEFILE:937myFileBucket = myNet->getGNEApplicationWindow()->getFileBucketHandler()->updateAC(this, value);938break;939case GNE_ATTR_CENTER_AFTER_CREATION:940myCenterAfterCreation = parse<bool>(value);941break;942case GNE_ATTR_SELECTED:943if (parse<bool>(value)) {944selectAttributeCarrier();945} else {946unselectAttributeCarrier();947}948break;949case GNE_ATTR_PARAMETERS:950if (getParameters()) {951getParameters()->setParametersStr(value);952} else {953throw InvalidArgument(getTagStr() + " doesn't support parameters");954}955break;956default:957throw InvalidArgument(getTagStr() + " doesn't have an attribute of type '" + toString(key) + "'");958}959}960961// ===========================================================================962// private963// ===========================================================================964965void966GNEAttributeCarrier::toggleAttribute(SumoXMLAttr /*key*/, const bool /*value*/) {967throw ProcessError(TL("Nothing to toggle, implement in Children"));968}969970/****************************************************************************/971972973