//---------------------------------------------------------------------------- // EgalTech 2014-2014 //---------------------------------------------------------------------------- // File : Attribs.cpp Data : 05.03.14 Versione : 1.5c1 // Contenuto : Implementazione della classe Attribs. // // // // Modifiche : 05.03.14 DS Creazione modulo. // // //---------------------------------------------------------------------------- //--------------------------- Include ---------------------------------------- #include "stdafx.h" #include "Attribs.h" #include "NgeWriter.h" #include "NgeReader.h" #include "GeomDB.h" #include "/EgtDev/Include/EGnStringUtils.h" #include "/EgtDev/Include/EGkStringUtils3d.h" using namespace std ; //---------------------------------------------------------------------------- static const string NAME = "N" ; static const char EQUAL = '=' ; //---------------------------------------------------------------------------- bool Attribs::Dump( const GeomDB& GDB, string& sOut, const char* szNewLine) const { // livello sOut += "Lev=" ; switch ( m_Data[LEVEL]) { default : /* GDB_LV_USER */ sOut += "user" ; break ; case GDB_LV_SYSTEM : sOut += "system" ; break ; case GDB_LV_TEMP : sOut += "temp" ; break ; } // modo sOut += " Mod=" ; switch ( m_Data[MODE]) { default : /* GDB_MD_STD */ sOut += "std" ; break ; case GDB_MD_LOCKED : sOut += "locked" ; break ; case GDB_MD_HIDDEN : sOut += "hidden" ; break ; } // stato sOut += " Sta=" ; switch ( m_Data[STATUS]) { case GDB_ST_OFF : sOut += "off" ; break ; default : /* GDB_ST_ON */ sOut += "on" ; break ; case GDB_ST_SEL : sOut += "sel" ; break ; } sOut += szNewLine ; // materiale sOut += "Mat=" ; switch ( m_Material) { case GDB_MT_COLOR : sOut += "color" ; break ; case GDB_MT_PARENT : sOut += "by parent" ; break ; } // eventuale colore if ( m_Material == GDB_MT_COLOR) { sOut += " Col=" ; string sColName ; if ( GetNameOfStdColor( m_Color, sColName)) sOut += sColName ; sOut += "(" + ToString( m_Color.GetIntRed()) ; sOut += "," + ToString( m_Color.GetIntGreen()) ; sOut += "," + ToString( m_Color.GetIntBlue()) ; if ( m_Color.GetIntAlpha() != 100) sOut += "," + ToString( m_Color.GetIntAlpha()) ; sOut += ")" ; } // eventuale materiale else if ( m_Material > GDB_MT_PARENT) { string sMatName ; if ( GDB.GetMaterialName( m_Material, sMatName)) sOut += " " + sMatName ; else sOut += " ??" ; sOut += " (" + ToString( m_Material) + ")" ; } sOut += szNewLine ; // eventuali nome e stringhe informative STRLIST::const_iterator iIter ; for ( iIter = m_slInfo.begin() ; iIter != m_slInfo.end() ; ++ iIter) sOut += *iIter + szNewLine ; return true ; } //---------------------------------------------------------------------------- bool Attribs::Save( NgeWriter& ngeOut) const { // flag presenza attributi if ( ! ngeOut.WriteKey( NGE_A)) return false ; // livello if ( ! ngeOut.WriteUchar( m_Data[LEVEL], ",")) return false ; // modo if ( ! ngeOut.WriteUchar( m_Data[MODE], ",")) return false ; // stato (se SEL è convertito in ON) int nStat = (( m_Data[STATUS] > GDB_ST_ON) ? GDB_ST_ON : m_Data[STATUS]) ; if ( ! ngeOut.WriteUchar( nStat, ",")) return false ; // marcatura (sempre OFF) if ( ! ngeOut.WriteUchar( GDB_MK_OFF, ";")) return false ; // materiale if ( ! ngeOut.WriteInt( m_Material, ";")) return false ; // colore if ( ! ngeOut.WriteCol( m_Color, ";")) return false ; // numero di stringhe di info (nelle linee successive) if ( ! ngeOut.WriteInt( int( m_slInfo.size()), ";", true)) return false ; // stringhe di info STRLIST::const_iterator iIter ; for ( iIter = m_slInfo.begin() ; iIter != m_slInfo.end() ; ++ iIter) { if ( ! ngeOut.WriteString( *iIter, nullptr, true)) return false ; } return true ; } //---------------------------------------------------------------------------- bool Attribs::Load( NgeReader& ngeIn) { // livello unsigned char ucLev ; if ( ! ngeIn.ReadUchar( ucLev, ",")) return false ; m_Data[LEVEL] = CLIP( ucLev, GDB_LV_USER, GDB_LV_TEMP) ; // modo unsigned char ucMode ; if ( ! ngeIn.ReadUchar( ucMode, ",")) return false ; m_Data[MODE] = CLIP( ucMode, GDB_MD_STD, GDB_MD_HIDDEN) ; // stato (se SEL è convertito in ON) unsigned char ucStat ; if ( ! ngeIn.ReadUchar( ucStat, ",")) return false ; m_Data[STATUS] = CLIP( ucStat, GDB_ST_OFF, GDB_ST_ON) ; // marcatura (sempre OFF) unsigned char ucMark ; if ( ! ngeIn.ReadUchar( ucMark, ";")) return false ; m_Data[MARK] = CLIP( ucMark, GDB_MK_OFF, GDB_MK_OFF) ; // materiale if ( ! ngeIn.ReadInt( m_Material, ";")) return false ; // colore if ( ! ngeIn.ReadCol( m_Color, ";")) return false ; // numero di stringhe di info (nelle linee successive) int nNext ; if ( ! ngeIn.ReadInt( nNext, ";", true)) return false ; // leggo le eventuali stringhe string sLine ; for ( int i = 0 ; i < nNext ; ++i) { // leggo la linea if ( ! ngeIn.ReadString( sLine, nullptr, true)) return false ; // la carico in lista m_slInfo.push_back( sLine) ; } return true ; } //---------------------------------------------------------------------------- bool Attribs::DataFromString( const string& sParam) { // il primo parametro è diviso in 4 parti STRVECTOR vsParams ; Tokenize( sParam, ",", vsParams) ; // 4 parti if ( vsParams.size() != 4) return false ; // livello int nLev ; if ( ! FromString( vsParams[0], nLev)) return false ; m_Data[LEVEL] = CLIP( nLev, GDB_LV_USER, GDB_LV_TEMP) ; // modo int nMode ; if ( ! FromString( vsParams[1], nMode)) return false ; m_Data[MODE] = CLIP( nMode, GDB_MD_STD, GDB_MD_HIDDEN) ; // stato (ammessi solo OFF e ON) int nStat ; if ( ! FromString( vsParams[2], nStat)) return false ; m_Data[STATUS] = CLIP( nStat, GDB_ST_OFF, GDB_ST_ON) ; // marcatura (ammesso solo OFF) int nMark ; if ( ! FromString( vsParams[3], nMark)) return false ; m_Data[MARK] = CLIP( nMark, GDB_MK_OFF, GDB_MK_OFF) ; return true ; } //---------------------------------------------------------------------------- bool Attribs::SetName( const string& sName) { // se nome non valido, esco con errore if ( ! IsValidString( sName) || ! IsValidName( sName)) return false ; // può essere solo la prima stringa STRLIST::iterator iIter ; if ( ( iIter = m_slInfo.begin()) != m_slInfo.end() && FindKey( *iIter, NAME)) { *iIter = NAME + EQUAL + sName ; return true ; } // altrimenti devo inserire la stringa prima dell'inizio try { m_slInfo.push_front( NAME + EQUAL + sName) ; } catch(...) { return false ; } return true ; } //---------------------------------------------------------------------------- bool Attribs::GetName( string& sName) const { // può essere solo la prima stringa STRLIST::const_iterator iIter ; if ( ( iIter = m_slInfo.begin()) != m_slInfo.end() && FindKey( *iIter, NAME)) { sName = iIter->substr( NAME.length() + 1) ; return true ; } return false ; } //---------------------------------------------------------------------------- bool Attribs::ExistsName( void) const { // può essere solo la prima stringa STRLIST::const_iterator iIter ; if ( ( iIter = m_slInfo.begin()) != m_slInfo.end() && FindKey( *iIter, NAME)) return true ; return false ; } //---------------------------------------------------------------------------- bool Attribs::RemoveName( void) { // può essere solo la prima stringa STRLIST::const_iterator iIter ; if ( ( iIter = m_slInfo.begin()) != m_slInfo.end() && FindKey( *iIter, NAME)) { m_slInfo.pop_front() ; return true ; } // non trovato, il nome non richiede rimozione return true ; } //---------------------------------------------------------------------------- bool Attribs::SetInfo( const string& sKey, const string& sVal) { // se chiave o valore non validi, esco con errore if ( ! IsValidString( sKey) || ! IsValidString( sVal)) return false ; // se è il nome if ( sKey == NAME) return SetName( sVal) ; // se esiste già una stringa con quella chiave la sostituisco STRLIST::iterator iIter ; for ( iIter = m_slInfo.begin() ; iIter != m_slInfo.end() ; ++ iIter) { if ( FindKey( *iIter, sKey)) { *iIter = sKey + EQUAL + sVal ; return true ; } } // altrimenti la appendo try { m_slInfo.push_back( sKey + EQUAL + sVal) ; } catch(...) { return false ; } return true ; } //---------------------------------------------------------------------------- bool Attribs::GetInfo( const string& sKey, string& sVal) const { // se chiave non valida, esco con errore if ( ! IsValidString( sKey)) return false ; // cerco una stringa con la chiave STRLIST::const_iterator iIter ; for ( iIter = m_slInfo.begin() ; iIter != m_slInfo.end() ; ++ iIter) { if ( FindKey( *iIter, sKey)) { sVal = iIter->substr( sKey.length() + 1) ; ; return true ; } } return false ; } //---------------------------------------------------------------------------- bool Attribs::ExistsInfo( const string& sKey) const { // se chiave non valida, esco con errore if ( ! IsValidString( sKey)) return false ; // cerco una stringa con la chiave STRLIST::const_iterator iIter ; for ( iIter = m_slInfo.begin() ; iIter != m_slInfo.end() ; ++ iIter) { if ( FindKey( *iIter, sKey)) return true ; } return false ; } //---------------------------------------------------------------------------- bool Attribs::RemoveInfo( const string& sKey) { // se chiave non valida, esco con errore if ( ! IsValidString( sKey)) return false ; // cerco una stringa con la chiave STRLIST::iterator iIter ; for ( iIter = m_slInfo.begin() ; iIter != m_slInfo.end() ; ++ iIter) { if ( FindKey( *iIter, sKey)) { m_slInfo.erase( iIter) ; return true ; } } // non trovata, la info non richiede rimozione return true ; } //---------------------------------------------------------------------------- bool Attribs::FindKey( const string& sString, const string& sKey) const { return ( sString.compare( 0, sKey.length(), sKey) == 0 && sString.length() > sKey.length() && sString[sKey.length()] == EQUAL) ; } //---------------------------------------------------------------------------- bool Attribs::IsValidString( const string& sString) const { return ( ! sString.empty() && sString.find( '\n') == string::npos && sString.find_first_not_of( " \t\r\n") != string::npos) ; }