Przeglądaj źródła

working with attributes. adding missing methods

Lee Thomason 14 lat temu
rodzic
commit
1ff38e0a5c
3 zmienionych plików z 272 dodań i 70 usunięć
  1. 128 0
      tinyxml2.cpp
  2. 73 10
      tinyxml2.h
  3. 71 60
      xmltest.cpp

+ 128 - 0
tinyxml2.cpp

@@ -344,6 +344,51 @@ XMLNode* XMLNode::InsertEndChild( XMLNode* addThis )
 }
 
 
+XMLNode* XMLNode::InsertFirstChild( XMLNode* addThis )
+{
+	if ( firstChild ) {
+		TIXMLASSERT( lastChild );
+		TIXMLASSERT( firstChild->prev == 0 );
+
+		firstChild->prev = addThis;
+		addThis->next = firstChild;
+		firstChild = addThis;
+
+		addThis->parent = this;
+		addThis->prev = 0;
+	}
+	else {
+		TIXMLASSERT( lastChild == 0 );
+		firstChild = lastChild = addThis;
+
+		addThis->parent = this;
+		addThis->prev = 0;
+		addThis->next = 0;
+	}
+	return addThis;
+}
+
+
+XMLNode* XMLNode::InsertAfterChild( XMLNode* afterThis, XMLNode* addThis )
+{
+	TIXMLASSERT( afterThis->parent == this );
+	if ( afterThis->parent != this )
+		return 0;
+
+	if ( afterThis->next == 0 ) {
+		// The last node or the only node.
+		return InsertEndChild( addThis );
+	}
+	addThis->prev = afterThis;
+	addThis->next = afterThis->next;
+	afterThis->next->prev = addThis;
+	afterThis->next = addThis;
+	return addThis;
+}
+
+
+
+
 const XMLElement* XMLNode::FirstChildElement( const char* value ) const
 {
 	for( XMLNode* node=firstChild; node; node=node->next ) {
@@ -510,6 +555,70 @@ char* XMLAttribute::ParseDeep( char* p )
 }
 
 
+int XMLAttribute::QueryIntAttribute( int* value ) const
+{
+	if ( TIXML_SSCANF( Value(), "%d", value ) == 1 )
+		return ATTRIBUTE_SUCCESS;
+	return WRONG_ATTRIBUTE_TYPE;
+}
+
+
+int XMLAttribute::QueryUnsignedAttribute( unsigned int* value ) const
+{
+	if ( TIXML_SSCANF( Value(), "%u", value ) == 1 )
+		return ATTRIBUTE_SUCCESS;
+	return WRONG_ATTRIBUTE_TYPE;
+}
+
+
+int XMLAttribute::QueryBoolAttribute( bool* value ) const
+{
+	int ival = -1;
+	QueryIntAttribute( &ival );
+
+	if ( ival > 0 || XMLUtil::StringEqual( Value(), "true" ) ) {
+		*value = true;
+		return ATTRIBUTE_SUCCESS;
+	}
+	else if ( ival == 0 || XMLUtil::StringEqual( Value(), "false" ) ) {
+		*value = false;
+		return ATTRIBUTE_SUCCESS;
+	}
+	return WRONG_ATTRIBUTE_TYPE;
+}
+
+
+int XMLAttribute::QueryDoubleAttribute( double* value ) const
+{
+	if ( TIXML_SSCANF( Value(), "%lf", value ) == 1 )
+		return ATTRIBUTE_SUCCESS;
+	return WRONG_ATTRIBUTE_TYPE;
+}
+
+
+int XMLAttribute::QueryFloatAttribute( float* value ) const
+{
+	if ( TIXML_SSCANF( Value(), "%f", value ) == 1 )
+		return ATTRIBUTE_SUCCESS;
+	return WRONG_ATTRIBUTE_TYPE;
+}
+
+
+void XMLAttribute::SetAttribute( const char* v )
+{
+	value.SetInternedStr( v );
+}
+
+
+/*
+void XMLAttribute::SetAttribute( int v )
+{
+	char buf[BUF_SIZE];
+	TIXML_SNPRINTF( buf, BUF_SIZE-1, "%d" );
+
+	value.SetInternedStr( v );
+}
+*/
 
 // --------- XMLElement ---------- //
 XMLElement::XMLElement( XMLDocument* doc ) : XMLNode( doc ),
@@ -683,6 +792,25 @@ XMLElement* XMLDocument::NewElement( const char* name )
 }
 
 
+XMLComment* XMLDocument::NewComment( const char* str )
+{
+	XMLComment* comment = new (commentPool.Alloc()) XMLComment( this );
+	comment->memPool = &commentPool;
+	comment->SetValue( str );
+	return comment;
+}
+
+
+XMLText* XMLDocument::NewText( const char* str )
+{
+	XMLText* Text = new (textPool.Alloc()) XMLText( this );
+	Text->memPool = &textPool;
+	Text->SetValue( str );
+	return Text;
+}
+
+
+
 int XMLDocument::Parse( const char* p )
 {
 	ClearChildren();

+ 73 - 10
tinyxml2.h

@@ -13,7 +13,11 @@
 	X hide copy constructor
 	X hide = operator
 	X UTF8 support: isAlpha, etc.
+	- string buffer for sets. (Grr.)
+	- MS BOM
+	- print to memory buffer
 	- tests from xml1
+	- xml1 tests especially UTF-8
 	- perf test: xml1
 	- perf test: xenowar
 */
@@ -45,6 +49,31 @@
 #endif
 
 
+// Deprecated library function hell. Compilers want to use the
+// new safe versions. This probably doesn't fully address the problem,
+// but it gets closer. There are too many compilers for me to fully
+// test. If you get compilation troubles, undefine TIXML_SAFE
+
+#if defined(_MSC_VER) && (_MSC_VER >= 1400 )
+	// Microsoft visual studio, version 2005 and higher.
+	#define TIXML_SNPRINTF _snprintf_s
+	#define TIXML_SSCANF   sscanf_s
+#elif defined(_MSC_VER) && (_MSC_VER >= 1200 )
+	// Microsoft visual studio, version 6 and higher.
+	//#pragma message( "Using _sn* functions." )
+	#define TIXML_SNPRINTF _snprintf
+	#define TIXML_SSCANF   sscanf
+#elif defined(__GNUC__) && (__GNUC__ >= 3 )
+	// GCC version 3 and higher.s
+	//#warning( "Using sn* functions." )
+	#define TIXML_SNPRINTF snprintf
+	#define TIXML_SSCANF   sscanf
+#else
+	#define TIXML_SNPRINTF snprintf
+	#define TIXML_SSCANF   sscanf
+#endif
+
+
 namespace tinyxml2
 {
 class XMLDocument;
@@ -365,8 +394,20 @@ public:
 	const XMLNode*	NextSiblingElement( const char* value=0 ) const;
  	XMLNode*	NextSiblingElement( const char* value=0 )	{ return const_cast<XMLNode*>(const_cast<const XMLNode*>(this)->NextSiblingElement( value ) ); }
 
+	/**
+
+		Tests: Programmatic DOM
+	*/
 	XMLNode* InsertEndChild( XMLNode* addThis );
+	/**
+
+		Tests: Programmatic DOM
+	*/
 	XMLNode* InsertFirstChild( XMLNode* addThis );
+	/**
+
+		Tests: Programmatic DOM
+	*/
 	XMLNode* InsertAfterChild( XMLNode* afterThis, XMLNode* addThis );
 	
 	void ClearChildren();
@@ -485,6 +526,13 @@ protected:
 };
 
 
+enum {
+	ATTRIBUTE_SUCCESS,
+	NO_ATTRIBUTE,
+	WRONG_ATTRIBUTE_TYPE
+};
+
+
 class XMLAttribute
 {
 	friend class XMLElement;
@@ -493,17 +541,21 @@ public:
 	const char* Value() const { return value.GetStr(); }
 	const XMLAttribute* Next() const { return next; }
 
-	int QueryIntAttribute( const char* name, int* value ) const;
-	int QueryUnsignedAttribute( const char* name, unsigned int* value ) const;
-	int QueryBoolAttribute( const char* name, bool* value ) const;
-	int QueryDoubleAttribute( const char* name, double* _value ) const;
-	int QueryFloatAttribute( const char* name, float* _value ) const;
+	int QueryIntAttribute( int* value ) const;
+	int QueryUnsignedAttribute( unsigned int* value ) const;
+	int QueryBoolAttribute( bool* value ) const;
+	int QueryDoubleAttribute( double* value ) const;
+	int QueryFloatAttribute( float* value ) const;
 
-	void SetAttribute( const char* name, const char* value );
-	void SetAttribute( const char* name, int value );
-	void SetAttribute( const char* name, unsigned value );
-	void SetAttribute( const char* name, bool value );
-	void SetAttribute( const char* name, double value );
+	void SetAttribute( const char* value );
+	
+	// NOTE: other sets aren't supported...need to deal with memory model?	
+	/*
+	void SetAttribute( int value );
+	void SetAttribute( unsigned value );
+	void SetAttribute( bool value );
+	void SetAttribute( double value );
+	*/
 
 private:
 	XMLAttribute( XMLElement* element ) : next( 0 ) {}
@@ -587,7 +639,18 @@ public:
 	void Print( XMLStreamer* streamer=0 );
 	virtual bool Accept( XMLVisitor* visitor ) const;
 
+	/**
+		Testing: Programmatic DOM
+	*/
 	XMLElement* NewElement( const char* name );
+	/**
+		Testing: Programmatic DOM
+	*/
+	XMLComment* NewComment( const char* comment );
+	/**
+		Testing: Programmatic DOM
+	*/
+	XMLText* NewText( const char* text );
 
 	enum {
 		NO_ERROR = 0,

+ 71 - 60
xmltest.cpp

@@ -4,63 +4,63 @@
 #include <stdlib.h>
 #include <string.h>
 
-#if defined( WIN32 )
-	#include <crtdbg.h>
-	_CrtMemState startMemState;
-	_CrtMemState endMemState;
-#endif
+#if defined( WIN32 )
+	#include <crtdbg.h>
+	_CrtMemState startMemState;
+	_CrtMemState endMemState;
+#endif
 
 using namespace tinyxml2;
 int gPass = 0;
 int gFail = 0;
 
-bool XmlTest (const char* testString, const char* expected, const char* found, bool noEcho )
-{
-	bool pass = !strcmp( expected, found );
-	if ( pass )
-		printf ("[pass]");
-	else
-		printf ("[fail]");
-
-	if ( noEcho )
-		printf (" %s\n", testString);
-	else
-		printf (" %s [%s][%s]\n", testString, expected, found);
-
-	if ( pass )
-		++gPass;
-	else
-		++gFail;
-	return pass;
-}
-
-
-bool XmlTest( const char* testString, int expected, int found, bool noEcho )
-{
-	bool pass = ( expected == found );
-	if ( pass )
-		printf ("[pass]");
-	else
-		printf ("[fail]");
-
-	if ( noEcho )
-		printf (" %s\n", testString);
-	else
-		printf (" %s [%d][%d]\n", testString, expected, found);
-
-	if ( pass )
-		++gPass;
-	else
-		++gFail;
-	return pass;
-}
+bool XmlTest (const char* testString, const char* expected, const char* found, bool noEcho )
+{
+	bool pass = !strcmp( expected, found );
+	if ( pass )
+		printf ("[pass]");
+	else
+		printf ("[fail]");
+
+	if ( noEcho )
+		printf (" %s\n", testString);
+	else
+		printf (" %s [%s][%s]\n", testString, expected, found);
+
+	if ( pass )
+		++gPass;
+	else
+		++gFail;
+	return pass;
+}
+
+
+bool XmlTest( const char* testString, int expected, int found, bool noEcho )
+{
+	bool pass = ( expected == found );
+	if ( pass )
+		printf ("[pass]");
+	else
+		printf ("[fail]");
+
+	if ( noEcho )
+		printf (" %s\n", testString);
+	else
+		printf (" %s [%d][%d]\n", testString, expected, found);
+
+	if ( pass )
+		++gPass;
+	else
+		++gFail;
+	return pass;
+}
 
 
 int main( int argc, const char* argv )
 {
-	#if defined( WIN32 )
-		_CrtMemCheckpoint( &startMemState );
-	#endif	
+	#if defined( WIN32 )
+		_CrtMemCheckpoint( &startMemState );
+	#endif	
 
 #if 0 
 	{
@@ -120,29 +120,40 @@ int main( int argc, const char* argv )
 	}
 #endif
 	{
+		// Test: Programmatic DOM
 		// Build:
 		//		<element>
 		//			<!--comment-->
 		//			<sub attrib="1" />
 		//			<sub attrib="2" />
-		//			<sub attrib="3" />
+		//			<sub attrib="3" >With Text!</sub>
 		//		<element>
 
 		XMLDocument* doc = new XMLDocument();
-		doc->InsertEndChild( doc->NewElement( "element" ) );
+		XMLNode* element = doc->InsertEndChild( doc->NewElement( "element" ) );
+
+		XMLElement* sub[3] = { doc->NewElement( "sub" ), doc->NewElement( "sub" ), doc->NewElement( "sub" ) };
+		for( int i=0; i<3; ++i ) {
+			sub[i]->SetAttribute( "attrib", i );
+		}
+		element->InsertEndChild( sub[2] );
+		XMLNode* comment = element->InsertFirstChild( doc->NewComment( "comment" ) );
+		element->InsertAfterChild( comment, sub[0] );
+		element->InsertAfterChild( sub[0], sub[1] );
+		sub[2]->InsertFirstChild( doc->NewText( "With Text!" ));
 		doc->Print();
 		delete doc;
 	}
 
-	#if defined( WIN32 )
-		_CrtMemCheckpoint( &endMemState );  
-		//_CrtMemDumpStatistics( &endMemState );
-
-		_CrtMemState diffMemState;
-		_CrtMemDifference( &diffMemState, &startMemState, &endMemState );
-		_CrtMemDumpStatistics( &diffMemState );
-	#endif
-
-	printf ("\nPass %d, Fail %d\n", gPass, gFail);
+	#if defined( WIN32 )
+		_CrtMemCheckpoint( &endMemState );  
+		//_CrtMemDumpStatistics( &endMemState );
+
+		_CrtMemState diffMemState;
+		_CrtMemDifference( &diffMemState, &startMemState, &endMemState );
+		_CrtMemDumpStatistics( &diffMemState );
+	#endif
+
+	printf ("\nPass %d, Fail %d\n", gPass, gFail);
 	return 0;
 }