Important changes to repositories hosted on mbed.com
Mbed hosted mercurial repositories are deprecated and are due to be permanently deleted in July 2026.
To keep a copy of this software download the repository Zip archive or clone locally using Mercurial.
It is also possible to export all your personal repositories from the account settings page.
tinyxml.h@0:7c97dcef700c, 2010-11-21 (annotated)
- Committer:
- steiger
- Date:
- Sun Nov 21 00:49:17 2010 +0000
- Revision:
- 0:7c97dcef700c
Who changed what in which revision?
| User | Revision | Line number | New contents of line |
|---|---|---|---|
| steiger | 0:7c97dcef700c | 1 | /* |
| steiger | 0:7c97dcef700c | 2 | www.sourceforge.net/projects/tinyxml |
| steiger | 0:7c97dcef700c | 3 | Original code (2.0 and earlier )copyright (c) 2000-2006 Lee Thomason (www.grinninglizard.com) |
| steiger | 0:7c97dcef700c | 4 | |
| steiger | 0:7c97dcef700c | 5 | This software is provided 'as-is', without any express or implied |
| steiger | 0:7c97dcef700c | 6 | warranty. In no event will the authors be held liable for any |
| steiger | 0:7c97dcef700c | 7 | damages arising from the use of this software. |
| steiger | 0:7c97dcef700c | 8 | |
| steiger | 0:7c97dcef700c | 9 | Permission is granted to anyone to use this software for any |
| steiger | 0:7c97dcef700c | 10 | purpose, including commercial applications, and to alter it and |
| steiger | 0:7c97dcef700c | 11 | redistribute it freely, subject to the following restrictions: |
| steiger | 0:7c97dcef700c | 12 | |
| steiger | 0:7c97dcef700c | 13 | 1. The origin of this software must not be misrepresented; you must |
| steiger | 0:7c97dcef700c | 14 | not claim that you wrote the original software. If you use this |
| steiger | 0:7c97dcef700c | 15 | software in a product, an acknowledgment in the product documentation |
| steiger | 0:7c97dcef700c | 16 | would be appreciated but is not required. |
| steiger | 0:7c97dcef700c | 17 | |
| steiger | 0:7c97dcef700c | 18 | 2. Altered source versions must be plainly marked as such, and |
| steiger | 0:7c97dcef700c | 19 | must not be misrepresented as being the original software. |
| steiger | 0:7c97dcef700c | 20 | |
| steiger | 0:7c97dcef700c | 21 | 3. This notice may not be removed or altered from any source |
| steiger | 0:7c97dcef700c | 22 | distribution. |
| steiger | 0:7c97dcef700c | 23 | */ |
| steiger | 0:7c97dcef700c | 24 | |
| steiger | 0:7c97dcef700c | 25 | |
| steiger | 0:7c97dcef700c | 26 | #ifndef TINYXML_INCLUDED |
| steiger | 0:7c97dcef700c | 27 | #define TINYXML_INCLUDED |
| steiger | 0:7c97dcef700c | 28 | |
| steiger | 0:7c97dcef700c | 29 | #ifdef _MSC_VER |
| steiger | 0:7c97dcef700c | 30 | #pragma warning( push ) |
| steiger | 0:7c97dcef700c | 31 | #pragma warning( disable : 4530 ) |
| steiger | 0:7c97dcef700c | 32 | #pragma warning( disable : 4786 ) |
| steiger | 0:7c97dcef700c | 33 | #endif |
| steiger | 0:7c97dcef700c | 34 | |
| steiger | 0:7c97dcef700c | 35 | #include <ctype.h> |
| steiger | 0:7c97dcef700c | 36 | #include <stdio.h> |
| steiger | 0:7c97dcef700c | 37 | #include <stdlib.h> |
| steiger | 0:7c97dcef700c | 38 | #include <string.h> |
| steiger | 0:7c97dcef700c | 39 | #include <assert.h> |
| steiger | 0:7c97dcef700c | 40 | |
| steiger | 0:7c97dcef700c | 41 | // Help out windows: |
| steiger | 0:7c97dcef700c | 42 | #if defined( _DEBUG ) && !defined( DEBUG ) |
| steiger | 0:7c97dcef700c | 43 | #define DEBUG |
| steiger | 0:7c97dcef700c | 44 | #endif |
| steiger | 0:7c97dcef700c | 45 | |
| steiger | 0:7c97dcef700c | 46 | #ifdef TIXML_USE_STL |
| steiger | 0:7c97dcef700c | 47 | #include <string> |
| steiger | 0:7c97dcef700c | 48 | #include <iostream> |
| steiger | 0:7c97dcef700c | 49 | #include <sstream> |
| steiger | 0:7c97dcef700c | 50 | #define TIXML_STRING std::string |
| steiger | 0:7c97dcef700c | 51 | #else |
| steiger | 0:7c97dcef700c | 52 | #include "tinystr.h" |
| steiger | 0:7c97dcef700c | 53 | #define TIXML_STRING TiXmlString |
| steiger | 0:7c97dcef700c | 54 | #endif |
| steiger | 0:7c97dcef700c | 55 | |
| steiger | 0:7c97dcef700c | 56 | // Deprecated library function hell. Compilers want to use the |
| steiger | 0:7c97dcef700c | 57 | // new safe versions. This probably doesn't fully address the problem, |
| steiger | 0:7c97dcef700c | 58 | // but it gets closer. There are too many compilers for me to fully |
| steiger | 0:7c97dcef700c | 59 | // test. If you get compilation troubles, undefine TIXML_SAFE |
| steiger | 0:7c97dcef700c | 60 | #define TIXML_SAFE |
| steiger | 0:7c97dcef700c | 61 | |
| steiger | 0:7c97dcef700c | 62 | #ifdef TIXML_SAFE |
| steiger | 0:7c97dcef700c | 63 | #if defined(_MSC_VER) && (_MSC_VER >= 1400 ) |
| steiger | 0:7c97dcef700c | 64 | // Microsoft visual studio, version 2005 and higher. |
| steiger | 0:7c97dcef700c | 65 | #define TIXML_SNPRINTF _snprintf_s |
| steiger | 0:7c97dcef700c | 66 | #define TIXML_SSCANF sscanf_s |
| steiger | 0:7c97dcef700c | 67 | #elif defined(_MSC_VER) && (_MSC_VER >= 1200 ) |
| steiger | 0:7c97dcef700c | 68 | // Microsoft visual studio, version 6 and higher. |
| steiger | 0:7c97dcef700c | 69 | //#pragma message( "Using _sn* functions." ) |
| steiger | 0:7c97dcef700c | 70 | #define TIXML_SNPRINTF _snprintf |
| steiger | 0:7c97dcef700c | 71 | #define TIXML_SSCANF sscanf |
| steiger | 0:7c97dcef700c | 72 | #elif defined(__GNUC__) && (__GNUC__ >= 3 ) |
| steiger | 0:7c97dcef700c | 73 | // GCC version 3 and higher.s |
| steiger | 0:7c97dcef700c | 74 | //#warning( "Using sn* functions." ) |
| steiger | 0:7c97dcef700c | 75 | #define TIXML_SNPRINTF snprintf |
| steiger | 0:7c97dcef700c | 76 | #define TIXML_SSCANF sscanf |
| steiger | 0:7c97dcef700c | 77 | #else |
| steiger | 0:7c97dcef700c | 78 | #define TIXML_SNPRINTF snprintf |
| steiger | 0:7c97dcef700c | 79 | #define TIXML_SSCANF sscanf |
| steiger | 0:7c97dcef700c | 80 | #endif |
| steiger | 0:7c97dcef700c | 81 | #endif |
| steiger | 0:7c97dcef700c | 82 | |
| steiger | 0:7c97dcef700c | 83 | class TiXmlDocument; |
| steiger | 0:7c97dcef700c | 84 | class TiXmlElement; |
| steiger | 0:7c97dcef700c | 85 | class TiXmlComment; |
| steiger | 0:7c97dcef700c | 86 | class TiXmlUnknown; |
| steiger | 0:7c97dcef700c | 87 | class TiXmlAttribute; |
| steiger | 0:7c97dcef700c | 88 | class TiXmlText; |
| steiger | 0:7c97dcef700c | 89 | class TiXmlDeclaration; |
| steiger | 0:7c97dcef700c | 90 | class TiXmlParsingData; |
| steiger | 0:7c97dcef700c | 91 | |
| steiger | 0:7c97dcef700c | 92 | const int TIXML_MAJOR_VERSION = 2; |
| steiger | 0:7c97dcef700c | 93 | const int TIXML_MINOR_VERSION = 6; |
| steiger | 0:7c97dcef700c | 94 | const int TIXML_PATCH_VERSION = 1; |
| steiger | 0:7c97dcef700c | 95 | |
| steiger | 0:7c97dcef700c | 96 | /* Internal structure for tracking location of items |
| steiger | 0:7c97dcef700c | 97 | in the XML file. |
| steiger | 0:7c97dcef700c | 98 | */ |
| steiger | 0:7c97dcef700c | 99 | struct TiXmlCursor |
| steiger | 0:7c97dcef700c | 100 | { |
| steiger | 0:7c97dcef700c | 101 | TiXmlCursor() { Clear(); } |
| steiger | 0:7c97dcef700c | 102 | void Clear() { row = col = -1; } |
| steiger | 0:7c97dcef700c | 103 | |
| steiger | 0:7c97dcef700c | 104 | int row; // 0 based. |
| steiger | 0:7c97dcef700c | 105 | int col; // 0 based. |
| steiger | 0:7c97dcef700c | 106 | }; |
| steiger | 0:7c97dcef700c | 107 | |
| steiger | 0:7c97dcef700c | 108 | |
| steiger | 0:7c97dcef700c | 109 | /** |
| steiger | 0:7c97dcef700c | 110 | Implements the interface to the "Visitor pattern" (see the Accept() method.) |
| steiger | 0:7c97dcef700c | 111 | If you call the Accept() method, it requires being passed a TiXmlVisitor |
| steiger | 0:7c97dcef700c | 112 | class to handle callbacks. For nodes that contain other nodes (Document, Element) |
| steiger | 0:7c97dcef700c | 113 | you will get called with a VisitEnter/VisitExit pair. Nodes that are always leaves |
| steiger | 0:7c97dcef700c | 114 | are simply called with Visit(). |
| steiger | 0:7c97dcef700c | 115 | |
| steiger | 0:7c97dcef700c | 116 | If you return 'true' from a Visit method, recursive parsing will continue. If you return |
| steiger | 0:7c97dcef700c | 117 | false, <b>no children of this node or its sibilings</b> will be Visited. |
| steiger | 0:7c97dcef700c | 118 | |
| steiger | 0:7c97dcef700c | 119 | All flavors of Visit methods have a default implementation that returns 'true' (continue |
| steiger | 0:7c97dcef700c | 120 | visiting). You need to only override methods that are interesting to you. |
| steiger | 0:7c97dcef700c | 121 | |
| steiger | 0:7c97dcef700c | 122 | Generally Accept() is called on the TiXmlDocument, although all nodes suppert Visiting. |
| steiger | 0:7c97dcef700c | 123 | |
| steiger | 0:7c97dcef700c | 124 | You should never change the document from a callback. |
| steiger | 0:7c97dcef700c | 125 | |
| steiger | 0:7c97dcef700c | 126 | @sa TiXmlNode::Accept() |
| steiger | 0:7c97dcef700c | 127 | */ |
| steiger | 0:7c97dcef700c | 128 | class TiXmlVisitor |
| steiger | 0:7c97dcef700c | 129 | { |
| steiger | 0:7c97dcef700c | 130 | public: |
| steiger | 0:7c97dcef700c | 131 | virtual ~TiXmlVisitor() {} |
| steiger | 0:7c97dcef700c | 132 | |
| steiger | 0:7c97dcef700c | 133 | /// Visit a document. |
| steiger | 0:7c97dcef700c | 134 | virtual bool VisitEnter( const TiXmlDocument& /*doc*/ ) { return true; } |
| steiger | 0:7c97dcef700c | 135 | /// Visit a document. |
| steiger | 0:7c97dcef700c | 136 | virtual bool VisitExit( const TiXmlDocument& /*doc*/ ) { return true; } |
| steiger | 0:7c97dcef700c | 137 | |
| steiger | 0:7c97dcef700c | 138 | /// Visit an element. |
| steiger | 0:7c97dcef700c | 139 | virtual bool VisitEnter( const TiXmlElement& /*element*/, const TiXmlAttribute* /*firstAttribute*/ ) { return true; } |
| steiger | 0:7c97dcef700c | 140 | /// Visit an element. |
| steiger | 0:7c97dcef700c | 141 | virtual bool VisitExit( const TiXmlElement& /*element*/ ) { return true; } |
| steiger | 0:7c97dcef700c | 142 | |
| steiger | 0:7c97dcef700c | 143 | /// Visit a declaration |
| steiger | 0:7c97dcef700c | 144 | virtual bool Visit( const TiXmlDeclaration& /*declaration*/ ) { return true; } |
| steiger | 0:7c97dcef700c | 145 | /// Visit a text node |
| steiger | 0:7c97dcef700c | 146 | virtual bool Visit( const TiXmlText& /*text*/ ) { return true; } |
| steiger | 0:7c97dcef700c | 147 | /// Visit a comment node |
| steiger | 0:7c97dcef700c | 148 | virtual bool Visit( const TiXmlComment& /*comment*/ ) { return true; } |
| steiger | 0:7c97dcef700c | 149 | /// Visit an unknow node |
| steiger | 0:7c97dcef700c | 150 | virtual bool Visit( const TiXmlUnknown& /*unknown*/ ) { return true; } |
| steiger | 0:7c97dcef700c | 151 | }; |
| steiger | 0:7c97dcef700c | 152 | |
| steiger | 0:7c97dcef700c | 153 | // Only used by Attribute::Query functions |
| steiger | 0:7c97dcef700c | 154 | enum |
| steiger | 0:7c97dcef700c | 155 | { |
| steiger | 0:7c97dcef700c | 156 | TIXML_SUCCESS, |
| steiger | 0:7c97dcef700c | 157 | TIXML_NO_ATTRIBUTE, |
| steiger | 0:7c97dcef700c | 158 | TIXML_WRONG_TYPE |
| steiger | 0:7c97dcef700c | 159 | }; |
| steiger | 0:7c97dcef700c | 160 | |
| steiger | 0:7c97dcef700c | 161 | |
| steiger | 0:7c97dcef700c | 162 | // Used by the parsing routines. |
| steiger | 0:7c97dcef700c | 163 | enum TiXmlEncoding |
| steiger | 0:7c97dcef700c | 164 | { |
| steiger | 0:7c97dcef700c | 165 | TIXML_ENCODING_UNKNOWN, |
| steiger | 0:7c97dcef700c | 166 | TIXML_ENCODING_UTF8, |
| steiger | 0:7c97dcef700c | 167 | TIXML_ENCODING_LEGACY |
| steiger | 0:7c97dcef700c | 168 | }; |
| steiger | 0:7c97dcef700c | 169 | |
| steiger | 0:7c97dcef700c | 170 | const TiXmlEncoding TIXML_DEFAULT_ENCODING = TIXML_ENCODING_UNKNOWN; |
| steiger | 0:7c97dcef700c | 171 | |
| steiger | 0:7c97dcef700c | 172 | /** TiXmlBase is a base class for every class in TinyXml. |
| steiger | 0:7c97dcef700c | 173 | It does little except to establish that TinyXml classes |
| steiger | 0:7c97dcef700c | 174 | can be printed and provide some utility functions. |
| steiger | 0:7c97dcef700c | 175 | |
| steiger | 0:7c97dcef700c | 176 | In XML, the document and elements can contain |
| steiger | 0:7c97dcef700c | 177 | other elements and other types of nodes. |
| steiger | 0:7c97dcef700c | 178 | |
| steiger | 0:7c97dcef700c | 179 | @verbatim |
| steiger | 0:7c97dcef700c | 180 | A Document can contain: Element (container or leaf) |
| steiger | 0:7c97dcef700c | 181 | Comment (leaf) |
| steiger | 0:7c97dcef700c | 182 | Unknown (leaf) |
| steiger | 0:7c97dcef700c | 183 | Declaration( leaf ) |
| steiger | 0:7c97dcef700c | 184 | |
| steiger | 0:7c97dcef700c | 185 | An Element can contain: Element (container or leaf) |
| steiger | 0:7c97dcef700c | 186 | Text (leaf) |
| steiger | 0:7c97dcef700c | 187 | Attributes (not on tree) |
| steiger | 0:7c97dcef700c | 188 | Comment (leaf) |
| steiger | 0:7c97dcef700c | 189 | Unknown (leaf) |
| steiger | 0:7c97dcef700c | 190 | |
| steiger | 0:7c97dcef700c | 191 | A Decleration contains: Attributes (not on tree) |
| steiger | 0:7c97dcef700c | 192 | @endverbatim |
| steiger | 0:7c97dcef700c | 193 | */ |
| steiger | 0:7c97dcef700c | 194 | class TiXmlBase |
| steiger | 0:7c97dcef700c | 195 | { |
| steiger | 0:7c97dcef700c | 196 | friend class TiXmlNode; |
| steiger | 0:7c97dcef700c | 197 | friend class TiXmlElement; |
| steiger | 0:7c97dcef700c | 198 | friend class TiXmlDocument; |
| steiger | 0:7c97dcef700c | 199 | |
| steiger | 0:7c97dcef700c | 200 | public: |
| steiger | 0:7c97dcef700c | 201 | TiXmlBase() : userData(0) {} |
| steiger | 0:7c97dcef700c | 202 | virtual ~TiXmlBase() {} |
| steiger | 0:7c97dcef700c | 203 | |
| steiger | 0:7c97dcef700c | 204 | /** All TinyXml classes can print themselves to a filestream |
| steiger | 0:7c97dcef700c | 205 | or the string class (TiXmlString in non-STL mode, std::string |
| steiger | 0:7c97dcef700c | 206 | in STL mode.) Either or both cfile and str can be null. |
| steiger | 0:7c97dcef700c | 207 | |
| steiger | 0:7c97dcef700c | 208 | This is a formatted print, and will insert |
| steiger | 0:7c97dcef700c | 209 | tabs and newlines. |
| steiger | 0:7c97dcef700c | 210 | |
| steiger | 0:7c97dcef700c | 211 | (For an unformatted stream, use the << operator.) |
| steiger | 0:7c97dcef700c | 212 | */ |
| steiger | 0:7c97dcef700c | 213 | virtual void Print( FILE* cfile, int depth ) const = 0; |
| steiger | 0:7c97dcef700c | 214 | |
| steiger | 0:7c97dcef700c | 215 | /** The world does not agree on whether white space should be kept or |
| steiger | 0:7c97dcef700c | 216 | not. In order to make everyone happy, these global, static functions |
| steiger | 0:7c97dcef700c | 217 | are provided to set whether or not TinyXml will condense all white space |
| steiger | 0:7c97dcef700c | 218 | into a single space or not. The default is to condense. Note changing this |
| steiger | 0:7c97dcef700c | 219 | value is not thread safe. |
| steiger | 0:7c97dcef700c | 220 | */ |
| steiger | 0:7c97dcef700c | 221 | static void SetCondenseWhiteSpace( bool condense ) { condenseWhiteSpace = condense; } |
| steiger | 0:7c97dcef700c | 222 | |
| steiger | 0:7c97dcef700c | 223 | /// Return the current white space setting. |
| steiger | 0:7c97dcef700c | 224 | static bool IsWhiteSpaceCondensed() { return condenseWhiteSpace; } |
| steiger | 0:7c97dcef700c | 225 | |
| steiger | 0:7c97dcef700c | 226 | /** Return the position, in the original source file, of this node or attribute. |
| steiger | 0:7c97dcef700c | 227 | The row and column are 1-based. (That is the first row and first column is |
| steiger | 0:7c97dcef700c | 228 | 1,1). If the returns values are 0 or less, then the parser does not have |
| steiger | 0:7c97dcef700c | 229 | a row and column value. |
| steiger | 0:7c97dcef700c | 230 | |
| steiger | 0:7c97dcef700c | 231 | Generally, the row and column value will be set when the TiXmlDocument::Load(), |
| steiger | 0:7c97dcef700c | 232 | TiXmlDocument::LoadFile(), or any TiXmlNode::Parse() is called. It will NOT be set |
| steiger | 0:7c97dcef700c | 233 | when the DOM was created from operator>>. |
| steiger | 0:7c97dcef700c | 234 | |
| steiger | 0:7c97dcef700c | 235 | The values reflect the initial load. Once the DOM is modified programmatically |
| steiger | 0:7c97dcef700c | 236 | (by adding or changing nodes and attributes) the new values will NOT update to |
| steiger | 0:7c97dcef700c | 237 | reflect changes in the document. |
| steiger | 0:7c97dcef700c | 238 | |
| steiger | 0:7c97dcef700c | 239 | There is a minor performance cost to computing the row and column. Computation |
| steiger | 0:7c97dcef700c | 240 | can be disabled if TiXmlDocument::SetTabSize() is called with 0 as the value. |
| steiger | 0:7c97dcef700c | 241 | |
| steiger | 0:7c97dcef700c | 242 | @sa TiXmlDocument::SetTabSize() |
| steiger | 0:7c97dcef700c | 243 | */ |
| steiger | 0:7c97dcef700c | 244 | int Row() const { return location.row + 1; } |
| steiger | 0:7c97dcef700c | 245 | int Column() const { return location.col + 1; } ///< See Row() |
| steiger | 0:7c97dcef700c | 246 | |
| steiger | 0:7c97dcef700c | 247 | void SetUserData( void* user ) { userData = user; } ///< Set a pointer to arbitrary user data. |
| steiger | 0:7c97dcef700c | 248 | void* GetUserData() { return userData; } ///< Get a pointer to arbitrary user data. |
| steiger | 0:7c97dcef700c | 249 | const void* GetUserData() const { return userData; } ///< Get a pointer to arbitrary user data. |
| steiger | 0:7c97dcef700c | 250 | |
| steiger | 0:7c97dcef700c | 251 | // Table that returs, for a given lead byte, the total number of bytes |
| steiger | 0:7c97dcef700c | 252 | // in the UTF-8 sequence. |
| steiger | 0:7c97dcef700c | 253 | static const int utf8ByteTable[256]; |
| steiger | 0:7c97dcef700c | 254 | |
| steiger | 0:7c97dcef700c | 255 | virtual const char* Parse( const char* p, |
| steiger | 0:7c97dcef700c | 256 | TiXmlParsingData* data, |
| steiger | 0:7c97dcef700c | 257 | TiXmlEncoding encoding /*= TIXML_ENCODING_UNKNOWN */ ) = 0; |
| steiger | 0:7c97dcef700c | 258 | |
| steiger | 0:7c97dcef700c | 259 | /** Expands entities in a string. Note this should not contian the tag's '<', '>', etc, |
| steiger | 0:7c97dcef700c | 260 | or they will be transformed into entities! |
| steiger | 0:7c97dcef700c | 261 | */ |
| steiger | 0:7c97dcef700c | 262 | static void EncodeString( const TIXML_STRING& str, TIXML_STRING* out ); |
| steiger | 0:7c97dcef700c | 263 | |
| steiger | 0:7c97dcef700c | 264 | enum |
| steiger | 0:7c97dcef700c | 265 | { |
| steiger | 0:7c97dcef700c | 266 | TIXML_NO_ERROR = 0, |
| steiger | 0:7c97dcef700c | 267 | TIXML_ERROR, |
| steiger | 0:7c97dcef700c | 268 | TIXML_ERROR_OPENING_FILE, |
| steiger | 0:7c97dcef700c | 269 | TIXML_ERROR_PARSING_ELEMENT, |
| steiger | 0:7c97dcef700c | 270 | TIXML_ERROR_FAILED_TO_READ_ELEMENT_NAME, |
| steiger | 0:7c97dcef700c | 271 | TIXML_ERROR_READING_ELEMENT_VALUE, |
| steiger | 0:7c97dcef700c | 272 | TIXML_ERROR_READING_ATTRIBUTES, |
| steiger | 0:7c97dcef700c | 273 | TIXML_ERROR_PARSING_EMPTY, |
| steiger | 0:7c97dcef700c | 274 | TIXML_ERROR_READING_END_TAG, |
| steiger | 0:7c97dcef700c | 275 | TIXML_ERROR_PARSING_UNKNOWN, |
| steiger | 0:7c97dcef700c | 276 | TIXML_ERROR_PARSING_COMMENT, |
| steiger | 0:7c97dcef700c | 277 | TIXML_ERROR_PARSING_DECLARATION, |
| steiger | 0:7c97dcef700c | 278 | TIXML_ERROR_DOCUMENT_EMPTY, |
| steiger | 0:7c97dcef700c | 279 | TIXML_ERROR_EMBEDDED_NULL, |
| steiger | 0:7c97dcef700c | 280 | TIXML_ERROR_PARSING_CDATA, |
| steiger | 0:7c97dcef700c | 281 | TIXML_ERROR_DOCUMENT_TOP_ONLY, |
| steiger | 0:7c97dcef700c | 282 | |
| steiger | 0:7c97dcef700c | 283 | TIXML_ERROR_STRING_COUNT |
| steiger | 0:7c97dcef700c | 284 | }; |
| steiger | 0:7c97dcef700c | 285 | |
| steiger | 0:7c97dcef700c | 286 | protected: |
| steiger | 0:7c97dcef700c | 287 | |
| steiger | 0:7c97dcef700c | 288 | static const char* SkipWhiteSpace( const char*, TiXmlEncoding encoding ); |
| steiger | 0:7c97dcef700c | 289 | |
| steiger | 0:7c97dcef700c | 290 | inline static bool IsWhiteSpace( char c ) |
| steiger | 0:7c97dcef700c | 291 | { |
| steiger | 0:7c97dcef700c | 292 | return ( isspace( (unsigned char) c ) || c == '\n' || c == '\r' ); |
| steiger | 0:7c97dcef700c | 293 | } |
| steiger | 0:7c97dcef700c | 294 | inline static bool IsWhiteSpace( int c ) |
| steiger | 0:7c97dcef700c | 295 | { |
| steiger | 0:7c97dcef700c | 296 | if ( c < 256 ) |
| steiger | 0:7c97dcef700c | 297 | return IsWhiteSpace( (char) c ); |
| steiger | 0:7c97dcef700c | 298 | return false; // Again, only truly correct for English/Latin...but usually works. |
| steiger | 0:7c97dcef700c | 299 | } |
| steiger | 0:7c97dcef700c | 300 | |
| steiger | 0:7c97dcef700c | 301 | #ifdef TIXML_USE_STL |
| steiger | 0:7c97dcef700c | 302 | static bool StreamWhiteSpace( std::istream * in, TIXML_STRING * tag ); |
| steiger | 0:7c97dcef700c | 303 | static bool StreamTo( std::istream * in, int character, TIXML_STRING * tag ); |
| steiger | 0:7c97dcef700c | 304 | #endif |
| steiger | 0:7c97dcef700c | 305 | |
| steiger | 0:7c97dcef700c | 306 | /* Reads an XML name into the string provided. Returns |
| steiger | 0:7c97dcef700c | 307 | a pointer just past the last character of the name, |
| steiger | 0:7c97dcef700c | 308 | or 0 if the function has an error. |
| steiger | 0:7c97dcef700c | 309 | */ |
| steiger | 0:7c97dcef700c | 310 | static const char* ReadName( const char* p, TIXML_STRING* name, TiXmlEncoding encoding ); |
| steiger | 0:7c97dcef700c | 311 | |
| steiger | 0:7c97dcef700c | 312 | /* Reads text. Returns a pointer past the given end tag. |
| steiger | 0:7c97dcef700c | 313 | Wickedly complex options, but it keeps the (sensitive) code in one place. |
| steiger | 0:7c97dcef700c | 314 | */ |
| steiger | 0:7c97dcef700c | 315 | static const char* ReadText( const char* in, // where to start |
| steiger | 0:7c97dcef700c | 316 | TIXML_STRING* text, // the string read |
| steiger | 0:7c97dcef700c | 317 | bool ignoreWhiteSpace, // whether to keep the white space |
| steiger | 0:7c97dcef700c | 318 | const char* endTag, // what ends this text |
| steiger | 0:7c97dcef700c | 319 | bool ignoreCase, // whether to ignore case in the end tag |
| steiger | 0:7c97dcef700c | 320 | TiXmlEncoding encoding ); // the current encoding |
| steiger | 0:7c97dcef700c | 321 | |
| steiger | 0:7c97dcef700c | 322 | // If an entity has been found, transform it into a character. |
| steiger | 0:7c97dcef700c | 323 | static const char* GetEntity( const char* in, char* value, int* length, TiXmlEncoding encoding ); |
| steiger | 0:7c97dcef700c | 324 | |
| steiger | 0:7c97dcef700c | 325 | // Get a character, while interpreting entities. |
| steiger | 0:7c97dcef700c | 326 | // The length can be from 0 to 4 bytes. |
| steiger | 0:7c97dcef700c | 327 | inline static const char* GetChar( const char* p, char* _value, int* length, TiXmlEncoding encoding ) |
| steiger | 0:7c97dcef700c | 328 | { |
| steiger | 0:7c97dcef700c | 329 | assert( p ); |
| steiger | 0:7c97dcef700c | 330 | if ( encoding == TIXML_ENCODING_UTF8 ) |
| steiger | 0:7c97dcef700c | 331 | { |
| steiger | 0:7c97dcef700c | 332 | *length = utf8ByteTable[ *((const unsigned char*)p) ]; |
| steiger | 0:7c97dcef700c | 333 | assert( *length >= 0 && *length < 5 ); |
| steiger | 0:7c97dcef700c | 334 | } |
| steiger | 0:7c97dcef700c | 335 | else |
| steiger | 0:7c97dcef700c | 336 | { |
| steiger | 0:7c97dcef700c | 337 | *length = 1; |
| steiger | 0:7c97dcef700c | 338 | } |
| steiger | 0:7c97dcef700c | 339 | |
| steiger | 0:7c97dcef700c | 340 | if ( *length == 1 ) |
| steiger | 0:7c97dcef700c | 341 | { |
| steiger | 0:7c97dcef700c | 342 | if ( *p == '&' ) |
| steiger | 0:7c97dcef700c | 343 | return GetEntity( p, _value, length, encoding ); |
| steiger | 0:7c97dcef700c | 344 | *_value = *p; |
| steiger | 0:7c97dcef700c | 345 | return p+1; |
| steiger | 0:7c97dcef700c | 346 | } |
| steiger | 0:7c97dcef700c | 347 | else if ( *length ) |
| steiger | 0:7c97dcef700c | 348 | { |
| steiger | 0:7c97dcef700c | 349 | //strncpy( _value, p, *length ); // lots of compilers don't like this function (unsafe), |
| steiger | 0:7c97dcef700c | 350 | // and the null terminator isn't needed |
| steiger | 0:7c97dcef700c | 351 | for( int i=0; p[i] && i<*length; ++i ) { |
| steiger | 0:7c97dcef700c | 352 | _value[i] = p[i]; |
| steiger | 0:7c97dcef700c | 353 | } |
| steiger | 0:7c97dcef700c | 354 | return p + (*length); |
| steiger | 0:7c97dcef700c | 355 | } |
| steiger | 0:7c97dcef700c | 356 | else |
| steiger | 0:7c97dcef700c | 357 | { |
| steiger | 0:7c97dcef700c | 358 | // Not valid text. |
| steiger | 0:7c97dcef700c | 359 | return 0; |
| steiger | 0:7c97dcef700c | 360 | } |
| steiger | 0:7c97dcef700c | 361 | } |
| steiger | 0:7c97dcef700c | 362 | |
| steiger | 0:7c97dcef700c | 363 | // Return true if the next characters in the stream are any of the endTag sequences. |
| steiger | 0:7c97dcef700c | 364 | // Ignore case only works for english, and should only be relied on when comparing |
| steiger | 0:7c97dcef700c | 365 | // to English words: StringEqual( p, "version", true ) is fine. |
| steiger | 0:7c97dcef700c | 366 | static bool StringEqual( const char* p, |
| steiger | 0:7c97dcef700c | 367 | const char* endTag, |
| steiger | 0:7c97dcef700c | 368 | bool ignoreCase, |
| steiger | 0:7c97dcef700c | 369 | TiXmlEncoding encoding ); |
| steiger | 0:7c97dcef700c | 370 | |
| steiger | 0:7c97dcef700c | 371 | static const char* errorString[ TIXML_ERROR_STRING_COUNT ]; |
| steiger | 0:7c97dcef700c | 372 | |
| steiger | 0:7c97dcef700c | 373 | TiXmlCursor location; |
| steiger | 0:7c97dcef700c | 374 | |
| steiger | 0:7c97dcef700c | 375 | /// Field containing a generic user pointer |
| steiger | 0:7c97dcef700c | 376 | void* userData; |
| steiger | 0:7c97dcef700c | 377 | |
| steiger | 0:7c97dcef700c | 378 | // None of these methods are reliable for any language except English. |
| steiger | 0:7c97dcef700c | 379 | // Good for approximation, not great for accuracy. |
| steiger | 0:7c97dcef700c | 380 | static int IsAlpha( unsigned char anyByte, TiXmlEncoding encoding ); |
| steiger | 0:7c97dcef700c | 381 | static int IsAlphaNum( unsigned char anyByte, TiXmlEncoding encoding ); |
| steiger | 0:7c97dcef700c | 382 | inline static int ToLower( int v, TiXmlEncoding encoding ) |
| steiger | 0:7c97dcef700c | 383 | { |
| steiger | 0:7c97dcef700c | 384 | if ( encoding == TIXML_ENCODING_UTF8 ) |
| steiger | 0:7c97dcef700c | 385 | { |
| steiger | 0:7c97dcef700c | 386 | if ( v < 128 ) return tolower( v ); |
| steiger | 0:7c97dcef700c | 387 | return v; |
| steiger | 0:7c97dcef700c | 388 | } |
| steiger | 0:7c97dcef700c | 389 | else |
| steiger | 0:7c97dcef700c | 390 | { |
| steiger | 0:7c97dcef700c | 391 | return tolower( v ); |
| steiger | 0:7c97dcef700c | 392 | } |
| steiger | 0:7c97dcef700c | 393 | } |
| steiger | 0:7c97dcef700c | 394 | static void ConvertUTF32ToUTF8( unsigned long input, char* output, int* length ); |
| steiger | 0:7c97dcef700c | 395 | |
| steiger | 0:7c97dcef700c | 396 | private: |
| steiger | 0:7c97dcef700c | 397 | TiXmlBase( const TiXmlBase& ); // not implemented. |
| steiger | 0:7c97dcef700c | 398 | void operator=( const TiXmlBase& base ); // not allowed. |
| steiger | 0:7c97dcef700c | 399 | |
| steiger | 0:7c97dcef700c | 400 | struct Entity |
| steiger | 0:7c97dcef700c | 401 | { |
| steiger | 0:7c97dcef700c | 402 | const char* str; |
| steiger | 0:7c97dcef700c | 403 | unsigned int strLength; |
| steiger | 0:7c97dcef700c | 404 | char chr; |
| steiger | 0:7c97dcef700c | 405 | }; |
| steiger | 0:7c97dcef700c | 406 | enum |
| steiger | 0:7c97dcef700c | 407 | { |
| steiger | 0:7c97dcef700c | 408 | NUM_ENTITY = 5, |
| steiger | 0:7c97dcef700c | 409 | MAX_ENTITY_LENGTH = 6 |
| steiger | 0:7c97dcef700c | 410 | |
| steiger | 0:7c97dcef700c | 411 | }; |
| steiger | 0:7c97dcef700c | 412 | static Entity entity[ NUM_ENTITY ]; |
| steiger | 0:7c97dcef700c | 413 | static bool condenseWhiteSpace; |
| steiger | 0:7c97dcef700c | 414 | }; |
| steiger | 0:7c97dcef700c | 415 | |
| steiger | 0:7c97dcef700c | 416 | |
| steiger | 0:7c97dcef700c | 417 | /** The parent class for everything in the Document Object Model. |
| steiger | 0:7c97dcef700c | 418 | (Except for attributes). |
| steiger | 0:7c97dcef700c | 419 | Nodes have siblings, a parent, and children. A node can be |
| steiger | 0:7c97dcef700c | 420 | in a document, or stand on its own. The type of a TiXmlNode |
| steiger | 0:7c97dcef700c | 421 | can be queried, and it can be cast to its more defined type. |
| steiger | 0:7c97dcef700c | 422 | */ |
| steiger | 0:7c97dcef700c | 423 | class TiXmlNode : public TiXmlBase |
| steiger | 0:7c97dcef700c | 424 | { |
| steiger | 0:7c97dcef700c | 425 | friend class TiXmlDocument; |
| steiger | 0:7c97dcef700c | 426 | friend class TiXmlElement; |
| steiger | 0:7c97dcef700c | 427 | |
| steiger | 0:7c97dcef700c | 428 | public: |
| steiger | 0:7c97dcef700c | 429 | #ifdef TIXML_USE_STL |
| steiger | 0:7c97dcef700c | 430 | |
| steiger | 0:7c97dcef700c | 431 | /** An input stream operator, for every class. Tolerant of newlines and |
| steiger | 0:7c97dcef700c | 432 | formatting, but doesn't expect them. |
| steiger | 0:7c97dcef700c | 433 | */ |
| steiger | 0:7c97dcef700c | 434 | friend std::istream& operator >> (std::istream& in, TiXmlNode& base); |
| steiger | 0:7c97dcef700c | 435 | |
| steiger | 0:7c97dcef700c | 436 | /** An output stream operator, for every class. Note that this outputs |
| steiger | 0:7c97dcef700c | 437 | without any newlines or formatting, as opposed to Print(), which |
| steiger | 0:7c97dcef700c | 438 | includes tabs and new lines. |
| steiger | 0:7c97dcef700c | 439 | |
| steiger | 0:7c97dcef700c | 440 | The operator<< and operator>> are not completely symmetric. Writing |
| steiger | 0:7c97dcef700c | 441 | a node to a stream is very well defined. You'll get a nice stream |
| steiger | 0:7c97dcef700c | 442 | of output, without any extra whitespace or newlines. |
| steiger | 0:7c97dcef700c | 443 | |
| steiger | 0:7c97dcef700c | 444 | But reading is not as well defined. (As it always is.) If you create |
| steiger | 0:7c97dcef700c | 445 | a TiXmlElement (for example) and read that from an input stream, |
| steiger | 0:7c97dcef700c | 446 | the text needs to define an element or junk will result. This is |
| steiger | 0:7c97dcef700c | 447 | true of all input streams, but it's worth keeping in mind. |
| steiger | 0:7c97dcef700c | 448 | |
| steiger | 0:7c97dcef700c | 449 | A TiXmlDocument will read nodes until it reads a root element, and |
| steiger | 0:7c97dcef700c | 450 | all the children of that root element. |
| steiger | 0:7c97dcef700c | 451 | */ |
| steiger | 0:7c97dcef700c | 452 | friend std::ostream& operator<< (std::ostream& out, const TiXmlNode& base); |
| steiger | 0:7c97dcef700c | 453 | |
| steiger | 0:7c97dcef700c | 454 | /// Appends the XML node or attribute to a std::string. |
| steiger | 0:7c97dcef700c | 455 | friend std::string& operator<< (std::string& out, const TiXmlNode& base ); |
| steiger | 0:7c97dcef700c | 456 | |
| steiger | 0:7c97dcef700c | 457 | #endif |
| steiger | 0:7c97dcef700c | 458 | |
| steiger | 0:7c97dcef700c | 459 | /** The types of XML nodes supported by TinyXml. (All the |
| steiger | 0:7c97dcef700c | 460 | unsupported types are picked up by UNKNOWN.) |
| steiger | 0:7c97dcef700c | 461 | */ |
| steiger | 0:7c97dcef700c | 462 | enum NodeType |
| steiger | 0:7c97dcef700c | 463 | { |
| steiger | 0:7c97dcef700c | 464 | TINYXML_DOCUMENT, |
| steiger | 0:7c97dcef700c | 465 | TINYXML_ELEMENT, |
| steiger | 0:7c97dcef700c | 466 | TINYXML_COMMENT, |
| steiger | 0:7c97dcef700c | 467 | TINYXML_UNKNOWN, |
| steiger | 0:7c97dcef700c | 468 | TINYXML_TEXT, |
| steiger | 0:7c97dcef700c | 469 | TINYXML_DECLARATION, |
| steiger | 0:7c97dcef700c | 470 | TINYXML_TYPECOUNT |
| steiger | 0:7c97dcef700c | 471 | }; |
| steiger | 0:7c97dcef700c | 472 | |
| steiger | 0:7c97dcef700c | 473 | virtual ~TiXmlNode(); |
| steiger | 0:7c97dcef700c | 474 | |
| steiger | 0:7c97dcef700c | 475 | /** The meaning of 'value' changes for the specific type of |
| steiger | 0:7c97dcef700c | 476 | TiXmlNode. |
| steiger | 0:7c97dcef700c | 477 | @verbatim |
| steiger | 0:7c97dcef700c | 478 | Document: filename of the xml file |
| steiger | 0:7c97dcef700c | 479 | Element: name of the element |
| steiger | 0:7c97dcef700c | 480 | Comment: the comment text |
| steiger | 0:7c97dcef700c | 481 | Unknown: the tag contents |
| steiger | 0:7c97dcef700c | 482 | Text: the text string |
| steiger | 0:7c97dcef700c | 483 | @endverbatim |
| steiger | 0:7c97dcef700c | 484 | |
| steiger | 0:7c97dcef700c | 485 | The subclasses will wrap this function. |
| steiger | 0:7c97dcef700c | 486 | */ |
| steiger | 0:7c97dcef700c | 487 | const char *Value() const { return value.c_str (); } |
| steiger | 0:7c97dcef700c | 488 | |
| steiger | 0:7c97dcef700c | 489 | #ifdef TIXML_USE_STL |
| steiger | 0:7c97dcef700c | 490 | /** Return Value() as a std::string. If you only use STL, |
| steiger | 0:7c97dcef700c | 491 | this is more efficient than calling Value(). |
| steiger | 0:7c97dcef700c | 492 | Only available in STL mode. |
| steiger | 0:7c97dcef700c | 493 | */ |
| steiger | 0:7c97dcef700c | 494 | const std::string& ValueStr() const { return value; } |
| steiger | 0:7c97dcef700c | 495 | #endif |
| steiger | 0:7c97dcef700c | 496 | |
| steiger | 0:7c97dcef700c | 497 | const TIXML_STRING& ValueTStr() const { return value; } |
| steiger | 0:7c97dcef700c | 498 | |
| steiger | 0:7c97dcef700c | 499 | /** Changes the value of the node. Defined as: |
| steiger | 0:7c97dcef700c | 500 | @verbatim |
| steiger | 0:7c97dcef700c | 501 | Document: filename of the xml file |
| steiger | 0:7c97dcef700c | 502 | Element: name of the element |
| steiger | 0:7c97dcef700c | 503 | Comment: the comment text |
| steiger | 0:7c97dcef700c | 504 | Unknown: the tag contents |
| steiger | 0:7c97dcef700c | 505 | Text: the text string |
| steiger | 0:7c97dcef700c | 506 | @endverbatim |
| steiger | 0:7c97dcef700c | 507 | */ |
| steiger | 0:7c97dcef700c | 508 | void SetValue(const char * _value) { value = _value;} |
| steiger | 0:7c97dcef700c | 509 | |
| steiger | 0:7c97dcef700c | 510 | #ifdef TIXML_USE_STL |
| steiger | 0:7c97dcef700c | 511 | /// STL std::string form. |
| steiger | 0:7c97dcef700c | 512 | void SetValue( const std::string& _value ) { value = _value; } |
| steiger | 0:7c97dcef700c | 513 | #endif |
| steiger | 0:7c97dcef700c | 514 | |
| steiger | 0:7c97dcef700c | 515 | /// Delete all the children of this node. Does not affect 'this'. |
| steiger | 0:7c97dcef700c | 516 | void Clear(); |
| steiger | 0:7c97dcef700c | 517 | |
| steiger | 0:7c97dcef700c | 518 | /// One step up the DOM. |
| steiger | 0:7c97dcef700c | 519 | TiXmlNode* Parent() { return parent; } |
| steiger | 0:7c97dcef700c | 520 | const TiXmlNode* Parent() const { return parent; } |
| steiger | 0:7c97dcef700c | 521 | |
| steiger | 0:7c97dcef700c | 522 | const TiXmlNode* FirstChild() const { return firstChild; } ///< The first child of this node. Will be null if there are no children. |
| steiger | 0:7c97dcef700c | 523 | TiXmlNode* FirstChild() { return firstChild; } |
| steiger | 0:7c97dcef700c | 524 | const TiXmlNode* FirstChild( const char * value ) const; ///< The first child of this node with the matching 'value'. Will be null if none found. |
| steiger | 0:7c97dcef700c | 525 | /// The first child of this node with the matching 'value'. Will be null if none found. |
| steiger | 0:7c97dcef700c | 526 | TiXmlNode* FirstChild( const char * _value ) { |
| steiger | 0:7c97dcef700c | 527 | // Call through to the const version - safe since nothing is changed. Exiting syntax: cast this to a const (always safe) |
| steiger | 0:7c97dcef700c | 528 | // call the method, cast the return back to non-const. |
| steiger | 0:7c97dcef700c | 529 | return const_cast< TiXmlNode* > ((const_cast< const TiXmlNode* >(this))->FirstChild( _value )); |
| steiger | 0:7c97dcef700c | 530 | } |
| steiger | 0:7c97dcef700c | 531 | const TiXmlNode* LastChild() const { return lastChild; } /// The last child of this node. Will be null if there are no children. |
| steiger | 0:7c97dcef700c | 532 | TiXmlNode* LastChild() { return lastChild; } |
| steiger | 0:7c97dcef700c | 533 | |
| steiger | 0:7c97dcef700c | 534 | const TiXmlNode* LastChild( const char * value ) const; /// The last child of this node matching 'value'. Will be null if there are no children. |
| steiger | 0:7c97dcef700c | 535 | TiXmlNode* LastChild( const char * _value ) { |
| steiger | 0:7c97dcef700c | 536 | return const_cast< TiXmlNode* > ((const_cast< const TiXmlNode* >(this))->LastChild( _value )); |
| steiger | 0:7c97dcef700c | 537 | } |
| steiger | 0:7c97dcef700c | 538 | |
| steiger | 0:7c97dcef700c | 539 | #ifdef TIXML_USE_STL |
| steiger | 0:7c97dcef700c | 540 | const TiXmlNode* FirstChild( const std::string& _value ) const { return FirstChild (_value.c_str ()); } ///< STL std::string form. |
| steiger | 0:7c97dcef700c | 541 | TiXmlNode* FirstChild( const std::string& _value ) { return FirstChild (_value.c_str ()); } ///< STL std::string form. |
| steiger | 0:7c97dcef700c | 542 | const TiXmlNode* LastChild( const std::string& _value ) const { return LastChild (_value.c_str ()); } ///< STL std::string form. |
| steiger | 0:7c97dcef700c | 543 | TiXmlNode* LastChild( const std::string& _value ) { return LastChild (_value.c_str ()); } ///< STL std::string form. |
| steiger | 0:7c97dcef700c | 544 | #endif |
| steiger | 0:7c97dcef700c | 545 | |
| steiger | 0:7c97dcef700c | 546 | /** An alternate way to walk the children of a node. |
| steiger | 0:7c97dcef700c | 547 | One way to iterate over nodes is: |
| steiger | 0:7c97dcef700c | 548 | @verbatim |
| steiger | 0:7c97dcef700c | 549 | for( child = parent->FirstChild(); child; child = child->NextSibling() ) |
| steiger | 0:7c97dcef700c | 550 | @endverbatim |
| steiger | 0:7c97dcef700c | 551 | |
| steiger | 0:7c97dcef700c | 552 | IterateChildren does the same thing with the syntax: |
| steiger | 0:7c97dcef700c | 553 | @verbatim |
| steiger | 0:7c97dcef700c | 554 | child = 0; |
| steiger | 0:7c97dcef700c | 555 | while( child = parent->IterateChildren( child ) ) |
| steiger | 0:7c97dcef700c | 556 | @endverbatim |
| steiger | 0:7c97dcef700c | 557 | |
| steiger | 0:7c97dcef700c | 558 | IterateChildren takes the previous child as input and finds |
| steiger | 0:7c97dcef700c | 559 | the next one. If the previous child is null, it returns the |
| steiger | 0:7c97dcef700c | 560 | first. IterateChildren will return null when done. |
| steiger | 0:7c97dcef700c | 561 | */ |
| steiger | 0:7c97dcef700c | 562 | const TiXmlNode* IterateChildren( const TiXmlNode* previous ) const; |
| steiger | 0:7c97dcef700c | 563 | TiXmlNode* IterateChildren( const TiXmlNode* previous ) { |
| steiger | 0:7c97dcef700c | 564 | return const_cast< TiXmlNode* >( (const_cast< const TiXmlNode* >(this))->IterateChildren( previous ) ); |
| steiger | 0:7c97dcef700c | 565 | } |
| steiger | 0:7c97dcef700c | 566 | |
| steiger | 0:7c97dcef700c | 567 | /// This flavor of IterateChildren searches for children with a particular 'value' |
| steiger | 0:7c97dcef700c | 568 | const TiXmlNode* IterateChildren( const char * value, const TiXmlNode* previous ) const; |
| steiger | 0:7c97dcef700c | 569 | TiXmlNode* IterateChildren( const char * _value, const TiXmlNode* previous ) { |
| steiger | 0:7c97dcef700c | 570 | return const_cast< TiXmlNode* >( (const_cast< const TiXmlNode* >(this))->IterateChildren( _value, previous ) ); |
| steiger | 0:7c97dcef700c | 571 | } |
| steiger | 0:7c97dcef700c | 572 | |
| steiger | 0:7c97dcef700c | 573 | #ifdef TIXML_USE_STL |
| steiger | 0:7c97dcef700c | 574 | const TiXmlNode* IterateChildren( const std::string& _value, const TiXmlNode* previous ) const { return IterateChildren (_value.c_str (), previous); } ///< STL std::string form. |
| steiger | 0:7c97dcef700c | 575 | TiXmlNode* IterateChildren( const std::string& _value, const TiXmlNode* previous ) { return IterateChildren (_value.c_str (), previous); } ///< STL std::string form. |
| steiger | 0:7c97dcef700c | 576 | #endif |
| steiger | 0:7c97dcef700c | 577 | |
| steiger | 0:7c97dcef700c | 578 | /** Add a new node related to this. Adds a child past the LastChild. |
| steiger | 0:7c97dcef700c | 579 | Returns a pointer to the new object or NULL if an error occured. |
| steiger | 0:7c97dcef700c | 580 | */ |
| steiger | 0:7c97dcef700c | 581 | TiXmlNode* InsertEndChild( const TiXmlNode& addThis ); |
| steiger | 0:7c97dcef700c | 582 | |
| steiger | 0:7c97dcef700c | 583 | |
| steiger | 0:7c97dcef700c | 584 | /** Add a new node related to this. Adds a child past the LastChild. |
| steiger | 0:7c97dcef700c | 585 | |
| steiger | 0:7c97dcef700c | 586 | NOTE: the node to be added is passed by pointer, and will be |
| steiger | 0:7c97dcef700c | 587 | henceforth owned (and deleted) by tinyXml. This method is efficient |
| steiger | 0:7c97dcef700c | 588 | and avoids an extra copy, but should be used with care as it |
| steiger | 0:7c97dcef700c | 589 | uses a different memory model than the other insert functions. |
| steiger | 0:7c97dcef700c | 590 | |
| steiger | 0:7c97dcef700c | 591 | @sa InsertEndChild |
| steiger | 0:7c97dcef700c | 592 | */ |
| steiger | 0:7c97dcef700c | 593 | TiXmlNode* LinkEndChild( TiXmlNode* addThis ); |
| steiger | 0:7c97dcef700c | 594 | |
| steiger | 0:7c97dcef700c | 595 | /** Add a new node related to this. Adds a child before the specified child. |
| steiger | 0:7c97dcef700c | 596 | Returns a pointer to the new object or NULL if an error occured. |
| steiger | 0:7c97dcef700c | 597 | */ |
| steiger | 0:7c97dcef700c | 598 | TiXmlNode* InsertBeforeChild( TiXmlNode* beforeThis, const TiXmlNode& addThis ); |
| steiger | 0:7c97dcef700c | 599 | |
| steiger | 0:7c97dcef700c | 600 | /** Add a new node related to this. Adds a child after the specified child. |
| steiger | 0:7c97dcef700c | 601 | Returns a pointer to the new object or NULL if an error occured. |
| steiger | 0:7c97dcef700c | 602 | */ |
| steiger | 0:7c97dcef700c | 603 | TiXmlNode* InsertAfterChild( TiXmlNode* afterThis, const TiXmlNode& addThis ); |
| steiger | 0:7c97dcef700c | 604 | |
| steiger | 0:7c97dcef700c | 605 | /** Replace a child of this node. |
| steiger | 0:7c97dcef700c | 606 | Returns a pointer to the new object or NULL if an error occured. |
| steiger | 0:7c97dcef700c | 607 | */ |
| steiger | 0:7c97dcef700c | 608 | TiXmlNode* ReplaceChild( TiXmlNode* replaceThis, const TiXmlNode& withThis ); |
| steiger | 0:7c97dcef700c | 609 | |
| steiger | 0:7c97dcef700c | 610 | /// Delete a child of this node. |
| steiger | 0:7c97dcef700c | 611 | bool RemoveChild( TiXmlNode* removeThis ); |
| steiger | 0:7c97dcef700c | 612 | |
| steiger | 0:7c97dcef700c | 613 | /// Navigate to a sibling node. |
| steiger | 0:7c97dcef700c | 614 | const TiXmlNode* PreviousSibling() const { return prev; } |
| steiger | 0:7c97dcef700c | 615 | TiXmlNode* PreviousSibling() { return prev; } |
| steiger | 0:7c97dcef700c | 616 | |
| steiger | 0:7c97dcef700c | 617 | /// Navigate to a sibling node. |
| steiger | 0:7c97dcef700c | 618 | const TiXmlNode* PreviousSibling( const char * ) const; |
| steiger | 0:7c97dcef700c | 619 | TiXmlNode* PreviousSibling( const char *_prev ) { |
| steiger | 0:7c97dcef700c | 620 | return const_cast< TiXmlNode* >( (const_cast< const TiXmlNode* >(this))->PreviousSibling( _prev ) ); |
| steiger | 0:7c97dcef700c | 621 | } |
| steiger | 0:7c97dcef700c | 622 | |
| steiger | 0:7c97dcef700c | 623 | #ifdef TIXML_USE_STL |
| steiger | 0:7c97dcef700c | 624 | const TiXmlNode* PreviousSibling( const std::string& _value ) const { return PreviousSibling (_value.c_str ()); } ///< STL std::string form. |
| steiger | 0:7c97dcef700c | 625 | TiXmlNode* PreviousSibling( const std::string& _value ) { return PreviousSibling (_value.c_str ()); } ///< STL std::string form. |
| steiger | 0:7c97dcef700c | 626 | const TiXmlNode* NextSibling( const std::string& _value) const { return NextSibling (_value.c_str ()); } ///< STL std::string form. |
| steiger | 0:7c97dcef700c | 627 | TiXmlNode* NextSibling( const std::string& _value) { return NextSibling (_value.c_str ()); } ///< STL std::string form. |
| steiger | 0:7c97dcef700c | 628 | #endif |
| steiger | 0:7c97dcef700c | 629 | |
| steiger | 0:7c97dcef700c | 630 | /// Navigate to a sibling node. |
| steiger | 0:7c97dcef700c | 631 | const TiXmlNode* NextSibling() const { return next; } |
| steiger | 0:7c97dcef700c | 632 | TiXmlNode* NextSibling() { return next; } |
| steiger | 0:7c97dcef700c | 633 | |
| steiger | 0:7c97dcef700c | 634 | /// Navigate to a sibling node with the given 'value'. |
| steiger | 0:7c97dcef700c | 635 | const TiXmlNode* NextSibling( const char * ) const; |
| steiger | 0:7c97dcef700c | 636 | TiXmlNode* NextSibling( const char* _next ) { |
| steiger | 0:7c97dcef700c | 637 | return const_cast< TiXmlNode* >( (const_cast< const TiXmlNode* >(this))->NextSibling( _next ) ); |
| steiger | 0:7c97dcef700c | 638 | } |
| steiger | 0:7c97dcef700c | 639 | |
| steiger | 0:7c97dcef700c | 640 | /** Convenience function to get through elements. |
| steiger | 0:7c97dcef700c | 641 | Calls NextSibling and ToElement. Will skip all non-Element |
| steiger | 0:7c97dcef700c | 642 | nodes. Returns 0 if there is not another element. |
| steiger | 0:7c97dcef700c | 643 | */ |
| steiger | 0:7c97dcef700c | 644 | const TiXmlElement* NextSiblingElement() const; |
| steiger | 0:7c97dcef700c | 645 | TiXmlElement* NextSiblingElement() { |
| steiger | 0:7c97dcef700c | 646 | return const_cast< TiXmlElement* >( (const_cast< const TiXmlNode* >(this))->NextSiblingElement() ); |
| steiger | 0:7c97dcef700c | 647 | } |
| steiger | 0:7c97dcef700c | 648 | |
| steiger | 0:7c97dcef700c | 649 | /** Convenience function to get through elements. |
| steiger | 0:7c97dcef700c | 650 | Calls NextSibling and ToElement. Will skip all non-Element |
| steiger | 0:7c97dcef700c | 651 | nodes. Returns 0 if there is not another element. |
| steiger | 0:7c97dcef700c | 652 | */ |
| steiger | 0:7c97dcef700c | 653 | const TiXmlElement* NextSiblingElement( const char * ) const; |
| steiger | 0:7c97dcef700c | 654 | TiXmlElement* NextSiblingElement( const char *_next ) { |
| steiger | 0:7c97dcef700c | 655 | return const_cast< TiXmlElement* >( (const_cast< const TiXmlNode* >(this))->NextSiblingElement( _next ) ); |
| steiger | 0:7c97dcef700c | 656 | } |
| steiger | 0:7c97dcef700c | 657 | |
| steiger | 0:7c97dcef700c | 658 | #ifdef TIXML_USE_STL |
| steiger | 0:7c97dcef700c | 659 | const TiXmlElement* NextSiblingElement( const std::string& _value) const { return NextSiblingElement (_value.c_str ()); } ///< STL std::string form. |
| steiger | 0:7c97dcef700c | 660 | TiXmlElement* NextSiblingElement( const std::string& _value) { return NextSiblingElement (_value.c_str ()); } ///< STL std::string form. |
| steiger | 0:7c97dcef700c | 661 | #endif |
| steiger | 0:7c97dcef700c | 662 | |
| steiger | 0:7c97dcef700c | 663 | /// Convenience function to get through elements. |
| steiger | 0:7c97dcef700c | 664 | const TiXmlElement* FirstChildElement() const; |
| steiger | 0:7c97dcef700c | 665 | TiXmlElement* FirstChildElement() { |
| steiger | 0:7c97dcef700c | 666 | return const_cast< TiXmlElement* >( (const_cast< const TiXmlNode* >(this))->FirstChildElement() ); |
| steiger | 0:7c97dcef700c | 667 | } |
| steiger | 0:7c97dcef700c | 668 | |
| steiger | 0:7c97dcef700c | 669 | /// Convenience function to get through elements. |
| steiger | 0:7c97dcef700c | 670 | const TiXmlElement* FirstChildElement( const char * _value ) const; |
| steiger | 0:7c97dcef700c | 671 | TiXmlElement* FirstChildElement( const char * _value ) { |
| steiger | 0:7c97dcef700c | 672 | return const_cast< TiXmlElement* >( (const_cast< const TiXmlNode* >(this))->FirstChildElement( _value ) ); |
| steiger | 0:7c97dcef700c | 673 | } |
| steiger | 0:7c97dcef700c | 674 | |
| steiger | 0:7c97dcef700c | 675 | #ifdef TIXML_USE_STL |
| steiger | 0:7c97dcef700c | 676 | const TiXmlElement* FirstChildElement( const std::string& _value ) const { return FirstChildElement (_value.c_str ()); } ///< STL std::string form. |
| steiger | 0:7c97dcef700c | 677 | TiXmlElement* FirstChildElement( const std::string& _value ) { return FirstChildElement (_value.c_str ()); } ///< STL std::string form. |
| steiger | 0:7c97dcef700c | 678 | #endif |
| steiger | 0:7c97dcef700c | 679 | |
| steiger | 0:7c97dcef700c | 680 | /** Query the type (as an enumerated value, above) of this node. |
| steiger | 0:7c97dcef700c | 681 | The possible types are: DOCUMENT, ELEMENT, COMMENT, |
| steiger | 0:7c97dcef700c | 682 | UNKNOWN, TEXT, and DECLARATION. |
| steiger | 0:7c97dcef700c | 683 | */ |
| steiger | 0:7c97dcef700c | 684 | int Type() const { return type; } |
| steiger | 0:7c97dcef700c | 685 | |
| steiger | 0:7c97dcef700c | 686 | /** Return a pointer to the Document this node lives in. |
| steiger | 0:7c97dcef700c | 687 | Returns null if not in a document. |
| steiger | 0:7c97dcef700c | 688 | */ |
| steiger | 0:7c97dcef700c | 689 | const TiXmlDocument* GetDocument() const; |
| steiger | 0:7c97dcef700c | 690 | TiXmlDocument* GetDocument() { |
| steiger | 0:7c97dcef700c | 691 | return const_cast< TiXmlDocument* >( (const_cast< const TiXmlNode* >(this))->GetDocument() ); |
| steiger | 0:7c97dcef700c | 692 | } |
| steiger | 0:7c97dcef700c | 693 | |
| steiger | 0:7c97dcef700c | 694 | /// Returns true if this node has no children. |
| steiger | 0:7c97dcef700c | 695 | bool NoChildren() const { return !firstChild; } |
| steiger | 0:7c97dcef700c | 696 | |
| steiger | 0:7c97dcef700c | 697 | virtual const TiXmlDocument* ToDocument() const { return 0; } ///< Cast to a more defined type. Will return null if not of the requested type. |
| steiger | 0:7c97dcef700c | 698 | virtual const TiXmlElement* ToElement() const { return 0; } ///< Cast to a more defined type. Will return null if not of the requested type. |
| steiger | 0:7c97dcef700c | 699 | virtual const TiXmlComment* ToComment() const { return 0; } ///< Cast to a more defined type. Will return null if not of the requested type. |
| steiger | 0:7c97dcef700c | 700 | virtual const TiXmlUnknown* ToUnknown() const { return 0; } ///< Cast to a more defined type. Will return null if not of the requested type. |
| steiger | 0:7c97dcef700c | 701 | virtual const TiXmlText* ToText() const { return 0; } ///< Cast to a more defined type. Will return null if not of the requested type. |
| steiger | 0:7c97dcef700c | 702 | virtual const TiXmlDeclaration* ToDeclaration() const { return 0; } ///< Cast to a more defined type. Will return null if not of the requested type. |
| steiger | 0:7c97dcef700c | 703 | |
| steiger | 0:7c97dcef700c | 704 | virtual TiXmlDocument* ToDocument() { return 0; } ///< Cast to a more defined type. Will return null if not of the requested type. |
| steiger | 0:7c97dcef700c | 705 | virtual TiXmlElement* ToElement() { return 0; } ///< Cast to a more defined type. Will return null if not of the requested type. |
| steiger | 0:7c97dcef700c | 706 | virtual TiXmlComment* ToComment() { return 0; } ///< Cast to a more defined type. Will return null if not of the requested type. |
| steiger | 0:7c97dcef700c | 707 | virtual TiXmlUnknown* ToUnknown() { return 0; } ///< Cast to a more defined type. Will return null if not of the requested type. |
| steiger | 0:7c97dcef700c | 708 | virtual TiXmlText* ToText() { return 0; } ///< Cast to a more defined type. Will return null if not of the requested type. |
| steiger | 0:7c97dcef700c | 709 | virtual TiXmlDeclaration* ToDeclaration() { return 0; } ///< Cast to a more defined type. Will return null if not of the requested type. |
| steiger | 0:7c97dcef700c | 710 | |
| steiger | 0:7c97dcef700c | 711 | /** Create an exact duplicate of this node and return it. The memory must be deleted |
| steiger | 0:7c97dcef700c | 712 | by the caller. |
| steiger | 0:7c97dcef700c | 713 | */ |
| steiger | 0:7c97dcef700c | 714 | virtual TiXmlNode* Clone() const = 0; |
| steiger | 0:7c97dcef700c | 715 | |
| steiger | 0:7c97dcef700c | 716 | /** Accept a hierchical visit the nodes in the TinyXML DOM. Every node in the |
| steiger | 0:7c97dcef700c | 717 | XML tree will be conditionally visited and the host will be called back |
| steiger | 0:7c97dcef700c | 718 | via the TiXmlVisitor interface. |
| steiger | 0:7c97dcef700c | 719 | |
| steiger | 0:7c97dcef700c | 720 | This is essentially a SAX interface for TinyXML. (Note however it doesn't re-parse |
| steiger | 0:7c97dcef700c | 721 | the XML for the callbacks, so the performance of TinyXML is unchanged by using this |
| steiger | 0:7c97dcef700c | 722 | interface versus any other.) |
| steiger | 0:7c97dcef700c | 723 | |
| steiger | 0:7c97dcef700c | 724 | The interface has been based on ideas from: |
| steiger | 0:7c97dcef700c | 725 | |
| steiger | 0:7c97dcef700c | 726 | - http://www.saxproject.org/ |
| steiger | 0:7c97dcef700c | 727 | - http://c2.com/cgi/wiki?HierarchicalVisitorPattern |
| steiger | 0:7c97dcef700c | 728 | |
| steiger | 0:7c97dcef700c | 729 | Which are both good references for "visiting". |
| steiger | 0:7c97dcef700c | 730 | |
| steiger | 0:7c97dcef700c | 731 | An example of using Accept(): |
| steiger | 0:7c97dcef700c | 732 | @verbatim |
| steiger | 0:7c97dcef700c | 733 | TiXmlPrinter printer; |
| steiger | 0:7c97dcef700c | 734 | tinyxmlDoc.Accept( &printer ); |
| steiger | 0:7c97dcef700c | 735 | const char* xmlcstr = printer.CStr(); |
| steiger | 0:7c97dcef700c | 736 | @endverbatim |
| steiger | 0:7c97dcef700c | 737 | */ |
| steiger | 0:7c97dcef700c | 738 | virtual bool Accept( TiXmlVisitor* visitor ) const = 0; |
| steiger | 0:7c97dcef700c | 739 | |
| steiger | 0:7c97dcef700c | 740 | protected: |
| steiger | 0:7c97dcef700c | 741 | TiXmlNode( NodeType _type ); |
| steiger | 0:7c97dcef700c | 742 | |
| steiger | 0:7c97dcef700c | 743 | // Copy to the allocated object. Shared functionality between Clone, Copy constructor, |
| steiger | 0:7c97dcef700c | 744 | // and the assignment operator. |
| steiger | 0:7c97dcef700c | 745 | void CopyTo( TiXmlNode* target ) const; |
| steiger | 0:7c97dcef700c | 746 | |
| steiger | 0:7c97dcef700c | 747 | #ifdef TIXML_USE_STL |
| steiger | 0:7c97dcef700c | 748 | // The real work of the input operator. |
| steiger | 0:7c97dcef700c | 749 | virtual void StreamIn( std::istream* in, TIXML_STRING* tag ) = 0; |
| steiger | 0:7c97dcef700c | 750 | #endif |
| steiger | 0:7c97dcef700c | 751 | |
| steiger | 0:7c97dcef700c | 752 | // Figure out what is at *p, and parse it. Returns null if it is not an xml node. |
| steiger | 0:7c97dcef700c | 753 | TiXmlNode* Identify( const char* start, TiXmlEncoding encoding ); |
| steiger | 0:7c97dcef700c | 754 | |
| steiger | 0:7c97dcef700c | 755 | TiXmlNode* parent; |
| steiger | 0:7c97dcef700c | 756 | NodeType type; |
| steiger | 0:7c97dcef700c | 757 | |
| steiger | 0:7c97dcef700c | 758 | TiXmlNode* firstChild; |
| steiger | 0:7c97dcef700c | 759 | TiXmlNode* lastChild; |
| steiger | 0:7c97dcef700c | 760 | |
| steiger | 0:7c97dcef700c | 761 | TIXML_STRING value; |
| steiger | 0:7c97dcef700c | 762 | |
| steiger | 0:7c97dcef700c | 763 | TiXmlNode* prev; |
| steiger | 0:7c97dcef700c | 764 | TiXmlNode* next; |
| steiger | 0:7c97dcef700c | 765 | |
| steiger | 0:7c97dcef700c | 766 | private: |
| steiger | 0:7c97dcef700c | 767 | TiXmlNode( const TiXmlNode& ); // not implemented. |
| steiger | 0:7c97dcef700c | 768 | void operator=( const TiXmlNode& base ); // not allowed. |
| steiger | 0:7c97dcef700c | 769 | }; |
| steiger | 0:7c97dcef700c | 770 | |
| steiger | 0:7c97dcef700c | 771 | |
| steiger | 0:7c97dcef700c | 772 | /** An attribute is a name-value pair. Elements have an arbitrary |
| steiger | 0:7c97dcef700c | 773 | number of attributes, each with a unique name. |
| steiger | 0:7c97dcef700c | 774 | |
| steiger | 0:7c97dcef700c | 775 | @note The attributes are not TiXmlNodes, since they are not |
| steiger | 0:7c97dcef700c | 776 | part of the tinyXML document object model. There are other |
| steiger | 0:7c97dcef700c | 777 | suggested ways to look at this problem. |
| steiger | 0:7c97dcef700c | 778 | */ |
| steiger | 0:7c97dcef700c | 779 | class TiXmlAttribute : public TiXmlBase |
| steiger | 0:7c97dcef700c | 780 | { |
| steiger | 0:7c97dcef700c | 781 | friend class TiXmlAttributeSet; |
| steiger | 0:7c97dcef700c | 782 | |
| steiger | 0:7c97dcef700c | 783 | public: |
| steiger | 0:7c97dcef700c | 784 | /// Construct an empty attribute. |
| steiger | 0:7c97dcef700c | 785 | TiXmlAttribute() : TiXmlBase() |
| steiger | 0:7c97dcef700c | 786 | { |
| steiger | 0:7c97dcef700c | 787 | document = 0; |
| steiger | 0:7c97dcef700c | 788 | prev = next = 0; |
| steiger | 0:7c97dcef700c | 789 | } |
| steiger | 0:7c97dcef700c | 790 | |
| steiger | 0:7c97dcef700c | 791 | #ifdef TIXML_USE_STL |
| steiger | 0:7c97dcef700c | 792 | /// std::string constructor. |
| steiger | 0:7c97dcef700c | 793 | TiXmlAttribute( const std::string& _name, const std::string& _value ) |
| steiger | 0:7c97dcef700c | 794 | { |
| steiger | 0:7c97dcef700c | 795 | name = _name; |
| steiger | 0:7c97dcef700c | 796 | value = _value; |
| steiger | 0:7c97dcef700c | 797 | document = 0; |
| steiger | 0:7c97dcef700c | 798 | prev = next = 0; |
| steiger | 0:7c97dcef700c | 799 | } |
| steiger | 0:7c97dcef700c | 800 | #endif |
| steiger | 0:7c97dcef700c | 801 | |
| steiger | 0:7c97dcef700c | 802 | /// Construct an attribute with a name and value. |
| steiger | 0:7c97dcef700c | 803 | TiXmlAttribute( const char * _name, const char * _value ) |
| steiger | 0:7c97dcef700c | 804 | { |
| steiger | 0:7c97dcef700c | 805 | name = _name; |
| steiger | 0:7c97dcef700c | 806 | value = _value; |
| steiger | 0:7c97dcef700c | 807 | document = 0; |
| steiger | 0:7c97dcef700c | 808 | prev = next = 0; |
| steiger | 0:7c97dcef700c | 809 | } |
| steiger | 0:7c97dcef700c | 810 | |
| steiger | 0:7c97dcef700c | 811 | const char* Name() const { return name.c_str(); } ///< Return the name of this attribute. |
| steiger | 0:7c97dcef700c | 812 | const char* Value() const { return value.c_str(); } ///< Return the value of this attribute. |
| steiger | 0:7c97dcef700c | 813 | #ifdef TIXML_USE_STL |
| steiger | 0:7c97dcef700c | 814 | const std::string& ValueStr() const { return value; } ///< Return the value of this attribute. |
| steiger | 0:7c97dcef700c | 815 | #endif |
| steiger | 0:7c97dcef700c | 816 | int IntValue() const; ///< Return the value of this attribute, converted to an integer. |
| steiger | 0:7c97dcef700c | 817 | double DoubleValue() const; ///< Return the value of this attribute, converted to a double. |
| steiger | 0:7c97dcef700c | 818 | |
| steiger | 0:7c97dcef700c | 819 | // Get the tinyxml string representation |
| steiger | 0:7c97dcef700c | 820 | const TIXML_STRING& NameTStr() const { return name; } |
| steiger | 0:7c97dcef700c | 821 | |
| steiger | 0:7c97dcef700c | 822 | /** QueryIntValue examines the value string. It is an alternative to the |
| steiger | 0:7c97dcef700c | 823 | IntValue() method with richer error checking. |
| steiger | 0:7c97dcef700c | 824 | If the value is an integer, it is stored in 'value' and |
| steiger | 0:7c97dcef700c | 825 | the call returns TIXML_SUCCESS. If it is not |
| steiger | 0:7c97dcef700c | 826 | an integer, it returns TIXML_WRONG_TYPE. |
| steiger | 0:7c97dcef700c | 827 | |
| steiger | 0:7c97dcef700c | 828 | A specialized but useful call. Note that for success it returns 0, |
| steiger | 0:7c97dcef700c | 829 | which is the opposite of almost all other TinyXml calls. |
| steiger | 0:7c97dcef700c | 830 | */ |
| steiger | 0:7c97dcef700c | 831 | int QueryIntValue( int* _value ) const; |
| steiger | 0:7c97dcef700c | 832 | /// QueryDoubleValue examines the value string. See QueryIntValue(). |
| steiger | 0:7c97dcef700c | 833 | int QueryDoubleValue( double* _value ) const; |
| steiger | 0:7c97dcef700c | 834 | |
| steiger | 0:7c97dcef700c | 835 | void SetName( const char* _name ) { name = _name; } ///< Set the name of this attribute. |
| steiger | 0:7c97dcef700c | 836 | void SetValue( const char* _value ) { value = _value; } ///< Set the value. |
| steiger | 0:7c97dcef700c | 837 | |
| steiger | 0:7c97dcef700c | 838 | void SetIntValue( int _value ); ///< Set the value from an integer. |
| steiger | 0:7c97dcef700c | 839 | void SetDoubleValue( double _value ); ///< Set the value from a double. |
| steiger | 0:7c97dcef700c | 840 | |
| steiger | 0:7c97dcef700c | 841 | #ifdef TIXML_USE_STL |
| steiger | 0:7c97dcef700c | 842 | /// STL std::string form. |
| steiger | 0:7c97dcef700c | 843 | void SetName( const std::string& _name ) { name = _name; } |
| steiger | 0:7c97dcef700c | 844 | /// STL std::string form. |
| steiger | 0:7c97dcef700c | 845 | void SetValue( const std::string& _value ) { value = _value; } |
| steiger | 0:7c97dcef700c | 846 | #endif |
| steiger | 0:7c97dcef700c | 847 | |
| steiger | 0:7c97dcef700c | 848 | /// Get the next sibling attribute in the DOM. Returns null at end. |
| steiger | 0:7c97dcef700c | 849 | const TiXmlAttribute* Next() const; |
| steiger | 0:7c97dcef700c | 850 | TiXmlAttribute* Next() { |
| steiger | 0:7c97dcef700c | 851 | return const_cast< TiXmlAttribute* >( (const_cast< const TiXmlAttribute* >(this))->Next() ); |
| steiger | 0:7c97dcef700c | 852 | } |
| steiger | 0:7c97dcef700c | 853 | |
| steiger | 0:7c97dcef700c | 854 | /// Get the previous sibling attribute in the DOM. Returns null at beginning. |
| steiger | 0:7c97dcef700c | 855 | const TiXmlAttribute* Previous() const; |
| steiger | 0:7c97dcef700c | 856 | TiXmlAttribute* Previous() { |
| steiger | 0:7c97dcef700c | 857 | return const_cast< TiXmlAttribute* >( (const_cast< const TiXmlAttribute* >(this))->Previous() ); |
| steiger | 0:7c97dcef700c | 858 | } |
| steiger | 0:7c97dcef700c | 859 | |
| steiger | 0:7c97dcef700c | 860 | bool operator==( const TiXmlAttribute& rhs ) const { return rhs.name == name; } |
| steiger | 0:7c97dcef700c | 861 | bool operator<( const TiXmlAttribute& rhs ) const { return name < rhs.name; } |
| steiger | 0:7c97dcef700c | 862 | bool operator>( const TiXmlAttribute& rhs ) const { return name > rhs.name; } |
| steiger | 0:7c97dcef700c | 863 | |
| steiger | 0:7c97dcef700c | 864 | /* Attribute parsing starts: first letter of the name |
| steiger | 0:7c97dcef700c | 865 | returns: the next char after the value end quote |
| steiger | 0:7c97dcef700c | 866 | */ |
| steiger | 0:7c97dcef700c | 867 | virtual const char* Parse( const char* p, TiXmlParsingData* data, TiXmlEncoding encoding ); |
| steiger | 0:7c97dcef700c | 868 | |
| steiger | 0:7c97dcef700c | 869 | // Prints this Attribute to a FILE stream. |
| steiger | 0:7c97dcef700c | 870 | virtual void Print( FILE* cfile, int depth ) const { |
| steiger | 0:7c97dcef700c | 871 | Print( cfile, depth, 0 ); |
| steiger | 0:7c97dcef700c | 872 | } |
| steiger | 0:7c97dcef700c | 873 | void Print( FILE* cfile, int depth, TIXML_STRING* str ) const; |
| steiger | 0:7c97dcef700c | 874 | |
| steiger | 0:7c97dcef700c | 875 | // [internal use] |
| steiger | 0:7c97dcef700c | 876 | // Set the document pointer so the attribute can report errors. |
| steiger | 0:7c97dcef700c | 877 | void SetDocument( TiXmlDocument* doc ) { document = doc; } |
| steiger | 0:7c97dcef700c | 878 | |
| steiger | 0:7c97dcef700c | 879 | private: |
| steiger | 0:7c97dcef700c | 880 | TiXmlAttribute( const TiXmlAttribute& ); // not implemented. |
| steiger | 0:7c97dcef700c | 881 | void operator=( const TiXmlAttribute& base ); // not allowed. |
| steiger | 0:7c97dcef700c | 882 | |
| steiger | 0:7c97dcef700c | 883 | TiXmlDocument* document; // A pointer back to a document, for error reporting. |
| steiger | 0:7c97dcef700c | 884 | TIXML_STRING name; |
| steiger | 0:7c97dcef700c | 885 | TIXML_STRING value; |
| steiger | 0:7c97dcef700c | 886 | TiXmlAttribute* prev; |
| steiger | 0:7c97dcef700c | 887 | TiXmlAttribute* next; |
| steiger | 0:7c97dcef700c | 888 | }; |
| steiger | 0:7c97dcef700c | 889 | |
| steiger | 0:7c97dcef700c | 890 | |
| steiger | 0:7c97dcef700c | 891 | /* A class used to manage a group of attributes. |
| steiger | 0:7c97dcef700c | 892 | It is only used internally, both by the ELEMENT and the DECLARATION. |
| steiger | 0:7c97dcef700c | 893 | |
| steiger | 0:7c97dcef700c | 894 | The set can be changed transparent to the Element and Declaration |
| steiger | 0:7c97dcef700c | 895 | classes that use it, but NOT transparent to the Attribute |
| steiger | 0:7c97dcef700c | 896 | which has to implement a next() and previous() method. Which makes |
| steiger | 0:7c97dcef700c | 897 | it a bit problematic and prevents the use of STL. |
| steiger | 0:7c97dcef700c | 898 | |
| steiger | 0:7c97dcef700c | 899 | This version is implemented with circular lists because: |
| steiger | 0:7c97dcef700c | 900 | - I like circular lists |
| steiger | 0:7c97dcef700c | 901 | - it demonstrates some independence from the (typical) doubly linked list. |
| steiger | 0:7c97dcef700c | 902 | */ |
| steiger | 0:7c97dcef700c | 903 | class TiXmlAttributeSet |
| steiger | 0:7c97dcef700c | 904 | { |
| steiger | 0:7c97dcef700c | 905 | public: |
| steiger | 0:7c97dcef700c | 906 | TiXmlAttributeSet(); |
| steiger | 0:7c97dcef700c | 907 | ~TiXmlAttributeSet(); |
| steiger | 0:7c97dcef700c | 908 | |
| steiger | 0:7c97dcef700c | 909 | void Add( TiXmlAttribute* attribute ); |
| steiger | 0:7c97dcef700c | 910 | void Remove( TiXmlAttribute* attribute ); |
| steiger | 0:7c97dcef700c | 911 | |
| steiger | 0:7c97dcef700c | 912 | const TiXmlAttribute* First() const { return ( sentinel.next == &sentinel ) ? 0 : sentinel.next; } |
| steiger | 0:7c97dcef700c | 913 | TiXmlAttribute* First() { return ( sentinel.next == &sentinel ) ? 0 : sentinel.next; } |
| steiger | 0:7c97dcef700c | 914 | const TiXmlAttribute* Last() const { return ( sentinel.prev == &sentinel ) ? 0 : sentinel.prev; } |
| steiger | 0:7c97dcef700c | 915 | TiXmlAttribute* Last() { return ( sentinel.prev == &sentinel ) ? 0 : sentinel.prev; } |
| steiger | 0:7c97dcef700c | 916 | |
| steiger | 0:7c97dcef700c | 917 | TiXmlAttribute* Find( const char* _name ) const; |
| steiger | 0:7c97dcef700c | 918 | TiXmlAttribute* FindOrCreate( const char* _name ); |
| steiger | 0:7c97dcef700c | 919 | |
| steiger | 0:7c97dcef700c | 920 | # ifdef TIXML_USE_STL |
| steiger | 0:7c97dcef700c | 921 | TiXmlAttribute* Find( const std::string& _name ) const; |
| steiger | 0:7c97dcef700c | 922 | TiXmlAttribute* FindOrCreate( const std::string& _name ); |
| steiger | 0:7c97dcef700c | 923 | # endif |
| steiger | 0:7c97dcef700c | 924 | |
| steiger | 0:7c97dcef700c | 925 | |
| steiger | 0:7c97dcef700c | 926 | private: |
| steiger | 0:7c97dcef700c | 927 | //*ME: Because of hidden/disabled copy-construktor in TiXmlAttribute (sentinel-element), |
| steiger | 0:7c97dcef700c | 928 | //*ME: this class must be also use a hidden/disabled copy-constructor !!! |
| steiger | 0:7c97dcef700c | 929 | TiXmlAttributeSet( const TiXmlAttributeSet& ); // not allowed |
| steiger | 0:7c97dcef700c | 930 | void operator=( const TiXmlAttributeSet& ); // not allowed (as TiXmlAttribute) |
| steiger | 0:7c97dcef700c | 931 | |
| steiger | 0:7c97dcef700c | 932 | TiXmlAttribute sentinel; |
| steiger | 0:7c97dcef700c | 933 | }; |
| steiger | 0:7c97dcef700c | 934 | |
| steiger | 0:7c97dcef700c | 935 | |
| steiger | 0:7c97dcef700c | 936 | /** The element is a container class. It has a value, the element name, |
| steiger | 0:7c97dcef700c | 937 | and can contain other elements, text, comments, and unknowns. |
| steiger | 0:7c97dcef700c | 938 | Elements also contain an arbitrary number of attributes. |
| steiger | 0:7c97dcef700c | 939 | */ |
| steiger | 0:7c97dcef700c | 940 | class TiXmlElement : public TiXmlNode |
| steiger | 0:7c97dcef700c | 941 | { |
| steiger | 0:7c97dcef700c | 942 | public: |
| steiger | 0:7c97dcef700c | 943 | /// Construct an element. |
| steiger | 0:7c97dcef700c | 944 | TiXmlElement (const char * in_value); |
| steiger | 0:7c97dcef700c | 945 | |
| steiger | 0:7c97dcef700c | 946 | #ifdef TIXML_USE_STL |
| steiger | 0:7c97dcef700c | 947 | /// std::string constructor. |
| steiger | 0:7c97dcef700c | 948 | TiXmlElement( const std::string& _value ); |
| steiger | 0:7c97dcef700c | 949 | #endif |
| steiger | 0:7c97dcef700c | 950 | |
| steiger | 0:7c97dcef700c | 951 | TiXmlElement( const TiXmlElement& ); |
| steiger | 0:7c97dcef700c | 952 | |
| steiger | 0:7c97dcef700c | 953 | void operator=( const TiXmlElement& base ); |
| steiger | 0:7c97dcef700c | 954 | |
| steiger | 0:7c97dcef700c | 955 | virtual ~TiXmlElement(); |
| steiger | 0:7c97dcef700c | 956 | |
| steiger | 0:7c97dcef700c | 957 | /** Given an attribute name, Attribute() returns the value |
| steiger | 0:7c97dcef700c | 958 | for the attribute of that name, or null if none exists. |
| steiger | 0:7c97dcef700c | 959 | */ |
| steiger | 0:7c97dcef700c | 960 | const char* Attribute( const char* name ) const; |
| steiger | 0:7c97dcef700c | 961 | |
| steiger | 0:7c97dcef700c | 962 | /** Given an attribute name, Attribute() returns the value |
| steiger | 0:7c97dcef700c | 963 | for the attribute of that name, or null if none exists. |
| steiger | 0:7c97dcef700c | 964 | If the attribute exists and can be converted to an integer, |
| steiger | 0:7c97dcef700c | 965 | the integer value will be put in the return 'i', if 'i' |
| steiger | 0:7c97dcef700c | 966 | is non-null. |
| steiger | 0:7c97dcef700c | 967 | */ |
| steiger | 0:7c97dcef700c | 968 | const char* Attribute( const char* name, int* i ) const; |
| steiger | 0:7c97dcef700c | 969 | |
| steiger | 0:7c97dcef700c | 970 | /** Given an attribute name, Attribute() returns the value |
| steiger | 0:7c97dcef700c | 971 | for the attribute of that name, or null if none exists. |
| steiger | 0:7c97dcef700c | 972 | If the attribute exists and can be converted to an double, |
| steiger | 0:7c97dcef700c | 973 | the double value will be put in the return 'd', if 'd' |
| steiger | 0:7c97dcef700c | 974 | is non-null. |
| steiger | 0:7c97dcef700c | 975 | */ |
| steiger | 0:7c97dcef700c | 976 | const char* Attribute( const char* name, double* d ) const; |
| steiger | 0:7c97dcef700c | 977 | |
| steiger | 0:7c97dcef700c | 978 | /** QueryIntAttribute examines the attribute - it is an alternative to the |
| steiger | 0:7c97dcef700c | 979 | Attribute() method with richer error checking. |
| steiger | 0:7c97dcef700c | 980 | If the attribute is an integer, it is stored in 'value' and |
| steiger | 0:7c97dcef700c | 981 | the call returns TIXML_SUCCESS. If it is not |
| steiger | 0:7c97dcef700c | 982 | an integer, it returns TIXML_WRONG_TYPE. If the attribute |
| steiger | 0:7c97dcef700c | 983 | does not exist, then TIXML_NO_ATTRIBUTE is returned. |
| steiger | 0:7c97dcef700c | 984 | */ |
| steiger | 0:7c97dcef700c | 985 | int QueryIntAttribute( const char* name, int* _value ) const; |
| steiger | 0:7c97dcef700c | 986 | /// QueryDoubleAttribute examines the attribute - see QueryIntAttribute(). |
| steiger | 0:7c97dcef700c | 987 | int QueryDoubleAttribute( const char* name, double* _value ) const; |
| steiger | 0:7c97dcef700c | 988 | /// QueryFloatAttribute examines the attribute - see QueryIntAttribute(). |
| steiger | 0:7c97dcef700c | 989 | int QueryFloatAttribute( const char* name, float* _value ) const { |
| steiger | 0:7c97dcef700c | 990 | double d; |
| steiger | 0:7c97dcef700c | 991 | int result = QueryDoubleAttribute( name, &d ); |
| steiger | 0:7c97dcef700c | 992 | if ( result == TIXML_SUCCESS ) { |
| steiger | 0:7c97dcef700c | 993 | *_value = (float)d; |
| steiger | 0:7c97dcef700c | 994 | } |
| steiger | 0:7c97dcef700c | 995 | return result; |
| steiger | 0:7c97dcef700c | 996 | } |
| steiger | 0:7c97dcef700c | 997 | |
| steiger | 0:7c97dcef700c | 998 | #ifdef TIXML_USE_STL |
| steiger | 0:7c97dcef700c | 999 | /// QueryStringAttribute examines the attribute - see QueryIntAttribute(). |
| steiger | 0:7c97dcef700c | 1000 | int QueryStringAttribute( const char* name, std::string* _value ) const { |
| steiger | 0:7c97dcef700c | 1001 | const char* cstr = Attribute( name ); |
| steiger | 0:7c97dcef700c | 1002 | if ( cstr ) { |
| steiger | 0:7c97dcef700c | 1003 | *_value = std::string( cstr ); |
| steiger | 0:7c97dcef700c | 1004 | return TIXML_SUCCESS; |
| steiger | 0:7c97dcef700c | 1005 | } |
| steiger | 0:7c97dcef700c | 1006 | return TIXML_NO_ATTRIBUTE; |
| steiger | 0:7c97dcef700c | 1007 | } |
| steiger | 0:7c97dcef700c | 1008 | |
| steiger | 0:7c97dcef700c | 1009 | /** Template form of the attribute query which will try to read the |
| steiger | 0:7c97dcef700c | 1010 | attribute into the specified type. Very easy, very powerful, but |
| steiger | 0:7c97dcef700c | 1011 | be careful to make sure to call this with the correct type. |
| steiger | 0:7c97dcef700c | 1012 | |
| steiger | 0:7c97dcef700c | 1013 | NOTE: This method doesn't work correctly for 'string' types that contain spaces. |
| steiger | 0:7c97dcef700c | 1014 | |
| steiger | 0:7c97dcef700c | 1015 | @return TIXML_SUCCESS, TIXML_WRONG_TYPE, or TIXML_NO_ATTRIBUTE |
| steiger | 0:7c97dcef700c | 1016 | */ |
| steiger | 0:7c97dcef700c | 1017 | template< typename T > int QueryValueAttribute( const std::string& name, T* outValue ) const |
| steiger | 0:7c97dcef700c | 1018 | { |
| steiger | 0:7c97dcef700c | 1019 | const TiXmlAttribute* node = attributeSet.Find( name ); |
| steiger | 0:7c97dcef700c | 1020 | if ( !node ) |
| steiger | 0:7c97dcef700c | 1021 | return TIXML_NO_ATTRIBUTE; |
| steiger | 0:7c97dcef700c | 1022 | |
| steiger | 0:7c97dcef700c | 1023 | std::stringstream sstream( node->ValueStr() ); |
| steiger | 0:7c97dcef700c | 1024 | sstream >> *outValue; |
| steiger | 0:7c97dcef700c | 1025 | if ( !sstream.fail() ) |
| steiger | 0:7c97dcef700c | 1026 | return TIXML_SUCCESS; |
| steiger | 0:7c97dcef700c | 1027 | return TIXML_WRONG_TYPE; |
| steiger | 0:7c97dcef700c | 1028 | } |
| steiger | 0:7c97dcef700c | 1029 | |
| steiger | 0:7c97dcef700c | 1030 | int QueryValueAttribute( const std::string& name, std::string* outValue ) const |
| steiger | 0:7c97dcef700c | 1031 | { |
| steiger | 0:7c97dcef700c | 1032 | const TiXmlAttribute* node = attributeSet.Find( name ); |
| steiger | 0:7c97dcef700c | 1033 | if ( !node ) |
| steiger | 0:7c97dcef700c | 1034 | return TIXML_NO_ATTRIBUTE; |
| steiger | 0:7c97dcef700c | 1035 | *outValue = node->ValueStr(); |
| steiger | 0:7c97dcef700c | 1036 | return TIXML_SUCCESS; |
| steiger | 0:7c97dcef700c | 1037 | } |
| steiger | 0:7c97dcef700c | 1038 | #endif |
| steiger | 0:7c97dcef700c | 1039 | |
| steiger | 0:7c97dcef700c | 1040 | /** Sets an attribute of name to a given value. The attribute |
| steiger | 0:7c97dcef700c | 1041 | will be created if it does not exist, or changed if it does. |
| steiger | 0:7c97dcef700c | 1042 | */ |
| steiger | 0:7c97dcef700c | 1043 | void SetAttribute( const char* name, const char * _value ); |
| steiger | 0:7c97dcef700c | 1044 | |
| steiger | 0:7c97dcef700c | 1045 | #ifdef TIXML_USE_STL |
| steiger | 0:7c97dcef700c | 1046 | const std::string* Attribute( const std::string& name ) const; |
| steiger | 0:7c97dcef700c | 1047 | const std::string* Attribute( const std::string& name, int* i ) const; |
| steiger | 0:7c97dcef700c | 1048 | const std::string* Attribute( const std::string& name, double* d ) const; |
| steiger | 0:7c97dcef700c | 1049 | int QueryIntAttribute( const std::string& name, int* _value ) const; |
| steiger | 0:7c97dcef700c | 1050 | int QueryDoubleAttribute( const std::string& name, double* _value ) const; |
| steiger | 0:7c97dcef700c | 1051 | |
| steiger | 0:7c97dcef700c | 1052 | /// STL std::string form. |
| steiger | 0:7c97dcef700c | 1053 | void SetAttribute( const std::string& name, const std::string& _value ); |
| steiger | 0:7c97dcef700c | 1054 | ///< STL std::string form. |
| steiger | 0:7c97dcef700c | 1055 | void SetAttribute( const std::string& name, int _value ); |
| steiger | 0:7c97dcef700c | 1056 | ///< STL std::string form. |
| steiger | 0:7c97dcef700c | 1057 | void SetDoubleAttribute( const std::string& name, double value ); |
| steiger | 0:7c97dcef700c | 1058 | #endif |
| steiger | 0:7c97dcef700c | 1059 | |
| steiger | 0:7c97dcef700c | 1060 | /** Sets an attribute of name to a given value. The attribute |
| steiger | 0:7c97dcef700c | 1061 | will be created if it does not exist, or changed if it does. |
| steiger | 0:7c97dcef700c | 1062 | */ |
| steiger | 0:7c97dcef700c | 1063 | void SetAttribute( const char * name, int value ); |
| steiger | 0:7c97dcef700c | 1064 | |
| steiger | 0:7c97dcef700c | 1065 | /** Sets an attribute of name to a given value. The attribute |
| steiger | 0:7c97dcef700c | 1066 | will be created if it does not exist, or changed if it does. |
| steiger | 0:7c97dcef700c | 1067 | */ |
| steiger | 0:7c97dcef700c | 1068 | void SetDoubleAttribute( const char * name, double value ); |
| steiger | 0:7c97dcef700c | 1069 | |
| steiger | 0:7c97dcef700c | 1070 | /** Deletes an attribute with the given name. |
| steiger | 0:7c97dcef700c | 1071 | */ |
| steiger | 0:7c97dcef700c | 1072 | void RemoveAttribute( const char * name ); |
| steiger | 0:7c97dcef700c | 1073 | #ifdef TIXML_USE_STL |
| steiger | 0:7c97dcef700c | 1074 | void RemoveAttribute( const std::string& name ) { RemoveAttribute (name.c_str ()); } ///< STL std::string form. |
| steiger | 0:7c97dcef700c | 1075 | #endif |
| steiger | 0:7c97dcef700c | 1076 | |
| steiger | 0:7c97dcef700c | 1077 | const TiXmlAttribute* FirstAttribute() const { return attributeSet.First(); } ///< Access the first attribute in this element. |
| steiger | 0:7c97dcef700c | 1078 | TiXmlAttribute* FirstAttribute() { return attributeSet.First(); } |
| steiger | 0:7c97dcef700c | 1079 | const TiXmlAttribute* LastAttribute() const { return attributeSet.Last(); } ///< Access the last attribute in this element. |
| steiger | 0:7c97dcef700c | 1080 | TiXmlAttribute* LastAttribute() { return attributeSet.Last(); } |
| steiger | 0:7c97dcef700c | 1081 | |
| steiger | 0:7c97dcef700c | 1082 | /** Convenience function for easy access to the text inside an element. Although easy |
| steiger | 0:7c97dcef700c | 1083 | and concise, GetText() is limited compared to getting the TiXmlText child |
| steiger | 0:7c97dcef700c | 1084 | and accessing it directly. |
| steiger | 0:7c97dcef700c | 1085 | |
| steiger | 0:7c97dcef700c | 1086 | If the first child of 'this' is a TiXmlText, the GetText() |
| steiger | 0:7c97dcef700c | 1087 | returns the character string of the Text node, else null is returned. |
| steiger | 0:7c97dcef700c | 1088 | |
| steiger | 0:7c97dcef700c | 1089 | This is a convenient method for getting the text of simple contained text: |
| steiger | 0:7c97dcef700c | 1090 | @verbatim |
| steiger | 0:7c97dcef700c | 1091 | <foo>This is text</foo> |
| steiger | 0:7c97dcef700c | 1092 | const char* str = fooElement->GetText(); |
| steiger | 0:7c97dcef700c | 1093 | @endverbatim |
| steiger | 0:7c97dcef700c | 1094 | |
| steiger | 0:7c97dcef700c | 1095 | 'str' will be a pointer to "This is text". |
| steiger | 0:7c97dcef700c | 1096 | |
| steiger | 0:7c97dcef700c | 1097 | Note that this function can be misleading. If the element foo was created from |
| steiger | 0:7c97dcef700c | 1098 | this XML: |
| steiger | 0:7c97dcef700c | 1099 | @verbatim |
| steiger | 0:7c97dcef700c | 1100 | <foo><b>This is text</b></foo> |
| steiger | 0:7c97dcef700c | 1101 | @endverbatim |
| steiger | 0:7c97dcef700c | 1102 | |
| steiger | 0:7c97dcef700c | 1103 | then the value of str would be null. The first child node isn't a text node, it is |
| steiger | 0:7c97dcef700c | 1104 | another element. From this XML: |
| steiger | 0:7c97dcef700c | 1105 | @verbatim |
| steiger | 0:7c97dcef700c | 1106 | <foo>This is <b>text</b></foo> |
| steiger | 0:7c97dcef700c | 1107 | @endverbatim |
| steiger | 0:7c97dcef700c | 1108 | GetText() will return "This is ". |
| steiger | 0:7c97dcef700c | 1109 | |
| steiger | 0:7c97dcef700c | 1110 | WARNING: GetText() accesses a child node - don't become confused with the |
| steiger | 0:7c97dcef700c | 1111 | similarly named TiXmlHandle::Text() and TiXmlNode::ToText() which are |
| steiger | 0:7c97dcef700c | 1112 | safe type casts on the referenced node. |
| steiger | 0:7c97dcef700c | 1113 | */ |
| steiger | 0:7c97dcef700c | 1114 | const char* GetText() const; |
| steiger | 0:7c97dcef700c | 1115 | |
| steiger | 0:7c97dcef700c | 1116 | /// Creates a new Element and returns it - the returned element is a copy. |
| steiger | 0:7c97dcef700c | 1117 | virtual TiXmlNode* Clone() const; |
| steiger | 0:7c97dcef700c | 1118 | // Print the Element to a FILE stream. |
| steiger | 0:7c97dcef700c | 1119 | virtual void Print( FILE* cfile, int depth ) const; |
| steiger | 0:7c97dcef700c | 1120 | |
| steiger | 0:7c97dcef700c | 1121 | /* Attribtue parsing starts: next char past '<' |
| steiger | 0:7c97dcef700c | 1122 | returns: next char past '>' |
| steiger | 0:7c97dcef700c | 1123 | */ |
| steiger | 0:7c97dcef700c | 1124 | virtual const char* Parse( const char* p, TiXmlParsingData* data, TiXmlEncoding encoding ); |
| steiger | 0:7c97dcef700c | 1125 | |
| steiger | 0:7c97dcef700c | 1126 | virtual const TiXmlElement* ToElement() const { return this; } ///< Cast to a more defined type. Will return null not of the requested type. |
| steiger | 0:7c97dcef700c | 1127 | virtual TiXmlElement* ToElement() { return this; } ///< Cast to a more defined type. Will return null not of the requested type. |
| steiger | 0:7c97dcef700c | 1128 | |
| steiger | 0:7c97dcef700c | 1129 | /** Walk the XML tree visiting this node and all of its children. |
| steiger | 0:7c97dcef700c | 1130 | */ |
| steiger | 0:7c97dcef700c | 1131 | virtual bool Accept( TiXmlVisitor* visitor ) const; |
| steiger | 0:7c97dcef700c | 1132 | |
| steiger | 0:7c97dcef700c | 1133 | protected: |
| steiger | 0:7c97dcef700c | 1134 | |
| steiger | 0:7c97dcef700c | 1135 | void CopyTo( TiXmlElement* target ) const; |
| steiger | 0:7c97dcef700c | 1136 | void ClearThis(); // like clear, but initializes 'this' object as well |
| steiger | 0:7c97dcef700c | 1137 | |
| steiger | 0:7c97dcef700c | 1138 | // Used to be public [internal use] |
| steiger | 0:7c97dcef700c | 1139 | #ifdef TIXML_USE_STL |
| steiger | 0:7c97dcef700c | 1140 | virtual void StreamIn( std::istream * in, TIXML_STRING * tag ); |
| steiger | 0:7c97dcef700c | 1141 | #endif |
| steiger | 0:7c97dcef700c | 1142 | /* [internal use] |
| steiger | 0:7c97dcef700c | 1143 | Reads the "value" of the element -- another element, or text. |
| steiger | 0:7c97dcef700c | 1144 | This should terminate with the current end tag. |
| steiger | 0:7c97dcef700c | 1145 | */ |
| steiger | 0:7c97dcef700c | 1146 | const char* ReadValue( const char* in, TiXmlParsingData* prevData, TiXmlEncoding encoding ); |
| steiger | 0:7c97dcef700c | 1147 | |
| steiger | 0:7c97dcef700c | 1148 | private: |
| steiger | 0:7c97dcef700c | 1149 | TiXmlAttributeSet attributeSet; |
| steiger | 0:7c97dcef700c | 1150 | }; |
| steiger | 0:7c97dcef700c | 1151 | |
| steiger | 0:7c97dcef700c | 1152 | |
| steiger | 0:7c97dcef700c | 1153 | /** An XML comment. |
| steiger | 0:7c97dcef700c | 1154 | */ |
| steiger | 0:7c97dcef700c | 1155 | class TiXmlComment : public TiXmlNode |
| steiger | 0:7c97dcef700c | 1156 | { |
| steiger | 0:7c97dcef700c | 1157 | public: |
| steiger | 0:7c97dcef700c | 1158 | /// Constructs an empty comment. |
| steiger | 0:7c97dcef700c | 1159 | TiXmlComment() : TiXmlNode( TiXmlNode::TINYXML_COMMENT ) {} |
| steiger | 0:7c97dcef700c | 1160 | /// Construct a comment from text. |
| steiger | 0:7c97dcef700c | 1161 | TiXmlComment( const char* _value ) : TiXmlNode( TiXmlNode::TINYXML_COMMENT ) { |
| steiger | 0:7c97dcef700c | 1162 | SetValue( _value ); |
| steiger | 0:7c97dcef700c | 1163 | } |
| steiger | 0:7c97dcef700c | 1164 | TiXmlComment( const TiXmlComment& ); |
| steiger | 0:7c97dcef700c | 1165 | void operator=( const TiXmlComment& base ); |
| steiger | 0:7c97dcef700c | 1166 | |
| steiger | 0:7c97dcef700c | 1167 | virtual ~TiXmlComment() {} |
| steiger | 0:7c97dcef700c | 1168 | |
| steiger | 0:7c97dcef700c | 1169 | /// Returns a copy of this Comment. |
| steiger | 0:7c97dcef700c | 1170 | virtual TiXmlNode* Clone() const; |
| steiger | 0:7c97dcef700c | 1171 | // Write this Comment to a FILE stream. |
| steiger | 0:7c97dcef700c | 1172 | virtual void Print( FILE* cfile, int depth ) const; |
| steiger | 0:7c97dcef700c | 1173 | |
| steiger | 0:7c97dcef700c | 1174 | /* Attribtue parsing starts: at the ! of the !-- |
| steiger | 0:7c97dcef700c | 1175 | returns: next char past '>' |
| steiger | 0:7c97dcef700c | 1176 | */ |
| steiger | 0:7c97dcef700c | 1177 | virtual const char* Parse( const char* p, TiXmlParsingData* data, TiXmlEncoding encoding ); |
| steiger | 0:7c97dcef700c | 1178 | |
| steiger | 0:7c97dcef700c | 1179 | virtual const TiXmlComment* ToComment() const { return this; } ///< Cast to a more defined type. Will return null not of the requested type. |
| steiger | 0:7c97dcef700c | 1180 | virtual TiXmlComment* ToComment() { return this; } ///< Cast to a more defined type. Will return null not of the requested type. |
| steiger | 0:7c97dcef700c | 1181 | |
| steiger | 0:7c97dcef700c | 1182 | /** Walk the XML tree visiting this node and all of its children. |
| steiger | 0:7c97dcef700c | 1183 | */ |
| steiger | 0:7c97dcef700c | 1184 | virtual bool Accept( TiXmlVisitor* visitor ) const; |
| steiger | 0:7c97dcef700c | 1185 | |
| steiger | 0:7c97dcef700c | 1186 | protected: |
| steiger | 0:7c97dcef700c | 1187 | void CopyTo( TiXmlComment* target ) const; |
| steiger | 0:7c97dcef700c | 1188 | |
| steiger | 0:7c97dcef700c | 1189 | // used to be public |
| steiger | 0:7c97dcef700c | 1190 | #ifdef TIXML_USE_STL |
| steiger | 0:7c97dcef700c | 1191 | virtual void StreamIn( std::istream * in, TIXML_STRING * tag ); |
| steiger | 0:7c97dcef700c | 1192 | #endif |
| steiger | 0:7c97dcef700c | 1193 | // virtual void StreamOut( TIXML_OSTREAM * out ) const; |
| steiger | 0:7c97dcef700c | 1194 | |
| steiger | 0:7c97dcef700c | 1195 | private: |
| steiger | 0:7c97dcef700c | 1196 | |
| steiger | 0:7c97dcef700c | 1197 | }; |
| steiger | 0:7c97dcef700c | 1198 | |
| steiger | 0:7c97dcef700c | 1199 | |
| steiger | 0:7c97dcef700c | 1200 | /** XML text. A text node can have 2 ways to output the next. "normal" output |
| steiger | 0:7c97dcef700c | 1201 | and CDATA. It will default to the mode it was parsed from the XML file and |
| steiger | 0:7c97dcef700c | 1202 | you generally want to leave it alone, but you can change the output mode with |
| steiger | 0:7c97dcef700c | 1203 | SetCDATA() and query it with CDATA(). |
| steiger | 0:7c97dcef700c | 1204 | */ |
| steiger | 0:7c97dcef700c | 1205 | class TiXmlText : public TiXmlNode |
| steiger | 0:7c97dcef700c | 1206 | { |
| steiger | 0:7c97dcef700c | 1207 | friend class TiXmlElement; |
| steiger | 0:7c97dcef700c | 1208 | public: |
| steiger | 0:7c97dcef700c | 1209 | /** Constructor for text element. By default, it is treated as |
| steiger | 0:7c97dcef700c | 1210 | normal, encoded text. If you want it be output as a CDATA text |
| steiger | 0:7c97dcef700c | 1211 | element, set the parameter _cdata to 'true' |
| steiger | 0:7c97dcef700c | 1212 | */ |
| steiger | 0:7c97dcef700c | 1213 | TiXmlText (const char * initValue ) : TiXmlNode (TiXmlNode::TINYXML_TEXT) |
| steiger | 0:7c97dcef700c | 1214 | { |
| steiger | 0:7c97dcef700c | 1215 | SetValue( initValue ); |
| steiger | 0:7c97dcef700c | 1216 | cdata = false; |
| steiger | 0:7c97dcef700c | 1217 | } |
| steiger | 0:7c97dcef700c | 1218 | virtual ~TiXmlText() {} |
| steiger | 0:7c97dcef700c | 1219 | |
| steiger | 0:7c97dcef700c | 1220 | #ifdef TIXML_USE_STL |
| steiger | 0:7c97dcef700c | 1221 | /// Constructor. |
| steiger | 0:7c97dcef700c | 1222 | TiXmlText( const std::string& initValue ) : TiXmlNode (TiXmlNode::TINYXML_TEXT) |
| steiger | 0:7c97dcef700c | 1223 | { |
| steiger | 0:7c97dcef700c | 1224 | SetValue( initValue ); |
| steiger | 0:7c97dcef700c | 1225 | cdata = false; |
| steiger | 0:7c97dcef700c | 1226 | } |
| steiger | 0:7c97dcef700c | 1227 | #endif |
| steiger | 0:7c97dcef700c | 1228 | |
| steiger | 0:7c97dcef700c | 1229 | TiXmlText( const TiXmlText& copy ) : TiXmlNode( TiXmlNode::TINYXML_TEXT ) { copy.CopyTo( this ); } |
| steiger | 0:7c97dcef700c | 1230 | void operator=( const TiXmlText& base ) { base.CopyTo( this ); } |
| steiger | 0:7c97dcef700c | 1231 | |
| steiger | 0:7c97dcef700c | 1232 | // Write this text object to a FILE stream. |
| steiger | 0:7c97dcef700c | 1233 | virtual void Print( FILE* cfile, int depth ) const; |
| steiger | 0:7c97dcef700c | 1234 | |
| steiger | 0:7c97dcef700c | 1235 | /// Queries whether this represents text using a CDATA section. |
| steiger | 0:7c97dcef700c | 1236 | bool CDATA() const { return cdata; } |
| steiger | 0:7c97dcef700c | 1237 | /// Turns on or off a CDATA representation of text. |
| steiger | 0:7c97dcef700c | 1238 | void SetCDATA( bool _cdata ) { cdata = _cdata; } |
| steiger | 0:7c97dcef700c | 1239 | |
| steiger | 0:7c97dcef700c | 1240 | virtual const char* Parse( const char* p, TiXmlParsingData* data, TiXmlEncoding encoding ); |
| steiger | 0:7c97dcef700c | 1241 | |
| steiger | 0:7c97dcef700c | 1242 | virtual const TiXmlText* ToText() const { return this; } ///< Cast to a more defined type. Will return null not of the requested type. |
| steiger | 0:7c97dcef700c | 1243 | virtual TiXmlText* ToText() { return this; } ///< Cast to a more defined type. Will return null not of the requested type. |
| steiger | 0:7c97dcef700c | 1244 | |
| steiger | 0:7c97dcef700c | 1245 | /** Walk the XML tree visiting this node and all of its children. |
| steiger | 0:7c97dcef700c | 1246 | */ |
| steiger | 0:7c97dcef700c | 1247 | virtual bool Accept( TiXmlVisitor* content ) const; |
| steiger | 0:7c97dcef700c | 1248 | |
| steiger | 0:7c97dcef700c | 1249 | protected : |
| steiger | 0:7c97dcef700c | 1250 | /// [internal use] Creates a new Element and returns it. |
| steiger | 0:7c97dcef700c | 1251 | virtual TiXmlNode* Clone() const; |
| steiger | 0:7c97dcef700c | 1252 | void CopyTo( TiXmlText* target ) const; |
| steiger | 0:7c97dcef700c | 1253 | |
| steiger | 0:7c97dcef700c | 1254 | bool Blank() const; // returns true if all white space and new lines |
| steiger | 0:7c97dcef700c | 1255 | // [internal use] |
| steiger | 0:7c97dcef700c | 1256 | #ifdef TIXML_USE_STL |
| steiger | 0:7c97dcef700c | 1257 | virtual void StreamIn( std::istream * in, TIXML_STRING * tag ); |
| steiger | 0:7c97dcef700c | 1258 | #endif |
| steiger | 0:7c97dcef700c | 1259 | |
| steiger | 0:7c97dcef700c | 1260 | private: |
| steiger | 0:7c97dcef700c | 1261 | bool cdata; // true if this should be input and output as a CDATA style text element |
| steiger | 0:7c97dcef700c | 1262 | }; |
| steiger | 0:7c97dcef700c | 1263 | |
| steiger | 0:7c97dcef700c | 1264 | |
| steiger | 0:7c97dcef700c | 1265 | /** In correct XML the declaration is the first entry in the file. |
| steiger | 0:7c97dcef700c | 1266 | @verbatim |
| steiger | 0:7c97dcef700c | 1267 | <?xml version="1.0" standalone="yes"?> |
| steiger | 0:7c97dcef700c | 1268 | @endverbatim |
| steiger | 0:7c97dcef700c | 1269 | |
| steiger | 0:7c97dcef700c | 1270 | TinyXml will happily read or write files without a declaration, |
| steiger | 0:7c97dcef700c | 1271 | however. There are 3 possible attributes to the declaration: |
| steiger | 0:7c97dcef700c | 1272 | version, encoding, and standalone. |
| steiger | 0:7c97dcef700c | 1273 | |
| steiger | 0:7c97dcef700c | 1274 | Note: In this version of the code, the attributes are |
| steiger | 0:7c97dcef700c | 1275 | handled as special cases, not generic attributes, simply |
| steiger | 0:7c97dcef700c | 1276 | because there can only be at most 3 and they are always the same. |
| steiger | 0:7c97dcef700c | 1277 | */ |
| steiger | 0:7c97dcef700c | 1278 | class TiXmlDeclaration : public TiXmlNode |
| steiger | 0:7c97dcef700c | 1279 | { |
| steiger | 0:7c97dcef700c | 1280 | public: |
| steiger | 0:7c97dcef700c | 1281 | /// Construct an empty declaration. |
| steiger | 0:7c97dcef700c | 1282 | TiXmlDeclaration() : TiXmlNode( TiXmlNode::TINYXML_DECLARATION ) {} |
| steiger | 0:7c97dcef700c | 1283 | |
| steiger | 0:7c97dcef700c | 1284 | #ifdef TIXML_USE_STL |
| steiger | 0:7c97dcef700c | 1285 | /// Constructor. |
| steiger | 0:7c97dcef700c | 1286 | TiXmlDeclaration( const std::string& _version, |
| steiger | 0:7c97dcef700c | 1287 | const std::string& _encoding, |
| steiger | 0:7c97dcef700c | 1288 | const std::string& _standalone ); |
| steiger | 0:7c97dcef700c | 1289 | #endif |
| steiger | 0:7c97dcef700c | 1290 | |
| steiger | 0:7c97dcef700c | 1291 | /// Construct. |
| steiger | 0:7c97dcef700c | 1292 | TiXmlDeclaration( const char* _version, |
| steiger | 0:7c97dcef700c | 1293 | const char* _encoding, |
| steiger | 0:7c97dcef700c | 1294 | const char* _standalone ); |
| steiger | 0:7c97dcef700c | 1295 | |
| steiger | 0:7c97dcef700c | 1296 | TiXmlDeclaration( const TiXmlDeclaration& copy ); |
| steiger | 0:7c97dcef700c | 1297 | void operator=( const TiXmlDeclaration& copy ); |
| steiger | 0:7c97dcef700c | 1298 | |
| steiger | 0:7c97dcef700c | 1299 | virtual ~TiXmlDeclaration() {} |
| steiger | 0:7c97dcef700c | 1300 | |
| steiger | 0:7c97dcef700c | 1301 | /// Version. Will return an empty string if none was found. |
| steiger | 0:7c97dcef700c | 1302 | const char *Version() const { return version.c_str (); } |
| steiger | 0:7c97dcef700c | 1303 | /// Encoding. Will return an empty string if none was found. |
| steiger | 0:7c97dcef700c | 1304 | const char *Encoding() const { return encoding.c_str (); } |
| steiger | 0:7c97dcef700c | 1305 | /// Is this a standalone document? |
| steiger | 0:7c97dcef700c | 1306 | const char *Standalone() const { return standalone.c_str (); } |
| steiger | 0:7c97dcef700c | 1307 | |
| steiger | 0:7c97dcef700c | 1308 | /// Creates a copy of this Declaration and returns it. |
| steiger | 0:7c97dcef700c | 1309 | virtual TiXmlNode* Clone() const; |
| steiger | 0:7c97dcef700c | 1310 | // Print this declaration to a FILE stream. |
| steiger | 0:7c97dcef700c | 1311 | virtual void Print( FILE* cfile, int depth, TIXML_STRING* str ) const; |
| steiger | 0:7c97dcef700c | 1312 | virtual void Print( FILE* cfile, int depth ) const { |
| steiger | 0:7c97dcef700c | 1313 | Print( cfile, depth, 0 ); |
| steiger | 0:7c97dcef700c | 1314 | } |
| steiger | 0:7c97dcef700c | 1315 | |
| steiger | 0:7c97dcef700c | 1316 | virtual const char* Parse( const char* p, TiXmlParsingData* data, TiXmlEncoding encoding ); |
| steiger | 0:7c97dcef700c | 1317 | |
| steiger | 0:7c97dcef700c | 1318 | virtual const TiXmlDeclaration* ToDeclaration() const { return this; } ///< Cast to a more defined type. Will return null not of the requested type. |
| steiger | 0:7c97dcef700c | 1319 | virtual TiXmlDeclaration* ToDeclaration() { return this; } ///< Cast to a more defined type. Will return null not of the requested type. |
| steiger | 0:7c97dcef700c | 1320 | |
| steiger | 0:7c97dcef700c | 1321 | /** Walk the XML tree visiting this node and all of its children. |
| steiger | 0:7c97dcef700c | 1322 | */ |
| steiger | 0:7c97dcef700c | 1323 | virtual bool Accept( TiXmlVisitor* visitor ) const; |
| steiger | 0:7c97dcef700c | 1324 | |
| steiger | 0:7c97dcef700c | 1325 | protected: |
| steiger | 0:7c97dcef700c | 1326 | void CopyTo( TiXmlDeclaration* target ) const; |
| steiger | 0:7c97dcef700c | 1327 | // used to be public |
| steiger | 0:7c97dcef700c | 1328 | #ifdef TIXML_USE_STL |
| steiger | 0:7c97dcef700c | 1329 | virtual void StreamIn( std::istream * in, TIXML_STRING * tag ); |
| steiger | 0:7c97dcef700c | 1330 | #endif |
| steiger | 0:7c97dcef700c | 1331 | |
| steiger | 0:7c97dcef700c | 1332 | private: |
| steiger | 0:7c97dcef700c | 1333 | |
| steiger | 0:7c97dcef700c | 1334 | TIXML_STRING version; |
| steiger | 0:7c97dcef700c | 1335 | TIXML_STRING encoding; |
| steiger | 0:7c97dcef700c | 1336 | TIXML_STRING standalone; |
| steiger | 0:7c97dcef700c | 1337 | }; |
| steiger | 0:7c97dcef700c | 1338 | |
| steiger | 0:7c97dcef700c | 1339 | |
| steiger | 0:7c97dcef700c | 1340 | /** Any tag that tinyXml doesn't recognize is saved as an |
| steiger | 0:7c97dcef700c | 1341 | unknown. It is a tag of text, but should not be modified. |
| steiger | 0:7c97dcef700c | 1342 | It will be written back to the XML, unchanged, when the file |
| steiger | 0:7c97dcef700c | 1343 | is saved. |
| steiger | 0:7c97dcef700c | 1344 | |
| steiger | 0:7c97dcef700c | 1345 | DTD tags get thrown into TiXmlUnknowns. |
| steiger | 0:7c97dcef700c | 1346 | */ |
| steiger | 0:7c97dcef700c | 1347 | class TiXmlUnknown : public TiXmlNode |
| steiger | 0:7c97dcef700c | 1348 | { |
| steiger | 0:7c97dcef700c | 1349 | public: |
| steiger | 0:7c97dcef700c | 1350 | TiXmlUnknown() : TiXmlNode( TiXmlNode::TINYXML_UNKNOWN ) {} |
| steiger | 0:7c97dcef700c | 1351 | virtual ~TiXmlUnknown() {} |
| steiger | 0:7c97dcef700c | 1352 | |
| steiger | 0:7c97dcef700c | 1353 | TiXmlUnknown( const TiXmlUnknown& copy ) : TiXmlNode( TiXmlNode::TINYXML_UNKNOWN ) { copy.CopyTo( this ); } |
| steiger | 0:7c97dcef700c | 1354 | void operator=( const TiXmlUnknown& copy ) { copy.CopyTo( this ); } |
| steiger | 0:7c97dcef700c | 1355 | |
| steiger | 0:7c97dcef700c | 1356 | /// Creates a copy of this Unknown and returns it. |
| steiger | 0:7c97dcef700c | 1357 | virtual TiXmlNode* Clone() const; |
| steiger | 0:7c97dcef700c | 1358 | // Print this Unknown to a FILE stream. |
| steiger | 0:7c97dcef700c | 1359 | virtual void Print( FILE* cfile, int depth ) const; |
| steiger | 0:7c97dcef700c | 1360 | |
| steiger | 0:7c97dcef700c | 1361 | virtual const char* Parse( const char* p, TiXmlParsingData* data, TiXmlEncoding encoding ); |
| steiger | 0:7c97dcef700c | 1362 | |
| steiger | 0:7c97dcef700c | 1363 | virtual const TiXmlUnknown* ToUnknown() const { return this; } ///< Cast to a more defined type. Will return null not of the requested type. |
| steiger | 0:7c97dcef700c | 1364 | virtual TiXmlUnknown* ToUnknown() { return this; } ///< Cast to a more defined type. Will return null not of the requested type. |
| steiger | 0:7c97dcef700c | 1365 | |
| steiger | 0:7c97dcef700c | 1366 | /** Walk the XML tree visiting this node and all of its children. |
| steiger | 0:7c97dcef700c | 1367 | */ |
| steiger | 0:7c97dcef700c | 1368 | virtual bool Accept( TiXmlVisitor* content ) const; |
| steiger | 0:7c97dcef700c | 1369 | |
| steiger | 0:7c97dcef700c | 1370 | protected: |
| steiger | 0:7c97dcef700c | 1371 | void CopyTo( TiXmlUnknown* target ) const; |
| steiger | 0:7c97dcef700c | 1372 | |
| steiger | 0:7c97dcef700c | 1373 | #ifdef TIXML_USE_STL |
| steiger | 0:7c97dcef700c | 1374 | virtual void StreamIn( std::istream * in, TIXML_STRING * tag ); |
| steiger | 0:7c97dcef700c | 1375 | #endif |
| steiger | 0:7c97dcef700c | 1376 | |
| steiger | 0:7c97dcef700c | 1377 | private: |
| steiger | 0:7c97dcef700c | 1378 | |
| steiger | 0:7c97dcef700c | 1379 | }; |
| steiger | 0:7c97dcef700c | 1380 | |
| steiger | 0:7c97dcef700c | 1381 | |
| steiger | 0:7c97dcef700c | 1382 | /** Always the top level node. A document binds together all the |
| steiger | 0:7c97dcef700c | 1383 | XML pieces. It can be saved, loaded, and printed to the screen. |
| steiger | 0:7c97dcef700c | 1384 | The 'value' of a document node is the xml file name. |
| steiger | 0:7c97dcef700c | 1385 | */ |
| steiger | 0:7c97dcef700c | 1386 | class TiXmlDocument : public TiXmlNode |
| steiger | 0:7c97dcef700c | 1387 | { |
| steiger | 0:7c97dcef700c | 1388 | public: |
| steiger | 0:7c97dcef700c | 1389 | /// Create an empty document, that has no name. |
| steiger | 0:7c97dcef700c | 1390 | TiXmlDocument(); |
| steiger | 0:7c97dcef700c | 1391 | /// Create a document with a name. The name of the document is also the filename of the xml. |
| steiger | 0:7c97dcef700c | 1392 | TiXmlDocument( const char * documentName ); |
| steiger | 0:7c97dcef700c | 1393 | |
| steiger | 0:7c97dcef700c | 1394 | #ifdef TIXML_USE_STL |
| steiger | 0:7c97dcef700c | 1395 | /// Constructor. |
| steiger | 0:7c97dcef700c | 1396 | TiXmlDocument( const std::string& documentName ); |
| steiger | 0:7c97dcef700c | 1397 | #endif |
| steiger | 0:7c97dcef700c | 1398 | |
| steiger | 0:7c97dcef700c | 1399 | TiXmlDocument( const TiXmlDocument& copy ); |
| steiger | 0:7c97dcef700c | 1400 | void operator=( const TiXmlDocument& copy ); |
| steiger | 0:7c97dcef700c | 1401 | |
| steiger | 0:7c97dcef700c | 1402 | virtual ~TiXmlDocument() {} |
| steiger | 0:7c97dcef700c | 1403 | |
| steiger | 0:7c97dcef700c | 1404 | /** Load a file using the current document value. |
| steiger | 0:7c97dcef700c | 1405 | Returns true if successful. Will delete any existing |
| steiger | 0:7c97dcef700c | 1406 | document data before loading. |
| steiger | 0:7c97dcef700c | 1407 | */ |
| steiger | 0:7c97dcef700c | 1408 | bool LoadFile( TiXmlEncoding encoding = TIXML_DEFAULT_ENCODING ); |
| steiger | 0:7c97dcef700c | 1409 | /// Save a file using the current document value. Returns true if successful. |
| steiger | 0:7c97dcef700c | 1410 | bool SaveFile() const; |
| steiger | 0:7c97dcef700c | 1411 | /// Load a file using the given filename. Returns true if successful. |
| steiger | 0:7c97dcef700c | 1412 | bool LoadFile( const char * filename, TiXmlEncoding encoding = TIXML_DEFAULT_ENCODING ); |
| steiger | 0:7c97dcef700c | 1413 | /// Save a file using the given filename. Returns true if successful. |
| steiger | 0:7c97dcef700c | 1414 | bool SaveFile( const char * filename ) const; |
| steiger | 0:7c97dcef700c | 1415 | /** Load a file using the given FILE*. Returns true if successful. Note that this method |
| steiger | 0:7c97dcef700c | 1416 | doesn't stream - the entire object pointed at by the FILE* |
| steiger | 0:7c97dcef700c | 1417 | will be interpreted as an XML file. TinyXML doesn't stream in XML from the current |
| steiger | 0:7c97dcef700c | 1418 | file location. Streaming may be added in the future. |
| steiger | 0:7c97dcef700c | 1419 | */ |
| steiger | 0:7c97dcef700c | 1420 | bool LoadFile( FILE*, TiXmlEncoding encoding = TIXML_DEFAULT_ENCODING ); |
| steiger | 0:7c97dcef700c | 1421 | /// Save a file using the given FILE*. Returns true if successful. |
| steiger | 0:7c97dcef700c | 1422 | bool SaveFile( FILE* ) const; |
| steiger | 0:7c97dcef700c | 1423 | |
| steiger | 0:7c97dcef700c | 1424 | #ifdef TIXML_USE_STL |
| steiger | 0:7c97dcef700c | 1425 | bool LoadFile( const std::string& filename, TiXmlEncoding encoding = TIXML_DEFAULT_ENCODING ) ///< STL std::string version. |
| steiger | 0:7c97dcef700c | 1426 | { |
| steiger | 0:7c97dcef700c | 1427 | return LoadFile( filename.c_str(), encoding ); |
| steiger | 0:7c97dcef700c | 1428 | } |
| steiger | 0:7c97dcef700c | 1429 | bool SaveFile( const std::string& filename ) const ///< STL std::string version. |
| steiger | 0:7c97dcef700c | 1430 | { |
| steiger | 0:7c97dcef700c | 1431 | return SaveFile( filename.c_str() ); |
| steiger | 0:7c97dcef700c | 1432 | } |
| steiger | 0:7c97dcef700c | 1433 | #endif |
| steiger | 0:7c97dcef700c | 1434 | |
| steiger | 0:7c97dcef700c | 1435 | /** Parse the given null terminated block of xml data. Passing in an encoding to this |
| steiger | 0:7c97dcef700c | 1436 | method (either TIXML_ENCODING_LEGACY or TIXML_ENCODING_UTF8 will force TinyXml |
| steiger | 0:7c97dcef700c | 1437 | to use that encoding, regardless of what TinyXml might otherwise try to detect. |
| steiger | 0:7c97dcef700c | 1438 | */ |
| steiger | 0:7c97dcef700c | 1439 | virtual const char* Parse( const char* p, TiXmlParsingData* data = 0, TiXmlEncoding encoding = TIXML_DEFAULT_ENCODING ); |
| steiger | 0:7c97dcef700c | 1440 | |
| steiger | 0:7c97dcef700c | 1441 | /** Get the root element -- the only top level element -- of the document. |
| steiger | 0:7c97dcef700c | 1442 | In well formed XML, there should only be one. TinyXml is tolerant of |
| steiger | 0:7c97dcef700c | 1443 | multiple elements at the document level. |
| steiger | 0:7c97dcef700c | 1444 | */ |
| steiger | 0:7c97dcef700c | 1445 | const TiXmlElement* RootElement() const { return FirstChildElement(); } |
| steiger | 0:7c97dcef700c | 1446 | TiXmlElement* RootElement() { return FirstChildElement(); } |
| steiger | 0:7c97dcef700c | 1447 | |
| steiger | 0:7c97dcef700c | 1448 | /** If an error occurs, Error will be set to true. Also, |
| steiger | 0:7c97dcef700c | 1449 | - The ErrorId() will contain the integer identifier of the error (not generally useful) |
| steiger | 0:7c97dcef700c | 1450 | - The ErrorDesc() method will return the name of the error. (very useful) |
| steiger | 0:7c97dcef700c | 1451 | - The ErrorRow() and ErrorCol() will return the location of the error (if known) |
| steiger | 0:7c97dcef700c | 1452 | */ |
| steiger | 0:7c97dcef700c | 1453 | bool Error() const { return error; } |
| steiger | 0:7c97dcef700c | 1454 | |
| steiger | 0:7c97dcef700c | 1455 | /// Contains a textual (english) description of the error if one occurs. |
| steiger | 0:7c97dcef700c | 1456 | const char * ErrorDesc() const { return errorDesc.c_str (); } |
| steiger | 0:7c97dcef700c | 1457 | |
| steiger | 0:7c97dcef700c | 1458 | /** Generally, you probably want the error string ( ErrorDesc() ). But if you |
| steiger | 0:7c97dcef700c | 1459 | prefer the ErrorId, this function will fetch it. |
| steiger | 0:7c97dcef700c | 1460 | */ |
| steiger | 0:7c97dcef700c | 1461 | int ErrorId() const { return errorId; } |
| steiger | 0:7c97dcef700c | 1462 | |
| steiger | 0:7c97dcef700c | 1463 | /** Returns the location (if known) of the error. The first column is column 1, |
| steiger | 0:7c97dcef700c | 1464 | and the first row is row 1. A value of 0 means the row and column wasn't applicable |
| steiger | 0:7c97dcef700c | 1465 | (memory errors, for example, have no row/column) or the parser lost the error. (An |
| steiger | 0:7c97dcef700c | 1466 | error in the error reporting, in that case.) |
| steiger | 0:7c97dcef700c | 1467 | |
| steiger | 0:7c97dcef700c | 1468 | @sa SetTabSize, Row, Column |
| steiger | 0:7c97dcef700c | 1469 | */ |
| steiger | 0:7c97dcef700c | 1470 | int ErrorRow() const { return errorLocation.row+1; } |
| steiger | 0:7c97dcef700c | 1471 | int ErrorCol() const { return errorLocation.col+1; } ///< The column where the error occured. See ErrorRow() |
| steiger | 0:7c97dcef700c | 1472 | |
| steiger | 0:7c97dcef700c | 1473 | /** SetTabSize() allows the error reporting functions (ErrorRow() and ErrorCol()) |
| steiger | 0:7c97dcef700c | 1474 | to report the correct values for row and column. It does not change the output |
| steiger | 0:7c97dcef700c | 1475 | or input in any way. |
| steiger | 0:7c97dcef700c | 1476 | |
| steiger | 0:7c97dcef700c | 1477 | By calling this method, with a tab size |
| steiger | 0:7c97dcef700c | 1478 | greater than 0, the row and column of each node and attribute is stored |
| steiger | 0:7c97dcef700c | 1479 | when the file is loaded. Very useful for tracking the DOM back in to |
| steiger | 0:7c97dcef700c | 1480 | the source file. |
| steiger | 0:7c97dcef700c | 1481 | |
| steiger | 0:7c97dcef700c | 1482 | The tab size is required for calculating the location of nodes. If not |
| steiger | 0:7c97dcef700c | 1483 | set, the default of 4 is used. The tabsize is set per document. Setting |
| steiger | 0:7c97dcef700c | 1484 | the tabsize to 0 disables row/column tracking. |
| steiger | 0:7c97dcef700c | 1485 | |
| steiger | 0:7c97dcef700c | 1486 | Note that row and column tracking is not supported when using operator>>. |
| steiger | 0:7c97dcef700c | 1487 | |
| steiger | 0:7c97dcef700c | 1488 | The tab size needs to be enabled before the parse or load. Correct usage: |
| steiger | 0:7c97dcef700c | 1489 | @verbatim |
| steiger | 0:7c97dcef700c | 1490 | TiXmlDocument doc; |
| steiger | 0:7c97dcef700c | 1491 | doc.SetTabSize( 8 ); |
| steiger | 0:7c97dcef700c | 1492 | doc.Load( "myfile.xml" ); |
| steiger | 0:7c97dcef700c | 1493 | @endverbatim |
| steiger | 0:7c97dcef700c | 1494 | |
| steiger | 0:7c97dcef700c | 1495 | @sa Row, Column |
| steiger | 0:7c97dcef700c | 1496 | */ |
| steiger | 0:7c97dcef700c | 1497 | void SetTabSize( int _tabsize ) { tabsize = _tabsize; } |
| steiger | 0:7c97dcef700c | 1498 | |
| steiger | 0:7c97dcef700c | 1499 | int TabSize() const { return tabsize; } |
| steiger | 0:7c97dcef700c | 1500 | |
| steiger | 0:7c97dcef700c | 1501 | /** If you have handled the error, it can be reset with this call. The error |
| steiger | 0:7c97dcef700c | 1502 | state is automatically cleared if you Parse a new XML block. |
| steiger | 0:7c97dcef700c | 1503 | */ |
| steiger | 0:7c97dcef700c | 1504 | void ClearError() { error = false; |
| steiger | 0:7c97dcef700c | 1505 | errorId = 0; |
| steiger | 0:7c97dcef700c | 1506 | errorDesc = ""; |
| steiger | 0:7c97dcef700c | 1507 | errorLocation.row = errorLocation.col = 0; |
| steiger | 0:7c97dcef700c | 1508 | //errorLocation.last = 0; |
| steiger | 0:7c97dcef700c | 1509 | } |
| steiger | 0:7c97dcef700c | 1510 | |
| steiger | 0:7c97dcef700c | 1511 | /** Write the document to standard out using formatted printing ("pretty print"). */ |
| steiger | 0:7c97dcef700c | 1512 | void Print() const { Print( stdout, 0 ); } |
| steiger | 0:7c97dcef700c | 1513 | |
| steiger | 0:7c97dcef700c | 1514 | /* Write the document to a string using formatted printing ("pretty print"). This |
| steiger | 0:7c97dcef700c | 1515 | will allocate a character array (new char[]) and return it as a pointer. The |
| steiger | 0:7c97dcef700c | 1516 | calling code pust call delete[] on the return char* to avoid a memory leak. |
| steiger | 0:7c97dcef700c | 1517 | */ |
| steiger | 0:7c97dcef700c | 1518 | //char* PrintToMemory() const; |
| steiger | 0:7c97dcef700c | 1519 | |
| steiger | 0:7c97dcef700c | 1520 | /// Print this Document to a FILE stream. |
| steiger | 0:7c97dcef700c | 1521 | virtual void Print( FILE* cfile, int depth = 0 ) const; |
| steiger | 0:7c97dcef700c | 1522 | // [internal use] |
| steiger | 0:7c97dcef700c | 1523 | void SetError( int err, const char* errorLocation, TiXmlParsingData* prevData, TiXmlEncoding encoding ); |
| steiger | 0:7c97dcef700c | 1524 | |
| steiger | 0:7c97dcef700c | 1525 | virtual const TiXmlDocument* ToDocument() const { return this; } ///< Cast to a more defined type. Will return null not of the requested type. |
| steiger | 0:7c97dcef700c | 1526 | virtual TiXmlDocument* ToDocument() { return this; } ///< Cast to a more defined type. Will return null not of the requested type. |
| steiger | 0:7c97dcef700c | 1527 | |
| steiger | 0:7c97dcef700c | 1528 | /** Walk the XML tree visiting this node and all of its children. |
| steiger | 0:7c97dcef700c | 1529 | */ |
| steiger | 0:7c97dcef700c | 1530 | virtual bool Accept( TiXmlVisitor* content ) const; |
| steiger | 0:7c97dcef700c | 1531 | |
| steiger | 0:7c97dcef700c | 1532 | protected : |
| steiger | 0:7c97dcef700c | 1533 | // [internal use] |
| steiger | 0:7c97dcef700c | 1534 | virtual TiXmlNode* Clone() const; |
| steiger | 0:7c97dcef700c | 1535 | #ifdef TIXML_USE_STL |
| steiger | 0:7c97dcef700c | 1536 | virtual void StreamIn( std::istream * in, TIXML_STRING * tag ); |
| steiger | 0:7c97dcef700c | 1537 | #endif |
| steiger | 0:7c97dcef700c | 1538 | |
| steiger | 0:7c97dcef700c | 1539 | private: |
| steiger | 0:7c97dcef700c | 1540 | void CopyTo( TiXmlDocument* target ) const; |
| steiger | 0:7c97dcef700c | 1541 | |
| steiger | 0:7c97dcef700c | 1542 | bool error; |
| steiger | 0:7c97dcef700c | 1543 | int errorId; |
| steiger | 0:7c97dcef700c | 1544 | TIXML_STRING errorDesc; |
| steiger | 0:7c97dcef700c | 1545 | int tabsize; |
| steiger | 0:7c97dcef700c | 1546 | TiXmlCursor errorLocation; |
| steiger | 0:7c97dcef700c | 1547 | bool useMicrosoftBOM; // the UTF-8 BOM were found when read. Note this, and try to write. |
| steiger | 0:7c97dcef700c | 1548 | }; |
| steiger | 0:7c97dcef700c | 1549 | |
| steiger | 0:7c97dcef700c | 1550 | |
| steiger | 0:7c97dcef700c | 1551 | /** |
| steiger | 0:7c97dcef700c | 1552 | A TiXmlHandle is a class that wraps a node pointer with null checks; this is |
| steiger | 0:7c97dcef700c | 1553 | an incredibly useful thing. Note that TiXmlHandle is not part of the TinyXml |
| steiger | 0:7c97dcef700c | 1554 | DOM structure. It is a separate utility class. |
| steiger | 0:7c97dcef700c | 1555 | |
| steiger | 0:7c97dcef700c | 1556 | Take an example: |
| steiger | 0:7c97dcef700c | 1557 | @verbatim |
| steiger | 0:7c97dcef700c | 1558 | <Document> |
| steiger | 0:7c97dcef700c | 1559 | <Element attributeA = "valueA"> |
| steiger | 0:7c97dcef700c | 1560 | <Child attributeB = "value1" /> |
| steiger | 0:7c97dcef700c | 1561 | <Child attributeB = "value2" /> |
| steiger | 0:7c97dcef700c | 1562 | </Element> |
| steiger | 0:7c97dcef700c | 1563 | <Document> |
| steiger | 0:7c97dcef700c | 1564 | @endverbatim |
| steiger | 0:7c97dcef700c | 1565 | |
| steiger | 0:7c97dcef700c | 1566 | Assuming you want the value of "attributeB" in the 2nd "Child" element, it's very |
| steiger | 0:7c97dcef700c | 1567 | easy to write a *lot* of code that looks like: |
| steiger | 0:7c97dcef700c | 1568 | |
| steiger | 0:7c97dcef700c | 1569 | @verbatim |
| steiger | 0:7c97dcef700c | 1570 | TiXmlElement* root = document.FirstChildElement( "Document" ); |
| steiger | 0:7c97dcef700c | 1571 | if ( root ) |
| steiger | 0:7c97dcef700c | 1572 | { |
| steiger | 0:7c97dcef700c | 1573 | TiXmlElement* element = root->FirstChildElement( "Element" ); |
| steiger | 0:7c97dcef700c | 1574 | if ( element ) |
| steiger | 0:7c97dcef700c | 1575 | { |
| steiger | 0:7c97dcef700c | 1576 | TiXmlElement* child = element->FirstChildElement( "Child" ); |
| steiger | 0:7c97dcef700c | 1577 | if ( child ) |
| steiger | 0:7c97dcef700c | 1578 | { |
| steiger | 0:7c97dcef700c | 1579 | TiXmlElement* child2 = child->NextSiblingElement( "Child" ); |
| steiger | 0:7c97dcef700c | 1580 | if ( child2 ) |
| steiger | 0:7c97dcef700c | 1581 | { |
| steiger | 0:7c97dcef700c | 1582 | // Finally do something useful. |
| steiger | 0:7c97dcef700c | 1583 | @endverbatim |
| steiger | 0:7c97dcef700c | 1584 | |
| steiger | 0:7c97dcef700c | 1585 | And that doesn't even cover "else" cases. TiXmlHandle addresses the verbosity |
| steiger | 0:7c97dcef700c | 1586 | of such code. A TiXmlHandle checks for null pointers so it is perfectly safe |
| steiger | 0:7c97dcef700c | 1587 | and correct to use: |
| steiger | 0:7c97dcef700c | 1588 | |
| steiger | 0:7c97dcef700c | 1589 | @verbatim |
| steiger | 0:7c97dcef700c | 1590 | TiXmlHandle docHandle( &document ); |
| steiger | 0:7c97dcef700c | 1591 | TiXmlElement* child2 = docHandle.FirstChild( "Document" ).FirstChild( "Element" ).Child( "Child", 1 ).ToElement(); |
| steiger | 0:7c97dcef700c | 1592 | if ( child2 ) |
| steiger | 0:7c97dcef700c | 1593 | { |
| steiger | 0:7c97dcef700c | 1594 | // do something useful |
| steiger | 0:7c97dcef700c | 1595 | @endverbatim |
| steiger | 0:7c97dcef700c | 1596 | |
| steiger | 0:7c97dcef700c | 1597 | Which is MUCH more concise and useful. |
| steiger | 0:7c97dcef700c | 1598 | |
| steiger | 0:7c97dcef700c | 1599 | It is also safe to copy handles - internally they are nothing more than node pointers. |
| steiger | 0:7c97dcef700c | 1600 | @verbatim |
| steiger | 0:7c97dcef700c | 1601 | TiXmlHandle handleCopy = handle; |
| steiger | 0:7c97dcef700c | 1602 | @endverbatim |
| steiger | 0:7c97dcef700c | 1603 | |
| steiger | 0:7c97dcef700c | 1604 | What they should not be used for is iteration: |
| steiger | 0:7c97dcef700c | 1605 | |
| steiger | 0:7c97dcef700c | 1606 | @verbatim |
| steiger | 0:7c97dcef700c | 1607 | int i=0; |
| steiger | 0:7c97dcef700c | 1608 | while ( true ) |
| steiger | 0:7c97dcef700c | 1609 | { |
| steiger | 0:7c97dcef700c | 1610 | TiXmlElement* child = docHandle.FirstChild( "Document" ).FirstChild( "Element" ).Child( "Child", i ).ToElement(); |
| steiger | 0:7c97dcef700c | 1611 | if ( !child ) |
| steiger | 0:7c97dcef700c | 1612 | break; |
| steiger | 0:7c97dcef700c | 1613 | // do something |
| steiger | 0:7c97dcef700c | 1614 | ++i; |
| steiger | 0:7c97dcef700c | 1615 | } |
| steiger | 0:7c97dcef700c | 1616 | @endverbatim |
| steiger | 0:7c97dcef700c | 1617 | |
| steiger | 0:7c97dcef700c | 1618 | It seems reasonable, but it is in fact two embedded while loops. The Child method is |
| steiger | 0:7c97dcef700c | 1619 | a linear walk to find the element, so this code would iterate much more than it needs |
| steiger | 0:7c97dcef700c | 1620 | to. Instead, prefer: |
| steiger | 0:7c97dcef700c | 1621 | |
| steiger | 0:7c97dcef700c | 1622 | @verbatim |
| steiger | 0:7c97dcef700c | 1623 | TiXmlElement* child = docHandle.FirstChild( "Document" ).FirstChild( "Element" ).FirstChild( "Child" ).ToElement(); |
| steiger | 0:7c97dcef700c | 1624 | |
| steiger | 0:7c97dcef700c | 1625 | for( child; child; child=child->NextSiblingElement() ) |
| steiger | 0:7c97dcef700c | 1626 | { |
| steiger | 0:7c97dcef700c | 1627 | // do something |
| steiger | 0:7c97dcef700c | 1628 | } |
| steiger | 0:7c97dcef700c | 1629 | @endverbatim |
| steiger | 0:7c97dcef700c | 1630 | */ |
| steiger | 0:7c97dcef700c | 1631 | class TiXmlHandle |
| steiger | 0:7c97dcef700c | 1632 | { |
| steiger | 0:7c97dcef700c | 1633 | public: |
| steiger | 0:7c97dcef700c | 1634 | /// Create a handle from any node (at any depth of the tree.) This can be a null pointer. |
| steiger | 0:7c97dcef700c | 1635 | TiXmlHandle( TiXmlNode* _node ) { this->node = _node; } |
| steiger | 0:7c97dcef700c | 1636 | /// Copy constructor |
| steiger | 0:7c97dcef700c | 1637 | TiXmlHandle( const TiXmlHandle& ref ) { this->node = ref.node; } |
| steiger | 0:7c97dcef700c | 1638 | TiXmlHandle operator=( const TiXmlHandle& ref ) { this->node = ref.node; return *this; } |
| steiger | 0:7c97dcef700c | 1639 | |
| steiger | 0:7c97dcef700c | 1640 | /// Return a handle to the first child node. |
| steiger | 0:7c97dcef700c | 1641 | TiXmlHandle FirstChild() const; |
| steiger | 0:7c97dcef700c | 1642 | /// Return a handle to the first child node with the given name. |
| steiger | 0:7c97dcef700c | 1643 | TiXmlHandle FirstChild( const char * value ) const; |
| steiger | 0:7c97dcef700c | 1644 | /// Return a handle to the first child element. |
| steiger | 0:7c97dcef700c | 1645 | TiXmlHandle FirstChildElement() const; |
| steiger | 0:7c97dcef700c | 1646 | /// Return a handle to the first child element with the given name. |
| steiger | 0:7c97dcef700c | 1647 | TiXmlHandle FirstChildElement( const char * value ) const; |
| steiger | 0:7c97dcef700c | 1648 | |
| steiger | 0:7c97dcef700c | 1649 | /** Return a handle to the "index" child with the given name. |
| steiger | 0:7c97dcef700c | 1650 | The first child is 0, the second 1, etc. |
| steiger | 0:7c97dcef700c | 1651 | */ |
| steiger | 0:7c97dcef700c | 1652 | TiXmlHandle Child( const char* value, int index ) const; |
| steiger | 0:7c97dcef700c | 1653 | /** Return a handle to the "index" child. |
| steiger | 0:7c97dcef700c | 1654 | The first child is 0, the second 1, etc. |
| steiger | 0:7c97dcef700c | 1655 | */ |
| steiger | 0:7c97dcef700c | 1656 | TiXmlHandle Child( int index ) const; |
| steiger | 0:7c97dcef700c | 1657 | /** Return a handle to the "index" child element with the given name. |
| steiger | 0:7c97dcef700c | 1658 | The first child element is 0, the second 1, etc. Note that only TiXmlElements |
| steiger | 0:7c97dcef700c | 1659 | are indexed: other types are not counted. |
| steiger | 0:7c97dcef700c | 1660 | */ |
| steiger | 0:7c97dcef700c | 1661 | TiXmlHandle ChildElement( const char* value, int index ) const; |
| steiger | 0:7c97dcef700c | 1662 | /** Return a handle to the "index" child element. |
| steiger | 0:7c97dcef700c | 1663 | The first child element is 0, the second 1, etc. Note that only TiXmlElements |
| steiger | 0:7c97dcef700c | 1664 | are indexed: other types are not counted. |
| steiger | 0:7c97dcef700c | 1665 | */ |
| steiger | 0:7c97dcef700c | 1666 | TiXmlHandle ChildElement( int index ) const; |
| steiger | 0:7c97dcef700c | 1667 | |
| steiger | 0:7c97dcef700c | 1668 | #ifdef TIXML_USE_STL |
| steiger | 0:7c97dcef700c | 1669 | TiXmlHandle FirstChild( const std::string& _value ) const { return FirstChild( _value.c_str() ); } |
| steiger | 0:7c97dcef700c | 1670 | TiXmlHandle FirstChildElement( const std::string& _value ) const { return FirstChildElement( _value.c_str() ); } |
| steiger | 0:7c97dcef700c | 1671 | |
| steiger | 0:7c97dcef700c | 1672 | TiXmlHandle Child( const std::string& _value, int index ) const { return Child( _value.c_str(), index ); } |
| steiger | 0:7c97dcef700c | 1673 | TiXmlHandle ChildElement( const std::string& _value, int index ) const { return ChildElement( _value.c_str(), index ); } |
| steiger | 0:7c97dcef700c | 1674 | #endif |
| steiger | 0:7c97dcef700c | 1675 | |
| steiger | 0:7c97dcef700c | 1676 | /** Return the handle as a TiXmlNode. This may return null. |
| steiger | 0:7c97dcef700c | 1677 | */ |
| steiger | 0:7c97dcef700c | 1678 | TiXmlNode* ToNode() const { return node; } |
| steiger | 0:7c97dcef700c | 1679 | /** Return the handle as a TiXmlElement. This may return null. |
| steiger | 0:7c97dcef700c | 1680 | */ |
| steiger | 0:7c97dcef700c | 1681 | TiXmlElement* ToElement() const { return ( ( node && node->ToElement() ) ? node->ToElement() : 0 ); } |
| steiger | 0:7c97dcef700c | 1682 | /** Return the handle as a TiXmlText. This may return null. |
| steiger | 0:7c97dcef700c | 1683 | */ |
| steiger | 0:7c97dcef700c | 1684 | TiXmlText* ToText() const { return ( ( node && node->ToText() ) ? node->ToText() : 0 ); } |
| steiger | 0:7c97dcef700c | 1685 | /** Return the handle as a TiXmlUnknown. This may return null. |
| steiger | 0:7c97dcef700c | 1686 | */ |
| steiger | 0:7c97dcef700c | 1687 | TiXmlUnknown* ToUnknown() const { return ( ( node && node->ToUnknown() ) ? node->ToUnknown() : 0 ); } |
| steiger | 0:7c97dcef700c | 1688 | |
| steiger | 0:7c97dcef700c | 1689 | /** @deprecated use ToNode. |
| steiger | 0:7c97dcef700c | 1690 | Return the handle as a TiXmlNode. This may return null. |
| steiger | 0:7c97dcef700c | 1691 | */ |
| steiger | 0:7c97dcef700c | 1692 | TiXmlNode* Node() const { return ToNode(); } |
| steiger | 0:7c97dcef700c | 1693 | /** @deprecated use ToElement. |
| steiger | 0:7c97dcef700c | 1694 | Return the handle as a TiXmlElement. This may return null. |
| steiger | 0:7c97dcef700c | 1695 | */ |
| steiger | 0:7c97dcef700c | 1696 | TiXmlElement* Element() const { return ToElement(); } |
| steiger | 0:7c97dcef700c | 1697 | /** @deprecated use ToText() |
| steiger | 0:7c97dcef700c | 1698 | Return the handle as a TiXmlText. This may return null. |
| steiger | 0:7c97dcef700c | 1699 | */ |
| steiger | 0:7c97dcef700c | 1700 | TiXmlText* Text() const { return ToText(); } |
| steiger | 0:7c97dcef700c | 1701 | /** @deprecated use ToUnknown() |
| steiger | 0:7c97dcef700c | 1702 | Return the handle as a TiXmlUnknown. This may return null. |
| steiger | 0:7c97dcef700c | 1703 | */ |
| steiger | 0:7c97dcef700c | 1704 | TiXmlUnknown* Unknown() const { return ToUnknown(); } |
| steiger | 0:7c97dcef700c | 1705 | |
| steiger | 0:7c97dcef700c | 1706 | private: |
| steiger | 0:7c97dcef700c | 1707 | TiXmlNode* node; |
| steiger | 0:7c97dcef700c | 1708 | }; |
| steiger | 0:7c97dcef700c | 1709 | |
| steiger | 0:7c97dcef700c | 1710 | |
| steiger | 0:7c97dcef700c | 1711 | /** Print to memory functionality. The TiXmlPrinter is useful when you need to: |
| steiger | 0:7c97dcef700c | 1712 | |
| steiger | 0:7c97dcef700c | 1713 | -# Print to memory (especially in non-STL mode) |
| steiger | 0:7c97dcef700c | 1714 | -# Control formatting (line endings, etc.) |
| steiger | 0:7c97dcef700c | 1715 | |
| steiger | 0:7c97dcef700c | 1716 | When constructed, the TiXmlPrinter is in its default "pretty printing" mode. |
| steiger | 0:7c97dcef700c | 1717 | Before calling Accept() you can call methods to control the printing |
| steiger | 0:7c97dcef700c | 1718 | of the XML document. After TiXmlNode::Accept() is called, the printed document can |
| steiger | 0:7c97dcef700c | 1719 | be accessed via the CStr(), Str(), and Size() methods. |
| steiger | 0:7c97dcef700c | 1720 | |
| steiger | 0:7c97dcef700c | 1721 | TiXmlPrinter uses the Visitor API. |
| steiger | 0:7c97dcef700c | 1722 | @verbatim |
| steiger | 0:7c97dcef700c | 1723 | TiXmlPrinter printer; |
| steiger | 0:7c97dcef700c | 1724 | printer.SetIndent( "\t" ); |
| steiger | 0:7c97dcef700c | 1725 | |
| steiger | 0:7c97dcef700c | 1726 | doc.Accept( &printer ); |
| steiger | 0:7c97dcef700c | 1727 | fprintf( stdout, "%s", printer.CStr() ); |
| steiger | 0:7c97dcef700c | 1728 | @endverbatim |
| steiger | 0:7c97dcef700c | 1729 | */ |
| steiger | 0:7c97dcef700c | 1730 | class TiXmlPrinter : public TiXmlVisitor |
| steiger | 0:7c97dcef700c | 1731 | { |
| steiger | 0:7c97dcef700c | 1732 | public: |
| steiger | 0:7c97dcef700c | 1733 | TiXmlPrinter() : depth( 0 ), simpleTextPrint( false ), |
| steiger | 0:7c97dcef700c | 1734 | buffer(), indent( " " ), lineBreak( "\n" ) {} |
| steiger | 0:7c97dcef700c | 1735 | |
| steiger | 0:7c97dcef700c | 1736 | virtual bool VisitEnter( const TiXmlDocument& doc ); |
| steiger | 0:7c97dcef700c | 1737 | virtual bool VisitExit( const TiXmlDocument& doc ); |
| steiger | 0:7c97dcef700c | 1738 | |
| steiger | 0:7c97dcef700c | 1739 | virtual bool VisitEnter( const TiXmlElement& element, const TiXmlAttribute* firstAttribute ); |
| steiger | 0:7c97dcef700c | 1740 | virtual bool VisitExit( const TiXmlElement& element ); |
| steiger | 0:7c97dcef700c | 1741 | |
| steiger | 0:7c97dcef700c | 1742 | virtual bool Visit( const TiXmlDeclaration& declaration ); |
| steiger | 0:7c97dcef700c | 1743 | virtual bool Visit( const TiXmlText& text ); |
| steiger | 0:7c97dcef700c | 1744 | virtual bool Visit( const TiXmlComment& comment ); |
| steiger | 0:7c97dcef700c | 1745 | virtual bool Visit( const TiXmlUnknown& unknown ); |
| steiger | 0:7c97dcef700c | 1746 | |
| steiger | 0:7c97dcef700c | 1747 | /** Set the indent characters for printing. By default 4 spaces |
| steiger | 0:7c97dcef700c | 1748 | but tab (\t) is also useful, or null/empty string for no indentation. |
| steiger | 0:7c97dcef700c | 1749 | */ |
| steiger | 0:7c97dcef700c | 1750 | void SetIndent( const char* _indent ) { indent = _indent ? _indent : "" ; } |
| steiger | 0:7c97dcef700c | 1751 | /// Query the indention string. |
| steiger | 0:7c97dcef700c | 1752 | const char* Indent() { return indent.c_str(); } |
| steiger | 0:7c97dcef700c | 1753 | /** Set the line breaking string. By default set to newline (\n). |
| steiger | 0:7c97dcef700c | 1754 | Some operating systems prefer other characters, or can be |
| steiger | 0:7c97dcef700c | 1755 | set to the null/empty string for no indenation. |
| steiger | 0:7c97dcef700c | 1756 | */ |
| steiger | 0:7c97dcef700c | 1757 | void SetLineBreak( const char* _lineBreak ) { lineBreak = _lineBreak ? _lineBreak : ""; } |
| steiger | 0:7c97dcef700c | 1758 | /// Query the current line breaking string. |
| steiger | 0:7c97dcef700c | 1759 | const char* LineBreak() { return lineBreak.c_str(); } |
| steiger | 0:7c97dcef700c | 1760 | |
| steiger | 0:7c97dcef700c | 1761 | /** Switch over to "stream printing" which is the most dense formatting without |
| steiger | 0:7c97dcef700c | 1762 | linebreaks. Common when the XML is needed for network transmission. |
| steiger | 0:7c97dcef700c | 1763 | */ |
| steiger | 0:7c97dcef700c | 1764 | void SetStreamPrinting() { indent = ""; |
| steiger | 0:7c97dcef700c | 1765 | lineBreak = ""; |
| steiger | 0:7c97dcef700c | 1766 | } |
| steiger | 0:7c97dcef700c | 1767 | /// Return the result. |
| steiger | 0:7c97dcef700c | 1768 | const char* CStr() { return buffer.c_str(); } |
| steiger | 0:7c97dcef700c | 1769 | /// Return the length of the result string. |
| steiger | 0:7c97dcef700c | 1770 | size_t Size() { return buffer.size(); } |
| steiger | 0:7c97dcef700c | 1771 | |
| steiger | 0:7c97dcef700c | 1772 | #ifdef TIXML_USE_STL |
| steiger | 0:7c97dcef700c | 1773 | /// Return the result. |
| steiger | 0:7c97dcef700c | 1774 | const std::string& Str() { return buffer; } |
| steiger | 0:7c97dcef700c | 1775 | #endif |
| steiger | 0:7c97dcef700c | 1776 | |
| steiger | 0:7c97dcef700c | 1777 | private: |
| steiger | 0:7c97dcef700c | 1778 | void DoIndent() { |
| steiger | 0:7c97dcef700c | 1779 | for( int i=0; i<depth; ++i ) |
| steiger | 0:7c97dcef700c | 1780 | buffer += indent; |
| steiger | 0:7c97dcef700c | 1781 | } |
| steiger | 0:7c97dcef700c | 1782 | void DoLineBreak() { |
| steiger | 0:7c97dcef700c | 1783 | buffer += lineBreak; |
| steiger | 0:7c97dcef700c | 1784 | } |
| steiger | 0:7c97dcef700c | 1785 | |
| steiger | 0:7c97dcef700c | 1786 | int depth; |
| steiger | 0:7c97dcef700c | 1787 | bool simpleTextPrint; |
| steiger | 0:7c97dcef700c | 1788 | TIXML_STRING buffer; |
| steiger | 0:7c97dcef700c | 1789 | TIXML_STRING indent; |
| steiger | 0:7c97dcef700c | 1790 | TIXML_STRING lineBreak; |
| steiger | 0:7c97dcef700c | 1791 | }; |
| steiger | 0:7c97dcef700c | 1792 | |
| steiger | 0:7c97dcef700c | 1793 | |
| steiger | 0:7c97dcef700c | 1794 | #ifdef _MSC_VER |
| steiger | 0:7c97dcef700c | 1795 | #pragma warning( pop ) |
| steiger | 0:7c97dcef700c | 1796 | #endif |
| steiger | 0:7c97dcef700c | 1797 | |
| steiger | 0:7c97dcef700c | 1798 | #endif |
| steiger | 0:7c97dcef700c | 1799 |