Major property-manager rewrite, using const char * throughout
interface instead of string. This will result in a lot more efficiency later, once I add in a simple hash table for caching lookups, since it will avoid creating a lot of temporary string objects. The major considerations for users will be that they cannot use node->getName() == "foo"; any more, and will have to use c_str() when setting a string value from a C++ string.
This commit is contained in:
+154
-109
@@ -6,17 +6,25 @@
|
|||||||
//
|
//
|
||||||
// $Id$
|
// $Id$
|
||||||
|
|
||||||
#include <simgear/compiler.h>
|
|
||||||
#include <simgear/debug/logstream.hxx>
|
|
||||||
|
|
||||||
#include <stdio.h>
|
|
||||||
#include <stdlib.h>
|
|
||||||
#include STL_IOSTREAM
|
|
||||||
#include <algorithm>
|
|
||||||
#include "props.hxx"
|
#include "props.hxx"
|
||||||
|
|
||||||
|
#if PROPS_STANDALONE
|
||||||
|
|
||||||
|
#include <iostream>
|
||||||
|
using std::cerr;
|
||||||
|
using std::endl;
|
||||||
|
using std::sort;
|
||||||
|
|
||||||
|
#else
|
||||||
|
|
||||||
|
#include <simgear/compiler.h>
|
||||||
|
#include <simgear/debug/logstream.hxx>
|
||||||
SG_USING_STD(sort);
|
SG_USING_STD(sort);
|
||||||
|
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#include <string.h>
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////////////
|
||||||
@@ -54,7 +62,7 @@ const int SGRawValue<int>::DefaultValue = 0;
|
|||||||
const long SGRawValue<long>::DefaultValue = 0L;
|
const long SGRawValue<long>::DefaultValue = 0L;
|
||||||
const float SGRawValue<float>::DefaultValue = 0.0;
|
const float SGRawValue<float>::DefaultValue = 0.0;
|
||||||
const double SGRawValue<double>::DefaultValue = 0.0L;
|
const double SGRawValue<double>::DefaultValue = 0.0L;
|
||||||
const string SGRawValue<string>::DefaultValue = "";
|
const char * const SGRawValue<const char *>::DefaultValue = "";
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
@@ -76,7 +84,7 @@ struct PathComponent
|
|||||||
*
|
*
|
||||||
* Name: [_a-zA-Z][-._a-zA-Z0-9]*
|
* Name: [_a-zA-Z][-._a-zA-Z0-9]*
|
||||||
*/
|
*/
|
||||||
static inline string
|
static inline const string
|
||||||
parse_name (const string &path, int &i)
|
parse_name (const string &path, int &i)
|
||||||
{
|
{
|
||||||
string name = "";
|
string name = "";
|
||||||
@@ -204,16 +212,35 @@ parse_path (const string &path, vector<PathComponent> &components)
|
|||||||
////////////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
|
|
||||||
|
static const char *
|
||||||
|
copy_string (const char * s)
|
||||||
|
{
|
||||||
|
// FIXME: potential buffer overflow.
|
||||||
|
// For some reason, strnlen and
|
||||||
|
// strncpy cause all kinds of crashes.
|
||||||
|
string str = s;
|
||||||
|
size_t len = strlen(s);
|
||||||
|
char * copy = new char[str.size() + 1];
|
||||||
|
strcpy(copy, str.c_str());
|
||||||
|
return copy;
|
||||||
|
}
|
||||||
|
|
||||||
|
static bool
|
||||||
|
compare_strings (const char * s1, const char * s2)
|
||||||
|
{
|
||||||
|
return !strncmp(s1, s2, SGPropertyNode::MAX_STRING_LEN);
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Locate a child node by name and index.
|
* Locate a child node by name and index.
|
||||||
*/
|
*/
|
||||||
static int
|
static int
|
||||||
find_child (const string &name, int index, vector<SGPropertyNode *> nodes)
|
find_child (const char * name, int index, vector<SGPropertyNode *> nodes)
|
||||||
{
|
{
|
||||||
int nNodes = nodes.size();
|
int nNodes = nodes.size();
|
||||||
for (int i = 0; i < nNodes; i++) {
|
for (int i = 0; i < nNodes; i++) {
|
||||||
SGPropertyNode * node = nodes[i];
|
SGPropertyNode * node = nodes[i];
|
||||||
if (node->getName() == name && node->getIndex() == index)
|
if (compare_strings(node->getName(), name) && node->getIndex() == index)
|
||||||
return i;
|
return i;
|
||||||
}
|
}
|
||||||
return -1;
|
return -1;
|
||||||
@@ -261,7 +288,7 @@ find_node (SGPropertyNode * current,
|
|||||||
// Otherwise, a child name
|
// Otherwise, a child name
|
||||||
else {
|
else {
|
||||||
SGPropertyNode * child =
|
SGPropertyNode * child =
|
||||||
current->getChild(components[position].name,
|
current->getChild(components[position].name.c_str(),
|
||||||
components[position].index,
|
components[position].index,
|
||||||
create);
|
create);
|
||||||
return find_node(child, components, position + 1, create);
|
return find_node(child, components, position + 1, create);
|
||||||
@@ -319,13 +346,13 @@ SGPropertyNode::get_double () const
|
|||||||
return _local_val.double_val;
|
return _local_val.double_val;
|
||||||
}
|
}
|
||||||
|
|
||||||
inline const string
|
inline const char *
|
||||||
SGPropertyNode::get_string () const
|
SGPropertyNode::get_string () const
|
||||||
{
|
{
|
||||||
if (_tied)
|
if (_tied)
|
||||||
return _value.string_val->getValue();
|
return _value.string_val->getValue();
|
||||||
else
|
else
|
||||||
return *(_local_val.string_val);
|
return _local_val.string_val;
|
||||||
}
|
}
|
||||||
|
|
||||||
inline bool
|
inline bool
|
||||||
@@ -384,12 +411,13 @@ SGPropertyNode::set_double (double val)
|
|||||||
}
|
}
|
||||||
|
|
||||||
inline bool
|
inline bool
|
||||||
SGPropertyNode::set_string (const string &val)
|
SGPropertyNode::set_string (const char * val)
|
||||||
{
|
{
|
||||||
if (_tied) {
|
if (_tied) {
|
||||||
return _value.string_val->setValue(val);
|
return _value.string_val->setValue(val);
|
||||||
} else {
|
} else {
|
||||||
(*_local_val.string_val) = val;
|
delete _local_val.string_val;
|
||||||
|
_local_val.string_val = copy_string(val);
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -443,12 +471,11 @@ SGPropertyNode::clear_value ()
|
|||||||
/**
|
/**
|
||||||
* Get the value as a string.
|
* Get the value as a string.
|
||||||
*/
|
*/
|
||||||
string
|
const char *
|
||||||
SGPropertyNode::make_string () const
|
SGPropertyNode::make_string () const
|
||||||
{
|
{
|
||||||
if (!getAttribute(READ))
|
if (!getAttribute(READ))
|
||||||
return "";
|
return "";
|
||||||
char buf[128];
|
|
||||||
|
|
||||||
switch (_type) {
|
switch (_type) {
|
||||||
case ALIAS:
|
case ALIAS:
|
||||||
@@ -459,17 +486,17 @@ SGPropertyNode::make_string () const
|
|||||||
else
|
else
|
||||||
return "false";
|
return "false";
|
||||||
case INT:
|
case INT:
|
||||||
sprintf(buf, "%d", get_int());
|
sprintf(_buffer, "%d", get_int());
|
||||||
return buf;
|
return _buffer;
|
||||||
case LONG:
|
case LONG:
|
||||||
sprintf(buf, "%ld", get_long());
|
sprintf(_buffer, "%ld", get_long());
|
||||||
return buf;
|
return _buffer;
|
||||||
case FLOAT:
|
case FLOAT:
|
||||||
sprintf(buf, "%f", get_float());
|
sprintf(_buffer, "%f", get_float());
|
||||||
return buf;
|
return _buffer;
|
||||||
case DOUBLE:
|
case DOUBLE:
|
||||||
sprintf(buf, "%f", get_double());
|
sprintf(_buffer, "%f", get_double());
|
||||||
return buf;
|
return _buffer;
|
||||||
case STRING:
|
case STRING:
|
||||||
case UNSPECIFIED:
|
case UNSPECIFIED:
|
||||||
return get_string();
|
return get_string();
|
||||||
@@ -485,8 +512,13 @@ SGPropertyNode::make_string () const
|
|||||||
void
|
void
|
||||||
SGPropertyNode::trace_write () const
|
SGPropertyNode::trace_write () const
|
||||||
{
|
{
|
||||||
|
#if PROPS_STANDALONE
|
||||||
|
cerr << "TRACE: Write node " << getPath () << ", value\""
|
||||||
|
<< make_string() << '"' << endl;
|
||||||
|
#else
|
||||||
SG_LOG(SG_GENERAL, SG_INFO, "TRACE: Write node " << getPath()
|
SG_LOG(SG_GENERAL, SG_INFO, "TRACE: Write node " << getPath()
|
||||||
<< ", value\"" << make_string() << '"');
|
<< ", value\"" << make_string() << '"');
|
||||||
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -495,8 +527,13 @@ SGPropertyNode::trace_write () const
|
|||||||
void
|
void
|
||||||
SGPropertyNode::trace_read () const
|
SGPropertyNode::trace_read () const
|
||||||
{
|
{
|
||||||
|
#if PROPS_STANDALONE
|
||||||
|
cerr << "TRACE: Write node " << getPath () << ", value \""
|
||||||
|
<< make_string() << '"' << endl;
|
||||||
|
#else
|
||||||
SG_LOG(SG_GENERAL, SG_INFO, "TRACE: Read node " << getPath()
|
SG_LOG(SG_GENERAL, SG_INFO, "TRACE: Read node " << getPath()
|
||||||
<< ", value \"" << make_string() << '"');
|
<< ", value \"" << make_string() << '"');
|
||||||
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@@ -509,7 +546,7 @@ SGPropertyNode::trace_read () const
|
|||||||
* Default constructor: always creates a root node.
|
* Default constructor: always creates a root node.
|
||||||
*/
|
*/
|
||||||
SGPropertyNode::SGPropertyNode ()
|
SGPropertyNode::SGPropertyNode ()
|
||||||
: _name(""),
|
: _name(copy_string("")),
|
||||||
_index(0),
|
_index(0),
|
||||||
_parent(0),
|
_parent(0),
|
||||||
_path_cache(0),
|
_path_cache(0),
|
||||||
@@ -517,6 +554,7 @@ SGPropertyNode::SGPropertyNode ()
|
|||||||
_tied(false),
|
_tied(false),
|
||||||
_attr(READ|WRITE)
|
_attr(READ|WRITE)
|
||||||
{
|
{
|
||||||
|
_local_val.string_val = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@@ -524,14 +562,15 @@ SGPropertyNode::SGPropertyNode ()
|
|||||||
* Copy constructor.
|
* Copy constructor.
|
||||||
*/
|
*/
|
||||||
SGPropertyNode::SGPropertyNode (const SGPropertyNode &node)
|
SGPropertyNode::SGPropertyNode (const SGPropertyNode &node)
|
||||||
: _name(node._name),
|
: _index(node._index),
|
||||||
_index(node._index),
|
|
||||||
_parent(0), // don't copy the parent
|
_parent(0), // don't copy the parent
|
||||||
_path_cache(0),
|
_path_cache(0),
|
||||||
_type(node._type),
|
_type(node._type),
|
||||||
_tied(node._tied),
|
_tied(node._tied),
|
||||||
_attr(node._attr)
|
_attr(node._attr)
|
||||||
{
|
{
|
||||||
|
_name = copy_string(node._name);
|
||||||
|
_local_val.string_val = 0;
|
||||||
switch (_type) {
|
switch (_type) {
|
||||||
case NONE:
|
case NONE:
|
||||||
break;
|
break;
|
||||||
@@ -591,7 +630,6 @@ SGPropertyNode::SGPropertyNode (const SGPropertyNode &node)
|
|||||||
_value.string_val = node._value.string_val->clone();
|
_value.string_val = node._value.string_val->clone();
|
||||||
} else {
|
} else {
|
||||||
_tied = false;
|
_tied = false;
|
||||||
_local_val.string_val = new string;
|
|
||||||
set_string(node.get_string());
|
set_string(node.get_string());
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
@@ -602,16 +640,18 @@ SGPropertyNode::SGPropertyNode (const SGPropertyNode &node)
|
|||||||
/**
|
/**
|
||||||
* Convenience constructor.
|
* Convenience constructor.
|
||||||
*/
|
*/
|
||||||
SGPropertyNode::SGPropertyNode (const string &name,
|
SGPropertyNode::SGPropertyNode (const char * name,
|
||||||
int index, SGPropertyNode * parent)
|
int index,
|
||||||
: _name(name),
|
SGPropertyNode * parent)
|
||||||
_index(index),
|
: _index(index),
|
||||||
_parent(parent),
|
_parent(parent),
|
||||||
_path_cache(0),
|
_path_cache(0),
|
||||||
_type(NONE),
|
_type(NONE),
|
||||||
_tied(false),
|
_tied(false),
|
||||||
_attr(READ|WRITE)
|
_attr(READ|WRITE)
|
||||||
{
|
{
|
||||||
|
_name = copy_string(name);
|
||||||
|
_local_val.string_val = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@@ -620,10 +660,11 @@ SGPropertyNode::SGPropertyNode (const string &name,
|
|||||||
*/
|
*/
|
||||||
SGPropertyNode::~SGPropertyNode ()
|
SGPropertyNode::~SGPropertyNode ()
|
||||||
{
|
{
|
||||||
|
delete _name;
|
||||||
for (int i = 0; i < (int)_children.size(); i++) {
|
for (int i = 0; i < (int)_children.size(); i++) {
|
||||||
delete _children[i];
|
delete _children[i];
|
||||||
}
|
}
|
||||||
delete _path_cache;
|
// delete _path_cache;
|
||||||
clear_value();
|
clear_value();
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -647,7 +688,7 @@ SGPropertyNode::alias (SGPropertyNode * target)
|
|||||||
* Alias to another node by path.
|
* Alias to another node by path.
|
||||||
*/
|
*/
|
||||||
bool
|
bool
|
||||||
SGPropertyNode::alias (const string &path)
|
SGPropertyNode::alias (const char * path)
|
||||||
{
|
{
|
||||||
return alias(getNode(path, true));
|
return alias(getNode(path, true));
|
||||||
}
|
}
|
||||||
@@ -714,7 +755,7 @@ SGPropertyNode::getChild (int position) const
|
|||||||
* Get a non-const child by name and index, creating if necessary.
|
* Get a non-const child by name and index, creating if necessary.
|
||||||
*/
|
*/
|
||||||
SGPropertyNode *
|
SGPropertyNode *
|
||||||
SGPropertyNode::getChild (const string &name, int index, bool create)
|
SGPropertyNode::getChild (const char * name, int index, bool create)
|
||||||
{
|
{
|
||||||
int pos = find_child(name, index, _children);
|
int pos = find_child(name, index, _children);
|
||||||
if (pos >= 0) {
|
if (pos >= 0) {
|
||||||
@@ -732,7 +773,7 @@ SGPropertyNode::getChild (const string &name, int index, bool create)
|
|||||||
* Get a const child by name and index.
|
* Get a const child by name and index.
|
||||||
*/
|
*/
|
||||||
const SGPropertyNode *
|
const SGPropertyNode *
|
||||||
SGPropertyNode::getChild (const string &name, int index) const
|
SGPropertyNode::getChild (const char * name, int index) const
|
||||||
{
|
{
|
||||||
int pos = find_child(name, index, _children);
|
int pos = find_child(name, index, _children);
|
||||||
if (pos >= 0)
|
if (pos >= 0)
|
||||||
@@ -746,13 +787,13 @@ SGPropertyNode::getChild (const string &name, int index) const
|
|||||||
* Get all children with the same name (but different indices).
|
* Get all children with the same name (but different indices).
|
||||||
*/
|
*/
|
||||||
vector<SGPropertyNode *>
|
vector<SGPropertyNode *>
|
||||||
SGPropertyNode::getChildren (const string &name)
|
SGPropertyNode::getChildren (const char * name)
|
||||||
{
|
{
|
||||||
vector<SGPropertyNode *> children;
|
vector<SGPropertyNode *> children;
|
||||||
int max = _children.size();
|
int max = _children.size();
|
||||||
|
|
||||||
for (int i = 0; i < max; i++)
|
for (int i = 0; i < max; i++)
|
||||||
if (_children[i]->getName() == name)
|
if (compare_strings(_children[i]->getName(), name))
|
||||||
children.push_back(_children[i]);
|
children.push_back(_children[i]);
|
||||||
|
|
||||||
sort(children.begin(), children.end(), CompareIndices());
|
sort(children.begin(), children.end(), CompareIndices());
|
||||||
@@ -764,13 +805,13 @@ SGPropertyNode::getChildren (const string &name)
|
|||||||
* Get all children const with the same name (but different indices).
|
* Get all children const with the same name (but different indices).
|
||||||
*/
|
*/
|
||||||
vector<const SGPropertyNode *>
|
vector<const SGPropertyNode *>
|
||||||
SGPropertyNode::getChildren (const string &name) const
|
SGPropertyNode::getChildren (const char * name) const
|
||||||
{
|
{
|
||||||
vector<const SGPropertyNode *> children;
|
vector<const SGPropertyNode *> children;
|
||||||
int max = _children.size();
|
int max = _children.size();
|
||||||
|
|
||||||
for (int i = 0; i < max; i++)
|
for (int i = 0; i < max; i++)
|
||||||
if (_children[i]->getName() == name)
|
if (compare_strings(_children[i]->getName(), name))
|
||||||
children.push_back(_children[i]);
|
children.push_back(_children[i]);
|
||||||
|
|
||||||
sort(children.begin(), children.end(), CompareIndices());
|
sort(children.begin(), children.end(), CompareIndices());
|
||||||
@@ -778,7 +819,7 @@ SGPropertyNode::getChildren (const string &name) const
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
string
|
const char *
|
||||||
SGPropertyNode::getPath (bool simplify) const
|
SGPropertyNode::getPath (bool simplify) const
|
||||||
{
|
{
|
||||||
if (_parent == 0)
|
if (_parent == 0)
|
||||||
@@ -792,7 +833,7 @@ SGPropertyNode::getPath (bool simplify) const
|
|||||||
sprintf(buffer, "[%d]", _index);
|
sprintf(buffer, "[%d]", _index);
|
||||||
path += buffer;
|
path += buffer;
|
||||||
}
|
}
|
||||||
return path;
|
return path.c_str();
|
||||||
}
|
}
|
||||||
|
|
||||||
SGPropertyNode::Type
|
SGPropertyNode::Type
|
||||||
@@ -831,7 +872,7 @@ SGPropertyNode::getBoolValue () const
|
|||||||
return get_double() == 0.0L ? false : true;
|
return get_double() == 0.0L ? false : true;
|
||||||
case STRING:
|
case STRING:
|
||||||
case UNSPECIFIED:
|
case UNSPECIFIED:
|
||||||
return (get_string() == "true" || getDoubleValue() != 0.0L);
|
return (compare_strings(get_string(), "true") || getDoubleValue() != 0.0L);
|
||||||
case NONE:
|
case NONE:
|
||||||
default:
|
default:
|
||||||
return SGRawValue<bool>::DefaultValue;
|
return SGRawValue<bool>::DefaultValue;
|
||||||
@@ -864,7 +905,7 @@ SGPropertyNode::getIntValue () const
|
|||||||
return int(get_double());
|
return int(get_double());
|
||||||
case STRING:
|
case STRING:
|
||||||
case UNSPECIFIED:
|
case UNSPECIFIED:
|
||||||
return atoi(get_string().c_str());
|
return atoi(get_string());
|
||||||
case NONE:
|
case NONE:
|
||||||
default:
|
default:
|
||||||
return SGRawValue<int>::DefaultValue;
|
return SGRawValue<int>::DefaultValue;
|
||||||
@@ -897,7 +938,7 @@ SGPropertyNode::getLongValue () const
|
|||||||
return long(get_double());
|
return long(get_double());
|
||||||
case STRING:
|
case STRING:
|
||||||
case UNSPECIFIED:
|
case UNSPECIFIED:
|
||||||
return strtol(get_string().c_str(), 0, 0);
|
return strtol(get_string(), 0, 0);
|
||||||
case NONE:
|
case NONE:
|
||||||
default:
|
default:
|
||||||
return SGRawValue<long>::DefaultValue;
|
return SGRawValue<long>::DefaultValue;
|
||||||
@@ -930,7 +971,7 @@ SGPropertyNode::getFloatValue () const
|
|||||||
return float(get_double());
|
return float(get_double());
|
||||||
case STRING:
|
case STRING:
|
||||||
case UNSPECIFIED:
|
case UNSPECIFIED:
|
||||||
return atof(get_string().c_str());
|
return atof(get_string());
|
||||||
case NONE:
|
case NONE:
|
||||||
default:
|
default:
|
||||||
return SGRawValue<float>::DefaultValue;
|
return SGRawValue<float>::DefaultValue;
|
||||||
@@ -964,14 +1005,14 @@ SGPropertyNode::getDoubleValue () const
|
|||||||
return get_double();
|
return get_double();
|
||||||
case STRING:
|
case STRING:
|
||||||
case UNSPECIFIED:
|
case UNSPECIFIED:
|
||||||
return strtod(get_string().c_str(), 0);
|
return strtod(get_string(), 0);
|
||||||
case NONE:
|
case NONE:
|
||||||
default:
|
default:
|
||||||
return SGRawValue<double>::DefaultValue;
|
return SGRawValue<double>::DefaultValue;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
string
|
const char *
|
||||||
SGPropertyNode::getStringValue () const
|
SGPropertyNode::getStringValue () const
|
||||||
{
|
{
|
||||||
// Shortcut for common case
|
// Shortcut for common case
|
||||||
@@ -981,7 +1022,7 @@ SGPropertyNode::getStringValue () const
|
|||||||
if (getAttribute(TRACE_READ))
|
if (getAttribute(TRACE_READ))
|
||||||
trace_read();
|
trace_read();
|
||||||
if (!getAttribute(READ))
|
if (!getAttribute(READ))
|
||||||
return SGRawValue<string>::DefaultValue;
|
return SGRawValue<const char *>::DefaultValue;
|
||||||
return make_string();
|
return make_string();
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -1238,7 +1279,7 @@ SGPropertyNode::setDoubleValue (double value)
|
|||||||
}
|
}
|
||||||
|
|
||||||
bool
|
bool
|
||||||
SGPropertyNode::setStringValue (string value)
|
SGPropertyNode::setStringValue (const char * value)
|
||||||
{
|
{
|
||||||
// Shortcut for common case
|
// Shortcut for common case
|
||||||
if (_attr == (READ|WRITE) && _type == STRING)
|
if (_attr == (READ|WRITE) && _type == STRING)
|
||||||
@@ -1248,7 +1289,6 @@ SGPropertyNode::setStringValue (string value)
|
|||||||
TEST_WRITE;
|
TEST_WRITE;
|
||||||
if (_type == NONE || _type == UNSPECIFIED) {
|
if (_type == NONE || _type == UNSPECIFIED) {
|
||||||
clear_value();
|
clear_value();
|
||||||
_local_val.string_val = new string;
|
|
||||||
_type = STRING;
|
_type = STRING;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -1257,19 +1297,20 @@ SGPropertyNode::setStringValue (string value)
|
|||||||
result = _value.alias->setStringValue(value);
|
result = _value.alias->setStringValue(value);
|
||||||
break;
|
break;
|
||||||
case BOOL:
|
case BOOL:
|
||||||
result = set_bool((value == "true" || atoi(value.c_str())) ? true : false);
|
result = set_bool((compare_strings(value, "true")
|
||||||
|
|| atoi(value)) ? true : false);
|
||||||
break;
|
break;
|
||||||
case INT:
|
case INT:
|
||||||
result = set_int(atoi(value.c_str()));
|
result = set_int(atoi(value));
|
||||||
break;
|
break;
|
||||||
case LONG:
|
case LONG:
|
||||||
result = set_long(strtol(value.c_str(), 0, 0));
|
result = set_long(strtol(value, 0, 0));
|
||||||
break;
|
break;
|
||||||
case FLOAT:
|
case FLOAT:
|
||||||
result = set_float(atof(value.c_str()));
|
result = set_float(atof(value));
|
||||||
break;
|
break;
|
||||||
case DOUBLE:
|
case DOUBLE:
|
||||||
result = set_double(strtod(value.c_str(), 0));
|
result = set_double(strtod(value, 0));
|
||||||
break;
|
break;
|
||||||
case STRING:
|
case STRING:
|
||||||
case UNSPECIFIED:
|
case UNSPECIFIED:
|
||||||
@@ -1286,13 +1327,12 @@ SGPropertyNode::setStringValue (string value)
|
|||||||
}
|
}
|
||||||
|
|
||||||
bool
|
bool
|
||||||
SGPropertyNode::setUnspecifiedValue (string value)
|
SGPropertyNode::setUnspecifiedValue (const char * value)
|
||||||
{
|
{
|
||||||
bool result = false;
|
bool result = false;
|
||||||
TEST_WRITE;
|
TEST_WRITE;
|
||||||
if (_type == NONE) {
|
if (_type == NONE) {
|
||||||
clear_value();
|
clear_value();
|
||||||
_local_val.string_val = new string;
|
|
||||||
_type = UNSPECIFIED;
|
_type = UNSPECIFIED;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -1301,19 +1341,20 @@ SGPropertyNode::setUnspecifiedValue (string value)
|
|||||||
result = _value.alias->setUnspecifiedValue(value);
|
result = _value.alias->setUnspecifiedValue(value);
|
||||||
break;
|
break;
|
||||||
case BOOL:
|
case BOOL:
|
||||||
result = set_bool((value == "true" || atoi(value.c_str())) ? true : false);
|
result = set_bool((compare_strings(value, "true")
|
||||||
|
|| atoi(value)) ? true : false);
|
||||||
break;
|
break;
|
||||||
case INT:
|
case INT:
|
||||||
result = set_int(atoi(value.c_str()));
|
result = set_int(atoi(value));
|
||||||
break;
|
break;
|
||||||
case LONG:
|
case LONG:
|
||||||
result = set_long(strtol(value.c_str(), 0, 0));
|
result = set_long(strtol(value, 0, 0));
|
||||||
break;
|
break;
|
||||||
case FLOAT:
|
case FLOAT:
|
||||||
result = set_float(atof(value.c_str()));
|
result = set_float(atof(value));
|
||||||
break;
|
break;
|
||||||
case DOUBLE:
|
case DOUBLE:
|
||||||
result = set_double(strtod(value.c_str(), 0));
|
result = set_double(strtod(value, 0));
|
||||||
break;
|
break;
|
||||||
case STRING:
|
case STRING:
|
||||||
case UNSPECIFIED:
|
case UNSPECIFIED:
|
||||||
@@ -1441,7 +1482,7 @@ SGPropertyNode::tie (const SGRawValue<double> &rawValue, bool useDefault)
|
|||||||
}
|
}
|
||||||
|
|
||||||
bool
|
bool
|
||||||
SGPropertyNode::tie (const SGRawValue<string> &rawValue, bool useDefault)
|
SGPropertyNode::tie (const SGRawValue<const char *> &rawValue, bool useDefault)
|
||||||
{
|
{
|
||||||
if (_type == ALIAS || _tied)
|
if (_type == ALIAS || _tied)
|
||||||
return false;
|
return false;
|
||||||
@@ -1457,7 +1498,7 @@ SGPropertyNode::tie (const SGRawValue<string> &rawValue, bool useDefault)
|
|||||||
_value.string_val = rawValue.clone();
|
_value.string_val = rawValue.clone();
|
||||||
|
|
||||||
if (useDefault)
|
if (useDefault)
|
||||||
setStringValue(old_val);
|
setStringValue(old_val.c_str());
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
@@ -1509,7 +1550,7 @@ SGPropertyNode::untie ()
|
|||||||
string val = getStringValue();
|
string val = getStringValue();
|
||||||
clear_value();
|
clear_value();
|
||||||
_type = STRING;
|
_type = STRING;
|
||||||
_local_val.string_val = new string(val);
|
_local_val.string_val = copy_string(val.c_str());
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case NONE:
|
case NONE:
|
||||||
@@ -1540,25 +1581,28 @@ SGPropertyNode::getRootNode () const
|
|||||||
}
|
}
|
||||||
|
|
||||||
SGPropertyNode *
|
SGPropertyNode *
|
||||||
SGPropertyNode::getNode (const string &relative_path, bool create)
|
SGPropertyNode::getNode (const char * relative_path, bool create)
|
||||||
{
|
{
|
||||||
if (_path_cache == 0)
|
// if (_path_cache == 0)
|
||||||
_path_cache = new cache_map;
|
// _path_cache = new cache_map;
|
||||||
|
|
||||||
SGPropertyNode * result = (*_path_cache)[relative_path];
|
// SGPropertyNode * result = (*_path_cache)[relative_path];
|
||||||
if (result == 0) {
|
// if (result == 0) {
|
||||||
vector<PathComponent> components;
|
// vector<PathComponent> components;
|
||||||
parse_path(relative_path, components);
|
// parse_path(relative_path, components);
|
||||||
result = find_node(this, components, 0, create);
|
// result = find_node(this, components, 0, create);
|
||||||
if (result != 0)
|
// if (result != 0)
|
||||||
(*_path_cache)[relative_path] = result;
|
// (*_path_cache)[relative_path] = result;
|
||||||
}
|
// }
|
||||||
|
|
||||||
return result;
|
// return result;
|
||||||
|
vector<PathComponent> components;
|
||||||
|
parse_path(relative_path, components);
|
||||||
|
return find_node(this, components, 0, create);
|
||||||
}
|
}
|
||||||
|
|
||||||
SGPropertyNode *
|
SGPropertyNode *
|
||||||
SGPropertyNode::getNode (const string &relative_path, int index, bool create)
|
SGPropertyNode::getNode (const char * relative_path, int index, bool create)
|
||||||
{
|
{
|
||||||
vector<PathComponent> components;
|
vector<PathComponent> components;
|
||||||
parse_path(relative_path, components);
|
parse_path(relative_path, components);
|
||||||
@@ -1568,13 +1612,13 @@ SGPropertyNode::getNode (const string &relative_path, int index, bool create)
|
|||||||
}
|
}
|
||||||
|
|
||||||
const SGPropertyNode *
|
const SGPropertyNode *
|
||||||
SGPropertyNode::getNode (const string &relative_path) const
|
SGPropertyNode::getNode (const char * relative_path) const
|
||||||
{
|
{
|
||||||
return ((SGPropertyNode *)this)->getNode(relative_path, false);
|
return ((SGPropertyNode *)this)->getNode(relative_path, false);
|
||||||
}
|
}
|
||||||
|
|
||||||
const SGPropertyNode *
|
const SGPropertyNode *
|
||||||
SGPropertyNode::getNode (const string &relative_path, int index) const
|
SGPropertyNode::getNode (const char * relative_path, int index) const
|
||||||
{
|
{
|
||||||
return ((SGPropertyNode *)this)->getNode(relative_path, index, false);
|
return ((SGPropertyNode *)this)->getNode(relative_path, index, false);
|
||||||
}
|
}
|
||||||
@@ -1589,7 +1633,7 @@ SGPropertyNode::getNode (const string &relative_path, int index) const
|
|||||||
* Test whether another node has a value attached.
|
* Test whether another node has a value attached.
|
||||||
*/
|
*/
|
||||||
bool
|
bool
|
||||||
SGPropertyNode::hasValue (const string &relative_path) const
|
SGPropertyNode::hasValue (const char * relative_path) const
|
||||||
{
|
{
|
||||||
const SGPropertyNode * node = getNode(relative_path);
|
const SGPropertyNode * node = getNode(relative_path);
|
||||||
return (node == 0 ? false : node->hasValue());
|
return (node == 0 ? false : node->hasValue());
|
||||||
@@ -1600,7 +1644,7 @@ SGPropertyNode::hasValue (const string &relative_path) const
|
|||||||
* Get the value type for another node.
|
* Get the value type for another node.
|
||||||
*/
|
*/
|
||||||
SGPropertyNode::Type
|
SGPropertyNode::Type
|
||||||
SGPropertyNode::getType (const string &relative_path) const
|
SGPropertyNode::getType (const char * relative_path) const
|
||||||
{
|
{
|
||||||
const SGPropertyNode * node = getNode(relative_path);
|
const SGPropertyNode * node = getNode(relative_path);
|
||||||
return (node == 0 ? UNSPECIFIED : (Type)(node->getType()));
|
return (node == 0 ? UNSPECIFIED : (Type)(node->getType()));
|
||||||
@@ -1611,7 +1655,7 @@ SGPropertyNode::getType (const string &relative_path) const
|
|||||||
* Get a bool value for another node.
|
* Get a bool value for another node.
|
||||||
*/
|
*/
|
||||||
bool
|
bool
|
||||||
SGPropertyNode::getBoolValue (const string &relative_path,
|
SGPropertyNode::getBoolValue (const char * relative_path,
|
||||||
bool defaultValue) const
|
bool defaultValue) const
|
||||||
{
|
{
|
||||||
const SGPropertyNode * node = getNode(relative_path);
|
const SGPropertyNode * node = getNode(relative_path);
|
||||||
@@ -1623,7 +1667,7 @@ SGPropertyNode::getBoolValue (const string &relative_path,
|
|||||||
* Get an int value for another node.
|
* Get an int value for another node.
|
||||||
*/
|
*/
|
||||||
int
|
int
|
||||||
SGPropertyNode::getIntValue (const string &relative_path,
|
SGPropertyNode::getIntValue (const char * relative_path,
|
||||||
int defaultValue) const
|
int defaultValue) const
|
||||||
{
|
{
|
||||||
const SGPropertyNode * node = getNode(relative_path);
|
const SGPropertyNode * node = getNode(relative_path);
|
||||||
@@ -1635,7 +1679,7 @@ SGPropertyNode::getIntValue (const string &relative_path,
|
|||||||
* Get a long value for another node.
|
* Get a long value for another node.
|
||||||
*/
|
*/
|
||||||
long
|
long
|
||||||
SGPropertyNode::getLongValue (const string &relative_path,
|
SGPropertyNode::getLongValue (const char * relative_path,
|
||||||
long defaultValue) const
|
long defaultValue) const
|
||||||
{
|
{
|
||||||
const SGPropertyNode * node = getNode(relative_path);
|
const SGPropertyNode * node = getNode(relative_path);
|
||||||
@@ -1647,7 +1691,7 @@ SGPropertyNode::getLongValue (const string &relative_path,
|
|||||||
* Get a float value for another node.
|
* Get a float value for another node.
|
||||||
*/
|
*/
|
||||||
float
|
float
|
||||||
SGPropertyNode::getFloatValue (const string &relative_path,
|
SGPropertyNode::getFloatValue (const char * relative_path,
|
||||||
float defaultValue) const
|
float defaultValue) const
|
||||||
{
|
{
|
||||||
const SGPropertyNode * node = getNode(relative_path);
|
const SGPropertyNode * node = getNode(relative_path);
|
||||||
@@ -1659,7 +1703,7 @@ SGPropertyNode::getFloatValue (const string &relative_path,
|
|||||||
* Get a double value for another node.
|
* Get a double value for another node.
|
||||||
*/
|
*/
|
||||||
double
|
double
|
||||||
SGPropertyNode::getDoubleValue (const string &relative_path,
|
SGPropertyNode::getDoubleValue (const char * relative_path,
|
||||||
double defaultValue) const
|
double defaultValue) const
|
||||||
{
|
{
|
||||||
const SGPropertyNode * node = getNode(relative_path);
|
const SGPropertyNode * node = getNode(relative_path);
|
||||||
@@ -1670,9 +1714,9 @@ SGPropertyNode::getDoubleValue (const string &relative_path,
|
|||||||
/**
|
/**
|
||||||
* Get a string value for another node.
|
* Get a string value for another node.
|
||||||
*/
|
*/
|
||||||
string
|
const char *
|
||||||
SGPropertyNode::getStringValue (const string &relative_path,
|
SGPropertyNode::getStringValue (const char * relative_path,
|
||||||
string defaultValue) const
|
const char * defaultValue) const
|
||||||
{
|
{
|
||||||
const SGPropertyNode * node = getNode(relative_path);
|
const SGPropertyNode * node = getNode(relative_path);
|
||||||
return (node == 0 ? defaultValue : node->getStringValue());
|
return (node == 0 ? defaultValue : node->getStringValue());
|
||||||
@@ -1683,7 +1727,7 @@ SGPropertyNode::getStringValue (const string &relative_path,
|
|||||||
* Set a bool value for another node.
|
* Set a bool value for another node.
|
||||||
*/
|
*/
|
||||||
bool
|
bool
|
||||||
SGPropertyNode::setBoolValue (const string &relative_path, bool value)
|
SGPropertyNode::setBoolValue (const char * relative_path, bool value)
|
||||||
{
|
{
|
||||||
return getNode(relative_path, true)->setBoolValue(value);
|
return getNode(relative_path, true)->setBoolValue(value);
|
||||||
}
|
}
|
||||||
@@ -1693,7 +1737,7 @@ SGPropertyNode::setBoolValue (const string &relative_path, bool value)
|
|||||||
* Set an int value for another node.
|
* Set an int value for another node.
|
||||||
*/
|
*/
|
||||||
bool
|
bool
|
||||||
SGPropertyNode::setIntValue (const string &relative_path, int value)
|
SGPropertyNode::setIntValue (const char * relative_path, int value)
|
||||||
{
|
{
|
||||||
return getNode(relative_path, true)->setIntValue(value);
|
return getNode(relative_path, true)->setIntValue(value);
|
||||||
}
|
}
|
||||||
@@ -1703,7 +1747,7 @@ SGPropertyNode::setIntValue (const string &relative_path, int value)
|
|||||||
* Set a long value for another node.
|
* Set a long value for another node.
|
||||||
*/
|
*/
|
||||||
bool
|
bool
|
||||||
SGPropertyNode::setLongValue (const string &relative_path, long value)
|
SGPropertyNode::setLongValue (const char * relative_path, long value)
|
||||||
{
|
{
|
||||||
return getNode(relative_path, true)->setLongValue(value);
|
return getNode(relative_path, true)->setLongValue(value);
|
||||||
}
|
}
|
||||||
@@ -1713,7 +1757,7 @@ SGPropertyNode::setLongValue (const string &relative_path, long value)
|
|||||||
* Set a float value for another node.
|
* Set a float value for another node.
|
||||||
*/
|
*/
|
||||||
bool
|
bool
|
||||||
SGPropertyNode::setFloatValue (const string &relative_path, float value)
|
SGPropertyNode::setFloatValue (const char * relative_path, float value)
|
||||||
{
|
{
|
||||||
return getNode(relative_path, true)->setFloatValue(value);
|
return getNode(relative_path, true)->setFloatValue(value);
|
||||||
}
|
}
|
||||||
@@ -1723,7 +1767,7 @@ SGPropertyNode::setFloatValue (const string &relative_path, float value)
|
|||||||
* Set a double value for another node.
|
* Set a double value for another node.
|
||||||
*/
|
*/
|
||||||
bool
|
bool
|
||||||
SGPropertyNode::setDoubleValue (const string &relative_path, double value)
|
SGPropertyNode::setDoubleValue (const char * relative_path, double value)
|
||||||
{
|
{
|
||||||
return getNode(relative_path, true)->setDoubleValue(value);
|
return getNode(relative_path, true)->setDoubleValue(value);
|
||||||
}
|
}
|
||||||
@@ -1733,7 +1777,7 @@ SGPropertyNode::setDoubleValue (const string &relative_path, double value)
|
|||||||
* Set a string value for another node.
|
* Set a string value for another node.
|
||||||
*/
|
*/
|
||||||
bool
|
bool
|
||||||
SGPropertyNode::setStringValue (const string &relative_path, string value)
|
SGPropertyNode::setStringValue (const char * relative_path, const char * value)
|
||||||
{
|
{
|
||||||
return getNode(relative_path, true)->setStringValue(value);
|
return getNode(relative_path, true)->setStringValue(value);
|
||||||
}
|
}
|
||||||
@@ -1743,7 +1787,8 @@ SGPropertyNode::setStringValue (const string &relative_path, string value)
|
|||||||
* Set an unknown value for another node.
|
* Set an unknown value for another node.
|
||||||
*/
|
*/
|
||||||
bool
|
bool
|
||||||
SGPropertyNode::setUnspecifiedValue (const string &relative_path, string value)
|
SGPropertyNode::setUnspecifiedValue (const char * relative_path,
|
||||||
|
const char * value)
|
||||||
{
|
{
|
||||||
return getNode(relative_path, true)->setUnspecifiedValue(value);
|
return getNode(relative_path, true)->setUnspecifiedValue(value);
|
||||||
}
|
}
|
||||||
@@ -1753,7 +1798,7 @@ SGPropertyNode::setUnspecifiedValue (const string &relative_path, string value)
|
|||||||
* Test whether another node is tied.
|
* Test whether another node is tied.
|
||||||
*/
|
*/
|
||||||
bool
|
bool
|
||||||
SGPropertyNode::isTied (const string &relative_path) const
|
SGPropertyNode::isTied (const char * relative_path) const
|
||||||
{
|
{
|
||||||
const SGPropertyNode * node = getNode(relative_path);
|
const SGPropertyNode * node = getNode(relative_path);
|
||||||
return (node == 0 ? false : node->isTied());
|
return (node == 0 ? false : node->isTied());
|
||||||
@@ -1764,7 +1809,7 @@ SGPropertyNode::isTied (const string &relative_path) const
|
|||||||
* Tie a node reached by a relative path, creating it if necessary.
|
* Tie a node reached by a relative path, creating it if necessary.
|
||||||
*/
|
*/
|
||||||
bool
|
bool
|
||||||
SGPropertyNode::tie (const string &relative_path,
|
SGPropertyNode::tie (const char * relative_path,
|
||||||
const SGRawValue<bool> &rawValue,
|
const SGRawValue<bool> &rawValue,
|
||||||
bool useDefault)
|
bool useDefault)
|
||||||
{
|
{
|
||||||
@@ -1776,7 +1821,7 @@ SGPropertyNode::tie (const string &relative_path,
|
|||||||
* Tie a node reached by a relative path, creating it if necessary.
|
* Tie a node reached by a relative path, creating it if necessary.
|
||||||
*/
|
*/
|
||||||
bool
|
bool
|
||||||
SGPropertyNode::tie (const string &relative_path,
|
SGPropertyNode::tie (const char * relative_path,
|
||||||
const SGRawValue<int> &rawValue,
|
const SGRawValue<int> &rawValue,
|
||||||
bool useDefault)
|
bool useDefault)
|
||||||
{
|
{
|
||||||
@@ -1788,7 +1833,7 @@ SGPropertyNode::tie (const string &relative_path,
|
|||||||
* Tie a node reached by a relative path, creating it if necessary.
|
* Tie a node reached by a relative path, creating it if necessary.
|
||||||
*/
|
*/
|
||||||
bool
|
bool
|
||||||
SGPropertyNode::tie (const string &relative_path,
|
SGPropertyNode::tie (const char * relative_path,
|
||||||
const SGRawValue<long> &rawValue,
|
const SGRawValue<long> &rawValue,
|
||||||
bool useDefault)
|
bool useDefault)
|
||||||
{
|
{
|
||||||
@@ -1800,7 +1845,7 @@ SGPropertyNode::tie (const string &relative_path,
|
|||||||
* Tie a node reached by a relative path, creating it if necessary.
|
* Tie a node reached by a relative path, creating it if necessary.
|
||||||
*/
|
*/
|
||||||
bool
|
bool
|
||||||
SGPropertyNode::tie (const string &relative_path,
|
SGPropertyNode::tie (const char * relative_path,
|
||||||
const SGRawValue<float> &rawValue,
|
const SGRawValue<float> &rawValue,
|
||||||
bool useDefault)
|
bool useDefault)
|
||||||
{
|
{
|
||||||
@@ -1812,7 +1857,7 @@ SGPropertyNode::tie (const string &relative_path,
|
|||||||
* Tie a node reached by a relative path, creating it if necessary.
|
* Tie a node reached by a relative path, creating it if necessary.
|
||||||
*/
|
*/
|
||||||
bool
|
bool
|
||||||
SGPropertyNode::tie (const string &relative_path,
|
SGPropertyNode::tie (const char * relative_path,
|
||||||
const SGRawValue<double> &rawValue,
|
const SGRawValue<double> &rawValue,
|
||||||
bool useDefault)
|
bool useDefault)
|
||||||
{
|
{
|
||||||
@@ -1824,8 +1869,8 @@ SGPropertyNode::tie (const string &relative_path,
|
|||||||
* Tie a node reached by a relative path, creating it if necessary.
|
* Tie a node reached by a relative path, creating it if necessary.
|
||||||
*/
|
*/
|
||||||
bool
|
bool
|
||||||
SGPropertyNode::tie (const string &relative_path,
|
SGPropertyNode::tie (const char * relative_path,
|
||||||
const SGRawValue<string> &rawValue,
|
const SGRawValue<const char *> &rawValue,
|
||||||
bool useDefault)
|
bool useDefault)
|
||||||
{
|
{
|
||||||
return getNode(relative_path, true)->tie(rawValue, useDefault);
|
return getNode(relative_path, true)->tie(rawValue, useDefault);
|
||||||
@@ -1836,7 +1881,7 @@ SGPropertyNode::tie (const string &relative_path,
|
|||||||
* Attempt to untie another node reached by a relative path.
|
* Attempt to untie another node reached by a relative path.
|
||||||
*/
|
*/
|
||||||
bool
|
bool
|
||||||
SGPropertyNode::untie (const string &relative_path)
|
SGPropertyNode::untie (const char * relative_path)
|
||||||
{
|
{
|
||||||
SGPropertyNode * node = getNode(relative_path);
|
SGPropertyNode * node = getNode(relative_path);
|
||||||
return (node == 0 ? false : node->untie());
|
return (node == 0 ? false : node->untie());
|
||||||
|
|||||||
+78
-52
@@ -12,16 +12,30 @@
|
|||||||
#ifndef __PROPS_HXX
|
#ifndef __PROPS_HXX
|
||||||
#define __PROPS_HXX
|
#define __PROPS_HXX
|
||||||
|
|
||||||
#include <simgear/compiler.h>
|
#ifndef PROPS_STANDALONE
|
||||||
#include <simgear/debug/logstream.hxx>
|
#define PROPS_STANDALONE 0
|
||||||
|
#endif
|
||||||
|
|
||||||
#include <stdio.h>
|
|
||||||
|
|
||||||
#include STL_STRING
|
|
||||||
#include <vector>
|
#include <vector>
|
||||||
#include <map>
|
#include <map>
|
||||||
#include STL_IOSTREAM
|
|
||||||
|
|
||||||
|
#if PROPS_STANDALONE
|
||||||
|
|
||||||
|
#include <string>
|
||||||
|
#include <iostream>
|
||||||
|
|
||||||
|
using std::string;
|
||||||
|
using std::vector;
|
||||||
|
using std::map;
|
||||||
|
using std::istream;
|
||||||
|
using std::ostream;
|
||||||
|
|
||||||
|
#else
|
||||||
|
|
||||||
|
#include <simgear/compiler.h>
|
||||||
|
#include <simgear/debug/logstream.hxx>
|
||||||
|
#include STL_STRING
|
||||||
|
#include STL_IOSTREAM
|
||||||
SG_USING_STD(string);
|
SG_USING_STD(string);
|
||||||
SG_USING_STD(vector);
|
SG_USING_STD(vector);
|
||||||
SG_USING_STD(map);
|
SG_USING_STD(map);
|
||||||
@@ -30,6 +44,9 @@ SG_USING_STD(istream);
|
|||||||
SG_USING_STD(ostream);
|
SG_USING_STD(ostream);
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
#endif
|
||||||
|
|
||||||
|
|
||||||
#ifdef NONE
|
#ifdef NONE
|
||||||
#pragma warn A sloppy coder has defined NONE as a macro!
|
#pragma warn A sloppy coder has defined NONE as a macro!
|
||||||
#undef NONE
|
#undef NONE
|
||||||
@@ -444,6 +461,13 @@ class SGPropertyNode
|
|||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Public constants.
|
||||||
|
*/
|
||||||
|
enum {
|
||||||
|
MAX_STRING_LEN = 1024
|
||||||
|
};
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Property value types.
|
* Property value types.
|
||||||
*/
|
*/
|
||||||
@@ -507,7 +531,7 @@ public:
|
|||||||
/**
|
/**
|
||||||
* Get the node's simple (XML) name.
|
* Get the node's simple (XML) name.
|
||||||
*/
|
*/
|
||||||
const string &getName () const { return _name; }
|
const char * getName () const { return _name; }
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -554,26 +578,26 @@ public:
|
|||||||
/**
|
/**
|
||||||
* Get a child node by name and index.
|
* Get a child node by name and index.
|
||||||
*/
|
*/
|
||||||
SGPropertyNode * getChild (const string &name, int index = 0,
|
SGPropertyNode * getChild (const char * name, int index = 0,
|
||||||
bool create = false);
|
bool create = false);
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Get a const child node by name and index.
|
* Get a const child node by name and index.
|
||||||
*/
|
*/
|
||||||
const SGPropertyNode * getChild (const string &name, int index = 0) const;
|
const SGPropertyNode * getChild (const char * name, int index = 0) const;
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Get a vector of all children with the specified name.
|
* Get a vector of all children with the specified name.
|
||||||
*/
|
*/
|
||||||
vector<SGPropertyNode *> getChildren (const string &name);
|
vector<SGPropertyNode *> getChildren (const char * name);
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Get a vector all all children (const) with the specified name.
|
* Get a vector all all children (const) with the specified name.
|
||||||
*/
|
*/
|
||||||
vector<const SGPropertyNode *> getChildren (const string &name) const;
|
vector<const SGPropertyNode *> getChildren (const char * name) const;
|
||||||
|
|
||||||
|
|
||||||
//
|
//
|
||||||
@@ -590,7 +614,7 @@ public:
|
|||||||
/**
|
/**
|
||||||
* Alias this node's leaf value to another's by relative path.
|
* Alias this node's leaf value to another's by relative path.
|
||||||
*/
|
*/
|
||||||
bool alias (const string &path);
|
bool alias (const char * path);
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -625,7 +649,7 @@ public:
|
|||||||
/**
|
/**
|
||||||
* Get the path to this node from the root.
|
* Get the path to this node from the root.
|
||||||
*/
|
*/
|
||||||
string getPath (bool simplify = false) const;
|
const char * getPath (bool simplify = false) const;
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -643,7 +667,7 @@ public:
|
|||||||
/**
|
/**
|
||||||
* Get a pointer to another node by relative path.
|
* Get a pointer to another node by relative path.
|
||||||
*/
|
*/
|
||||||
SGPropertyNode * getNode (const string &relative_path, bool create = false);
|
SGPropertyNode * getNode (const char * relative_path, bool create = false);
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -656,14 +680,14 @@ public:
|
|||||||
* provided overrides any given in the path itself for the last
|
* provided overrides any given in the path itself for the last
|
||||||
* component.
|
* component.
|
||||||
*/
|
*/
|
||||||
SGPropertyNode * getNode (const string &relative_path, int index,
|
SGPropertyNode * getNode (const char * relative_path, int index,
|
||||||
bool create = false);
|
bool create = false);
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Get a const pointer to another node by relative path.
|
* Get a const pointer to another node by relative path.
|
||||||
*/
|
*/
|
||||||
const SGPropertyNode * getNode (const string &relative_path) const;
|
const SGPropertyNode * getNode (const char * relative_path) const;
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -672,7 +696,7 @@ public:
|
|||||||
* This method leaves the index off the last member of the path,
|
* This method leaves the index off the last member of the path,
|
||||||
* so that the user can specify it separate.
|
* so that the user can specify it separate.
|
||||||
*/
|
*/
|
||||||
const SGPropertyNode * getNode (const string &relative_path,
|
const SGPropertyNode * getNode (const char * relative_path,
|
||||||
int index) const;
|
int index) const;
|
||||||
|
|
||||||
|
|
||||||
@@ -750,7 +774,7 @@ public:
|
|||||||
/**
|
/**
|
||||||
* Get a string value for this node.
|
* Get a string value for this node.
|
||||||
*/
|
*/
|
||||||
string getStringValue () const;
|
const char * getStringValue () const;
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
@@ -787,13 +811,13 @@ public:
|
|||||||
/**
|
/**
|
||||||
* Set a string value for this node.
|
* Set a string value for this node.
|
||||||
*/
|
*/
|
||||||
bool setStringValue (string value);
|
bool setStringValue (const char * value);
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Set a value of unspecified type for this node.
|
* Set a value of unspecified type for this node.
|
||||||
*/
|
*/
|
||||||
bool setUnspecifiedValue (string value);
|
bool setUnspecifiedValue (const char * value);
|
||||||
|
|
||||||
|
|
||||||
//
|
//
|
||||||
@@ -840,7 +864,7 @@ public:
|
|||||||
/**
|
/**
|
||||||
* Bind this node to an external string source.
|
* Bind this node to an external string source.
|
||||||
*/
|
*/
|
||||||
bool tie (const SGRawValue<string> &rawValue, bool useDefault = true);
|
bool tie (const SGRawValue<const char *> &rawValue, bool useDefault = true);
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -858,151 +882,151 @@ public:
|
|||||||
/**
|
/**
|
||||||
* Get another node's type.
|
* Get another node's type.
|
||||||
*/
|
*/
|
||||||
Type getType (const string &relative_path) const;
|
Type getType (const char * relative_path) const;
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Test whether another node has a leaf value.
|
* Test whether another node has a leaf value.
|
||||||
*/
|
*/
|
||||||
bool hasValue (const string &relative_path) const;
|
bool hasValue (const char * relative_path) const;
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Get another node's value as a bool.
|
* Get another node's value as a bool.
|
||||||
*/
|
*/
|
||||||
bool getBoolValue (const string &relative_path,
|
bool getBoolValue (const char * relative_path,
|
||||||
bool defaultValue = false) const;
|
bool defaultValue = false) const;
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Get another node's value as an int.
|
* Get another node's value as an int.
|
||||||
*/
|
*/
|
||||||
int getIntValue (const string &relative_path,
|
int getIntValue (const char * relative_path,
|
||||||
int defaultValue = 0) const;
|
int defaultValue = 0) const;
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Get another node's value as a long int.
|
* Get another node's value as a long int.
|
||||||
*/
|
*/
|
||||||
long getLongValue (const string &relative_path,
|
long getLongValue (const char * relative_path,
|
||||||
long defaultValue = 0L) const;
|
long defaultValue = 0L) const;
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Get another node's value as a float.
|
* Get another node's value as a float.
|
||||||
*/
|
*/
|
||||||
float getFloatValue (const string &relative_path,
|
float getFloatValue (const char * relative_path,
|
||||||
float defaultValue = 0.0) const;
|
float defaultValue = 0.0) const;
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Get another node's value as a double.
|
* Get another node's value as a double.
|
||||||
*/
|
*/
|
||||||
double getDoubleValue (const string &relative_path,
|
double getDoubleValue (const char * relative_path,
|
||||||
double defaultValue = 0.0L) const;
|
double defaultValue = 0.0L) const;
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Get another node's value as a string.
|
* Get another node's value as a string.
|
||||||
*/
|
*/
|
||||||
string getStringValue (const string &relative_path,
|
const char * getStringValue (const char * relative_path,
|
||||||
string defaultValue = "") const;
|
const char * defaultValue = "") const;
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Set another node's value as a bool.
|
* Set another node's value as a bool.
|
||||||
*/
|
*/
|
||||||
bool setBoolValue (const string &relative_path, bool value);
|
bool setBoolValue (const char * relative_path, bool value);
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Set another node's value as an int.
|
* Set another node's value as an int.
|
||||||
*/
|
*/
|
||||||
bool setIntValue (const string &relative_path, int value);
|
bool setIntValue (const char * relative_path, int value);
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Set another node's value as a long int.
|
* Set another node's value as a long int.
|
||||||
*/
|
*/
|
||||||
bool setLongValue (const string &relative_path, long value);
|
bool setLongValue (const char * relative_path, long value);
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Set another node's value as a float.
|
* Set another node's value as a float.
|
||||||
*/
|
*/
|
||||||
bool setFloatValue (const string &relative_path, float value);
|
bool setFloatValue (const char * relative_path, float value);
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Set another node's value as a double.
|
* Set another node's value as a double.
|
||||||
*/
|
*/
|
||||||
bool setDoubleValue (const string &relative_path, double value);
|
bool setDoubleValue (const char * relative_path, double value);
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Set another node's value as a string.
|
* Set another node's value as a string.
|
||||||
*/
|
*/
|
||||||
bool setStringValue (const string &relative_path, string value);
|
bool setStringValue (const char * relative_path, const char * value);
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Set another node's value with no specified type.
|
* Set another node's value with no specified type.
|
||||||
*/
|
*/
|
||||||
bool setUnspecifiedValue (const string &relative_path, string value);
|
bool setUnspecifiedValue (const char * relative_path, const char * value);
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Test whether another node is bound to an external data source.
|
* Test whether another node is bound to an external data source.
|
||||||
*/
|
*/
|
||||||
bool isTied (const string &relative_path) const;
|
bool isTied (const char * relative_path) const;
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Bind another node to an external bool source.
|
* Bind another node to an external bool source.
|
||||||
*/
|
*/
|
||||||
bool tie (const string &relative_path, const SGRawValue<bool> &rawValue,
|
bool tie (const char * relative_path, const SGRawValue<bool> &rawValue,
|
||||||
bool useDefault = true);
|
bool useDefault = true);
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Bind another node to an external int source.
|
* Bind another node to an external int source.
|
||||||
*/
|
*/
|
||||||
bool tie (const string &relative_path, const SGRawValue<int> &rawValue,
|
bool tie (const char * relative_path, const SGRawValue<int> &rawValue,
|
||||||
bool useDefault = true);
|
bool useDefault = true);
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Bind another node to an external long int source.
|
* Bind another node to an external long int source.
|
||||||
*/
|
*/
|
||||||
bool tie (const string &relative_path, const SGRawValue<long> &rawValue,
|
bool tie (const char * relative_path, const SGRawValue<long> &rawValue,
|
||||||
bool useDefault = true);
|
bool useDefault = true);
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Bind another node to an external float source.
|
* Bind another node to an external float source.
|
||||||
*/
|
*/
|
||||||
bool tie (const string &relative_path, const SGRawValue<float> &rawValue,
|
bool tie (const char * relative_path, const SGRawValue<float> &rawValue,
|
||||||
bool useDefault = true);
|
bool useDefault = true);
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Bind another node to an external double source.
|
* Bind another node to an external double source.
|
||||||
*/
|
*/
|
||||||
bool tie (const string &relative_path, const SGRawValue<double> &rawValue,
|
bool tie (const char * relative_path, const SGRawValue<double> &rawValue,
|
||||||
bool useDefault = true);
|
bool useDefault = true);
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Bind another node to an external string source.
|
* Bind another node to an external string source.
|
||||||
*/
|
*/
|
||||||
bool tie (const string &relative_path, const SGRawValue<string> &rawValue,
|
bool tie (const char * relative_path, const SGRawValue<const char *> &rawValue,
|
||||||
bool useDefault = true);
|
bool useDefault = true);
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Unbind another node from any external data source.
|
* Unbind another node from any external data source.
|
||||||
*/
|
*/
|
||||||
bool untie (const string &relative_path);
|
bool untie (const char * relative_path);
|
||||||
|
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
@@ -1011,7 +1035,7 @@ protected:
|
|||||||
/**
|
/**
|
||||||
* Protected constructor for making new nodes on demand.
|
* Protected constructor for making new nodes on demand.
|
||||||
*/
|
*/
|
||||||
SGPropertyNode (const string &name, int index, SGPropertyNode * parent);
|
SGPropertyNode (const char * name, int index, SGPropertyNode * parent);
|
||||||
|
|
||||||
|
|
||||||
private:
|
private:
|
||||||
@@ -1022,7 +1046,7 @@ private:
|
|||||||
long get_long () const;
|
long get_long () const;
|
||||||
float get_float () const;
|
float get_float () const;
|
||||||
double get_double () const;
|
double get_double () const;
|
||||||
const string get_string () const;
|
const char * get_string () const;
|
||||||
|
|
||||||
// Set the raw value
|
// Set the raw value
|
||||||
bool set_bool (bool value);
|
bool set_bool (bool value);
|
||||||
@@ -1030,7 +1054,7 @@ private:
|
|||||||
bool set_long (long value);
|
bool set_long (long value);
|
||||||
bool set_float (float value);
|
bool set_float (float value);
|
||||||
bool set_double (double value);
|
bool set_double (double value);
|
||||||
bool set_string (const string &value);
|
bool set_string (const char * value);
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -1042,7 +1066,7 @@ private:
|
|||||||
/**
|
/**
|
||||||
* Get the value as a string.
|
* Get the value as a string.
|
||||||
*/
|
*/
|
||||||
string make_string () const;
|
const char * make_string () const;
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -1056,7 +1080,9 @@ private:
|
|||||||
*/
|
*/
|
||||||
void trace_write () const;
|
void trace_write () const;
|
||||||
|
|
||||||
string _name;
|
mutable char _buffer[MAX_STRING_LEN+1];
|
||||||
|
|
||||||
|
const char * _name;
|
||||||
int _index;
|
int _index;
|
||||||
SGPropertyNode * _parent;
|
SGPropertyNode * _parent;
|
||||||
vector<SGPropertyNode *> _children;
|
vector<SGPropertyNode *> _children;
|
||||||
@@ -1074,7 +1100,7 @@ private:
|
|||||||
SGRawValue<long> * long_val;
|
SGRawValue<long> * long_val;
|
||||||
SGRawValue<float> * float_val;
|
SGRawValue<float> * float_val;
|
||||||
SGRawValue<double> * double_val;
|
SGRawValue<double> * double_val;
|
||||||
SGRawValue<string> * string_val;
|
SGRawValue<const char *> * string_val;
|
||||||
} _value;
|
} _value;
|
||||||
|
|
||||||
union {
|
union {
|
||||||
@@ -1083,7 +1109,7 @@ private:
|
|||||||
long long_val;
|
long long_val;
|
||||||
float float_val;
|
float float_val;
|
||||||
double double_val;
|
double double_val;
|
||||||
string * string_val;
|
const char * string_val;
|
||||||
} _local_val;
|
} _local_val;
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
@@ -235,9 +235,9 @@ PropsVisitor::endElement (const char * name)
|
|||||||
} else if (st.type == "double") {
|
} else if (st.type == "double") {
|
||||||
ret = st.node->setDoubleValue(strtod(_data.c_str(), 0));
|
ret = st.node->setDoubleValue(strtod(_data.c_str(), 0));
|
||||||
} else if (st.type == "string") {
|
} else if (st.type == "string") {
|
||||||
ret = st.node->setStringValue(_data);
|
ret = st.node->setStringValue(_data.c_str());
|
||||||
} else if (st.type == "unspecified") {
|
} else if (st.type == "unspecified") {
|
||||||
ret = st.node->setUnspecifiedValue(_data);
|
ret = st.node->setUnspecifiedValue(_data.c_str());
|
||||||
} else {
|
} else {
|
||||||
string message = "Unrecognized data type '";
|
string message = "Unrecognized data type '";
|
||||||
message += st.type;
|
message += st.type;
|
||||||
@@ -438,7 +438,7 @@ writeNode (ostream &output, const SGPropertyNode * node,
|
|||||||
if (!write_all && !isArchivable(node))
|
if (!write_all && !isArchivable(node))
|
||||||
return true; // Everything's OK, but we won't write.
|
return true; // Everything's OK, but we won't write.
|
||||||
|
|
||||||
const string &name = node->getName();
|
const string name = node->getName();
|
||||||
int nChildren = node->nChildren();
|
int nChildren = node->nChildren();
|
||||||
|
|
||||||
// If there is a literal value,
|
// If there is a literal value,
|
||||||
|
|||||||
@@ -53,7 +53,7 @@ static double getNum (int index) { return 1.0 / index; }
|
|||||||
static void
|
static void
|
||||||
show_values (const SGPropertyNode * node)
|
show_values (const SGPropertyNode * node)
|
||||||
{
|
{
|
||||||
cout << "Bool: " << node->getBoolValue() << endl;
|
cout << "Bool: " << (node->getBoolValue() ? "true" : "false") << endl;
|
||||||
cout << "Int: " << node->getIntValue() << endl;
|
cout << "Int: " << node->getIntValue() << endl;
|
||||||
cout << "Float: " << node->getFloatValue() << endl;
|
cout << "Float: " << node->getFloatValue() << endl;
|
||||||
cout << "Double: " << node->getDoubleValue() << endl;
|
cout << "Double: " << node->getDoubleValue() << endl;
|
||||||
@@ -275,7 +275,7 @@ test_value ()
|
|||||||
static void
|
static void
|
||||||
dump_node (const SGPropertyNode * node)
|
dump_node (const SGPropertyNode * node)
|
||||||
{
|
{
|
||||||
writeProperties(cout, node);
|
writeProperties(cout, node, true);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
@@ -333,11 +333,15 @@ int main (int ac, char ** av)
|
|||||||
test_property_nodes();
|
test_property_nodes();
|
||||||
|
|
||||||
for (int i = 1; i < ac; i++) {
|
for (int i = 1; i < ac; i++) {
|
||||||
cout << "Reading " << av[i] << endl;
|
try {
|
||||||
SGPropertyNode root;
|
cout << "Reading " << av[i] << endl;
|
||||||
readProperties(av[i], &root);
|
SGPropertyNode root;
|
||||||
writeProperties(cout, &root);
|
readProperties(av[i], &root);
|
||||||
cout << endl;
|
writeProperties(cout, &root, true);
|
||||||
|
cout << endl;
|
||||||
|
} catch (string &message) {
|
||||||
|
cout << "Aborted with " << message << endl;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
|
|||||||
Reference in New Issue
Block a user