diff --git a/tinyxml2.cpp b/tinyxml2.cpp index bfd8d1f..7a804f5 100755 --- a/tinyxml2.cpp +++ b/tinyxml2.cpp @@ -556,6 +556,12 @@ void XMLUtil::ToStr( double v, char* buffer, int bufferSize ) } +void XMLUtil::ToStr(int64_t v, char* buffer, int bufferSize) +{ + TIXML_SNPRINTF(buffer, bufferSize, "%lld", v); +} + + bool XMLUtil::ToInt( const char* str, int* value ) { if ( TIXML_SSCANF( str, "%d", value ) == 1 ) { @@ -599,6 +605,7 @@ bool XMLUtil::ToFloat( const char* str, float* value ) return false; } + bool XMLUtil::ToDouble( const char* str, double* value ) { if ( TIXML_SSCANF( str, "%lf", value ) == 1 ) { @@ -608,6 +615,15 @@ bool XMLUtil::ToDouble( const char* str, double* value ) } +bool XMLUtil::ToInt64(const char* str, int64_t* value) +{ + if (TIXML_SSCANF(str, "%lld", value) == 1) { + return true; + } + return false; +} + + char* XMLDocument::Identify( char* p, XMLNode** node ) { TIXMLASSERT( node ); @@ -1301,6 +1317,15 @@ XMLError XMLAttribute::QueryUnsignedValue( unsigned int* value ) const } +XMLError XMLAttribute::QueryInt64Value(int64_t* value) const +{ + if (XMLUtil::ToInt64(Value(), value)) { + return XML_SUCCESS; + } + return XML_WRONG_ATTRIBUTE_TYPE; +} + + XMLError XMLAttribute::QueryBoolValue( bool* value ) const { if ( XMLUtil::ToBool( Value(), value )) { @@ -1350,6 +1375,15 @@ void XMLAttribute::SetAttribute( unsigned v ) } +void XMLAttribute::SetAttribute(int64_t v) +{ + char buf[BUF_SIZE]; + XMLUtil::ToStr(v, buf, BUF_SIZE); + _value.SetStr(buf); +} + + + void XMLAttribute::SetAttribute( bool v ) { char buf[BUF_SIZE]; @@ -1450,7 +1484,15 @@ void XMLElement::SetText( unsigned v ) } -void XMLElement::SetText( bool v ) +void XMLElement::SetText(int64_t v) +{ + char buf[BUF_SIZE]; + XMLUtil::ToStr(v, buf, BUF_SIZE); + SetText(buf); +} + + +void XMLElement::SetText( bool v ) { char buf[BUF_SIZE]; XMLUtil::ToStr( v, buf, BUF_SIZE ); @@ -1500,6 +1542,19 @@ XMLError XMLElement::QueryUnsignedText( unsigned* uval ) const } +XMLError XMLElement::QueryInt64Text(int64_t* ival) const +{ + if (FirstChild() && FirstChild()->ToText()) { + const char* t = FirstChild()->Value(); + if (XMLUtil::ToInt64(t, ival)) { + return XML_SUCCESS; + } + return XML_CAN_NOT_CONVERT_TEXT; + } + return XML_NO_TEXT_NODE; +} + + XMLError XMLElement::QueryBoolText( bool* bval ) const { if ( FirstChild() && FirstChild()->ToText() ) { @@ -2263,6 +2318,14 @@ void XMLPrinter::PushAttribute( const char* name, unsigned v ) } +void XMLPrinter::PushAttribute(const char* name, int64_t v) +{ + char buf[BUF_SIZE]; + XMLUtil::ToStr(v, buf, BUF_SIZE); + PushAttribute(name, buf); +} + + void XMLPrinter::PushAttribute( const char* name, bool v ) { char buf[BUF_SIZE]; diff --git a/tinyxml2.h b/tinyxml2.h index 0fe2cdd..0c15ee8 100755 --- a/tinyxml2.h +++ b/tinyxml2.h @@ -30,6 +30,7 @@ distribution. # include # include # include +# include # if defined(__PS3__) # include # endif @@ -39,6 +40,7 @@ distribution. # include # include # include +# include #endif /* @@ -577,6 +579,7 @@ public: static void ToStr( bool v, char* buffer, int bufferSize ); static void ToStr( float v, char* buffer, int bufferSize ); static void ToStr( double v, char* buffer, int bufferSize ); + static void ToStr(int64_t v, char* buffer, int bufferSize); // converts strings to primitive types static bool ToInt( const char* str, int* value ); @@ -584,6 +587,7 @@ public: static bool ToBool( const char* str, bool* value ); static bool ToFloat( const char* str, float* value ); static bool ToDouble( const char* str, double* value ); + static bool ToInt64(const char* str, int64_t* value); }; @@ -1061,11 +1065,18 @@ public: If the value isn't an integer, 0 will be returned. There is no error checking; use QueryIntValue() if you need error checking. */ - int IntValue() const { - int i=0; - QueryIntValue( &i ); - return i; - } + int IntValue() const { + int i = 0; + QueryIntValue(&i); + return i; + } + + int64_t Int64Value() const { + int64_t i = 0; + QueryInt64Value(&i); + return i; + } + /// Query as an unsigned integer. See IntValue() unsigned UnsignedValue() const { unsigned i=0; @@ -1098,7 +1109,9 @@ public: XMLError QueryIntValue( int* value ) const; /// See QueryIntValue XMLError QueryUnsignedValue( unsigned int* value ) const; - /// See QueryIntValue + /// See QueryIntValue + XMLError QueryInt64Value(int64_t* value) const; + /// See QueryIntValue XMLError QueryBoolValue( bool* value ) const; /// See QueryIntValue XMLError QueryDoubleValue( double* value ) const; @@ -1111,7 +1124,9 @@ public: void SetAttribute( int value ); /// Set the attribute to value. void SetAttribute( unsigned value ); - /// Set the attribute to value. + /// Set the attribute to value. + void SetAttribute(int64_t value); + /// Set the attribute to value. void SetAttribute( bool value ); /// Set the attribute to value. void SetAttribute( double value ); @@ -1197,26 +1212,35 @@ public: QueryIntAttribute( name, &i ); return i; } + /// See IntAttribute() unsigned UnsignedAttribute( const char* name ) const { unsigned i=0; QueryUnsignedAttribute( name, &i ); return i; } - /// See IntAttribute() - bool BoolAttribute( const char* name ) const { + + /// See IntAttribute() + int64_t Int64Attribute(const char* name) const { + int64_t i = 0; + QueryInt64Attribute(name, &i); + return i; + } + + /// See IntAttribute() + bool BoolAttribute( const char* name ) const { bool b=false; QueryBoolAttribute( name, &b ); return b; } /// See IntAttribute() - double DoubleAttribute( const char* name ) const { + double DoubleAttribute( const char* name ) const { double d=0; QueryDoubleAttribute( name, &d ); return d; } /// See IntAttribute() - float FloatAttribute( const char* name ) const { + float FloatAttribute( const char* name ) const { float f=0; QueryFloatAttribute( name, &f ); return f; @@ -1242,7 +1266,8 @@ public: } return a->QueryIntValue( value ); } - /// See QueryIntAttribute() + + /// See QueryIntAttribute() XMLError QueryUnsignedAttribute( const char* name, unsigned int* value ) const { const XMLAttribute* a = FindAttribute( name ); if ( !a ) { @@ -1250,7 +1275,17 @@ public: } return a->QueryUnsignedValue( value ); } - /// See QueryIntAttribute() + + /// See QueryIntAttribute() + XMLError QueryInt64Attribute(const char* name, int64_t* value) const { + const XMLAttribute* a = FindAttribute(name); + if (!a) { + return XML_NO_ATTRIBUTE; + } + return a->QueryInt64Value(value); + } + + /// See QueryIntAttribute() XMLError QueryBoolAttribute( const char* name, bool* value ) const { const XMLAttribute* a = FindAttribute( name ); if ( !a ) { @@ -1301,6 +1336,10 @@ public: return QueryUnsignedAttribute( name, value ); } + int QueryAttribute(const char* name, int64_t* value) const { + return QueryInt64Attribute(name, value); + } + int QueryAttribute( const char* name, bool* value ) const { return QueryBoolAttribute( name, value ); } @@ -1328,7 +1367,14 @@ public: XMLAttribute* a = FindOrCreateAttribute( name ); a->SetAttribute( value ); } - /// Sets the named attribute to value. + + /// Sets the named attribute to value. + void SetAttribute(const char* name, int64_t value) { + XMLAttribute* a = FindOrCreateAttribute(name); + a->SetAttribute(value); + } + + /// Sets the named attribute to value. void SetAttribute( const char* name, bool value ) { XMLAttribute* a = FindOrCreateAttribute( name ); a->SetAttribute( value ); @@ -1425,7 +1471,9 @@ public: void SetText( int value ); /// Convenience method for setting text inside an element. See SetText() for important limitations. void SetText( unsigned value ); - /// Convenience method for setting text inside an element. See SetText() for important limitations. + /// Convenience method for setting text inside an element. See SetText() for important limitations. + void SetText(int64_t value); + /// Convenience method for setting text inside an element. See SetText() for important limitations. void SetText( bool value ); /// Convenience method for setting text inside an element. See SetText() for important limitations. void SetText( double value ); @@ -1461,7 +1509,9 @@ public: XMLError QueryIntText( int* ival ) const; /// See QueryIntText() XMLError QueryUnsignedText( unsigned* uval ) const; - /// See QueryIntText() + /// See QueryIntText() + XMLError QueryInt64Text(int64_t* uval) const; + /// See QueryIntText() XMLError QueryBoolText( bool* bval ) const; /// See QueryIntText() XMLError QueryDoubleText( double* dval ) const; @@ -1998,7 +2048,8 @@ public: void PushAttribute( const char* name, const char* value ); void PushAttribute( const char* name, int value ); void PushAttribute( const char* name, unsigned value ); - void PushAttribute( const char* name, bool value ); + void PushAttribute(const char* name, int64_t value); + void PushAttribute( const char* name, bool value ); void PushAttribute( const char* name, double value ); /// If streaming, close the Element. virtual void CloseElement( bool compactMode=false ); @@ -2009,7 +2060,9 @@ public: void PushText( int value ); /// Add a text node from an unsigned. void PushText( unsigned value ); - /// Add a text node from a bool. + /// Add a text node from an unsigned. + void PushText(int64_t value); + /// Add a text node from a bool. void PushText( bool value ); /// Add a text node from a float. void PushText( float value ); diff --git a/xmltest.cpp b/xmltest.cpp index 78f072c..2009d1a 100644 --- a/xmltest.cpp +++ b/xmltest.cpp @@ -686,6 +686,107 @@ int main( int argc, const char ** argv ) XMLTest( "SetText types", "1.5", element->GetText() ); } + // ---------- Attributes --------- + { + static const int64_t BIG = -123456789012345678; + XMLDocument doc; + XMLElement* element = doc.NewElement("element"); + doc.InsertFirstChild(element); + + { + element->SetAttribute("attrib", int(-100)); + int v = 0; + element->QueryIntAttribute("attrib", &v); + XMLTest("Attribute: int", -100, v, true); + element->QueryAttribute("attrib", &v); + XMLTest("Attribute: int", -100, v, true); + } + { + element->SetAttribute("attrib", unsigned(100)); + unsigned v = 0; + element->QueryUnsignedAttribute("attrib", &v); + XMLTest("Attribute: unsigned", unsigned(100), v, true); + element->QueryAttribute("attrib", &v); + XMLTest("Attribute: unsigned", unsigned(100), v, true); + } + { + element->SetAttribute("attrib", BIG); + int64_t v = 0; + element->QueryInt64Attribute("attrib", &v); + XMLTest("Attribute: int64_t", BIG, v, true); + element->QueryAttribute("attrib", &v); + XMLTest("Attribute: int64_t", BIG, v, true); + } + { + element->SetAttribute("attrib", true); + bool v = false; + element->QueryBoolAttribute("attrib", &v); + XMLTest("Attribute: bool", true, v, true); + element->QueryAttribute("attrib", &v); + XMLTest("Attribute: bool", true, v, true); + } + { + element->SetAttribute("attrib", 100.0); + double v = 0; + element->QueryDoubleAttribute("attrib", &v); + XMLTest("Attribute: double", 100.0, v, true); + element->QueryAttribute("attrib", &v); + XMLTest("Attribute: double", 100.0, v, true); + } + { + element->SetAttribute("attrib", 100.0f); + float v = 0; + element->QueryFloatAttribute("attrib", &v); + XMLTest("Attribute: float", 100.0f, v, true); + element->QueryAttribute("attrib", &v); + XMLTest("Attribute: float", 100.0f, v, true); + } + { + element->SetText(BIG); + int64_t v = 0; + element->QueryInt64Text(&v); + XMLTest("Element: int64_t", BIG, v, true); + } + } + + // ---------- XMLPrinter stream mode ------ + { + { + FILE* printerfp = fopen("resources/printer.xml", "w"); + XMLPrinter printer(printerfp); + printer.OpenElement("foo"); + printer.PushAttribute("attrib-text", "text"); + printer.PushAttribute("attrib-int", int(1)); + printer.PushAttribute("attrib-unsigned", unsigned(2)); + printer.PushAttribute("attrib-int64", int64_t(3)); + printer.PushAttribute("attrib-bool", true); + printer.PushAttribute("attrib-double", 4.0); + printer.CloseElement(); + fclose(printerfp); + } + { + XMLDocument doc; + doc.LoadFile("resources/printer.xml"); + XMLTest("XMLPrinter Stream mode: load", doc.ErrorID(), XML_SUCCESS, true); + + const XMLDocument& cdoc = doc; + + const XMLAttribute* attrib = cdoc.FirstChildElement("foo")->FindAttribute("attrib-text"); + XMLTest("attrib-text", "text", attrib->Value(), true); + attrib = cdoc.FirstChildElement("foo")->FindAttribute("attrib-int"); + XMLTest("attrib-int", int(1), attrib->IntValue(), true); + attrib = cdoc.FirstChildElement("foo")->FindAttribute("attrib-unsigned"); + XMLTest("attrib-unsigned", unsigned(2), attrib->UnsignedValue(), true); + attrib = cdoc.FirstChildElement("foo")->FindAttribute("attrib-int64"); + XMLTest("attrib-int64", int64_t(3), attrib->Int64Value(), true); + attrib = cdoc.FirstChildElement("foo")->FindAttribute("attrib-bool"); + XMLTest("attrib-bool", true, attrib->BoolValue(), true); + attrib = cdoc.FirstChildElement("foo")->FindAttribute("attrib-double"); + XMLTest("attrib-double", 4.0, attrib->DoubleValue(), true); + } + + } + // ---------- CDATA --------------- {