X-Git-Url: https://git.mxchange.org/?a=blobdiff_plain;f=simgear%2Fprops%2Fprops_io.cxx;h=45886a6cd4614e95f75ceccd84d85a6845c9988b;hb=dcb95d131bc6aef1abe25d1f415e309f06e52436;hp=e936f5b011f0fb6bab7f22abb350c33ea9fb8dfe;hpb=090f79b951f563c406de3cb597f0c47c40756043;p=simgear.git diff --git a/simgear/props/props_io.cxx b/simgear/props/props_io.cxx index e936f5b0..45886a6c 100644 --- a/simgear/props/props_io.cxx +++ b/simgear/props/props_io.cxx @@ -1,3 +1,16 @@ +/** + * \file props_io.cxx + * Started Fall 2000 by David Megginson, david@megginson.com + * This code is released into the Public Domain. + * + * See props.html for documentation [replace with URL when available]. + * + * $Id$ + */ + +#ifdef HAVE_CONFIG_H +# include +#endif #include @@ -37,8 +50,8 @@ class PropsVisitor : public XMLVisitor { public: - PropsVisitor (SGPropertyNode * root, const string &base) - : _root(root), _level(0), _base(base), _hasException(false) {} + PropsVisitor (SGPropertyNode * root, const string &base, int default_mode = 0) + : _default_mode(default_mode), _root(root), _level(0), _base(base), _hasException(false) {} virtual ~PropsVisitor () {} @@ -85,6 +98,7 @@ private: _level--; } + int _default_mode; string _data; SGPropertyNode * _root; int _level; @@ -177,7 +191,7 @@ PropsVisitor::startElement (const char * name, const XMLAttributes &atts) // Get the access-mode attributes, // but don't set yet (in case they // prevent us from recording the value). - int mode = 0; + int mode = _default_mode; attval = atts.getValue("read"); if (checkFlag(attval, true)) @@ -194,6 +208,9 @@ PropsVisitor::startElement (const char * name, const XMLAttributes &atts) attval = atts.getValue("trace-write"); if (checkFlag(attval, false)) mode |= SGPropertyNode::TRACE_WRITE; + attval = atts.getValue("userarchive"); + if (checkFlag(attval, false)) + mode |= SGPropertyNode::USERARCHIVE; // Check for an alias. attval = atts.getValue("alias"); @@ -214,7 +231,10 @@ PropsVisitor::startElement (const char * name, const XMLAttributes &atts) } } - push_state(node, atts.getValue("type"), mode); + const char *type = atts.getValue("type"); + if (type) + node->clearValue(); + push_state(node, type, mode); } } @@ -296,9 +316,9 @@ PropsVisitor::warning (const char * message, int line, int column) */ void readProperties (istream &input, SGPropertyNode * start_node, - const string &base) + const string &base, int default_mode) { - PropsVisitor visitor(start_node, base); + PropsVisitor visitor(start_node, base, default_mode); readXML(input, visitor, base); if (visitor.hasException()) throw visitor.getException(); @@ -313,9 +333,10 @@ readProperties (istream &input, SGPropertyNode * start_node, * @return true if the read succeeded, false otherwise. */ void -readProperties (const string &file, SGPropertyNode * start_node) +readProperties (const string &file, SGPropertyNode * start_node, + int default_mode) { - PropsVisitor visitor(start_node, file); + PropsVisitor visitor(start_node, file, default_mode); readXML(file, visitor); if (visitor.hasException()) throw visitor.getException(); @@ -331,9 +352,9 @@ readProperties (const string &file, SGPropertyNode * start_node) * @return true if the read succeeded, false otherwise. */ void readProperties (const char *buf, const int size, - SGPropertyNode * start_node) + SGPropertyNode * start_node, int default_mode) { - PropsVisitor visitor(start_node, ""); + PropsVisitor visitor(start_node, "", default_mode); readXML(buf, size, visitor); if (visitor.hasException()) throw visitor.getException(); @@ -436,15 +457,15 @@ writeAtts (ostream &output, const SGPropertyNode * node) * Test whether a node is archivable or has archivable descendants. */ static bool -isArchivable (const SGPropertyNode * node) +isArchivable (const SGPropertyNode * node, SGPropertyNode::Attribute archive_flag) { // FIXME: it's inefficient to do this all the time - if (node->getAttribute(SGPropertyNode::ARCHIVE)) + if (node->getAttribute(archive_flag)) return true; else { int nChildren = node->nChildren(); for (int i = 0; i < nChildren; i++) - if (isArchivable(node->getChild(i))) + if (isArchivable(node->getChild(i), archive_flag)) return true; } return false; @@ -453,12 +474,12 @@ isArchivable (const SGPropertyNode * node) static bool writeNode (ostream &output, const SGPropertyNode * node, - bool write_all, int indent) + bool write_all, int indent, SGPropertyNode::Attribute archive_flag) { // Don't write the node or any of // its descendants unless it is // allowed to be archived. - if (!write_all && !isArchivable(node)) + if (!write_all && !isArchivable(node, archive_flag)) return true; // Everything's OK, but we won't write. const string name = node->getName(); @@ -466,7 +487,7 @@ writeNode (ostream &output, const SGPropertyNode * node, // If there is a literal value, // write it first. - if (node->hasValue() && (write_all || node->getAttribute(SGPropertyNode::ARCHIVE))) { + if (node->hasValue() && (write_all || node->getAttribute(archive_flag))) { doIndent(output, indent); output << '<' << name; writeAtts(output, node); @@ -483,13 +504,13 @@ writeNode (ostream &output, const SGPropertyNode * node, } // If there are children, write them next. - if (nChildren > 0 || node->isAlias()) { + if (nChildren > 0) { doIndent(output, indent); output << '<' << name; writeAtts(output, node); output << '>' << endl; for (int i = 0; i < nChildren; i++) - writeNode(output, node->getChild(i), write_all, indent + INDENT_STEP); + writeNode(output, node->getChild(i), write_all, indent + INDENT_STEP, archive_flag); doIndent(output, indent); output << "' << endl; } @@ -500,7 +521,7 @@ writeNode (ostream &output, const SGPropertyNode * node, void writeProperties (ostream &output, const SGPropertyNode * start_node, - bool write_all) + bool write_all, SGPropertyNode::Attribute archive_flag) { int nChildren = start_node->nChildren(); @@ -508,7 +529,7 @@ writeProperties (ostream &output, const SGPropertyNode * start_node, output << "" << endl; for (int i = 0; i < nChildren; i++) { - writeNode(output, start_node->getChild(i), write_all, INDENT_STEP); + writeNode(output, start_node->getChild(i), write_all, INDENT_STEP, archive_flag); } output << "" << endl; @@ -517,11 +538,11 @@ writeProperties (ostream &output, const SGPropertyNode * start_node, void writeProperties (const string &file, const SGPropertyNode * start_node, - bool write_all) + bool write_all, SGPropertyNode::Attribute archive_flag) { ofstream output(file.c_str()); if (output.good()) { - writeProperties(output, start_node, write_all); + writeProperties(output, start_node, write_all, archive_flag); } else { throw sg_io_exception("Cannot open file", sg_location(file)); } @@ -580,12 +601,17 @@ copyProperties (const SGPropertyNode *in, SGPropertyNode *out) retval = false; break; default: + if (in->isAlias()) + break; string message = "Unknown internal SGPropertyNode type"; message += in->getType(); throw sg_error(message, "SimGear Property Reader"); } } + // copy the attributes. + out->setAttributes( in->getAttributes() ); + // Next, copy the children. int nChildren = in->nChildren(); for (int i = 0; i < nChildren; i++) {