1
0
Fork 0

- introduce some typedefs for SGSharedPtr<>

- add a <period> element to input and output of each filter to support periodical values like headings. See README.digitalfilters for details.
This commit is contained in:
torsten 2009-12-15 21:27:46 +00:00 committed by Tim Moore
parent 179a799333
commit 506f6894e4
2 changed files with 72 additions and 13 deletions

View file

@ -40,14 +40,42 @@
using std::cout; using std::cout;
using std::endl; using std::endl;
FGPeriodicalValue::FGPeriodicalValue( SGPropertyNode_ptr root )
{
SGPropertyNode_ptr minNode = root->getChild( "min" );
SGPropertyNode_ptr maxNode = root->getChild( "max" );
if( minNode == NULL || maxNode == NULL ) {
SG_LOG(SG_AUTOPILOT, SG_ALERT, "periodical defined, but no <min> and/or <max> tag. Period ignored." );
} else {
minPeriod = new FGXMLAutoInput( minNode );
maxPeriod = new FGXMLAutoInput( maxNode );
}
}
double FGPeriodicalValue::normalize( double value )
{
if( !(minPeriod && maxPeriod )) return value;
double p1 = minPeriod->get_value();
double p2 = maxPeriod->get_value();
double min = std::min<double>(p1,p2);
double max = std::max<double>(p1,p2);
double phase = fabs(max - min);
if( phase > SGLimitsd::min() ) {
while( value < min ) value += phase;
while( value > max ) value -= phase;
} else {
value = min; // phase is zero
}
return value;
}
FGXMLAutoInput::FGXMLAutoInput( SGPropertyNode_ptr node, double value, double offset, double scale) : FGXMLAutoInput::FGXMLAutoInput( SGPropertyNode_ptr node, double value, double offset, double scale) :
value(0.0), value(0.0),
abs(false), abs(false),
property(NULL),
offset(NULL),
scale(NULL),
min(NULL),
max(NULL),
_condition(NULL) _condition(NULL)
{ {
parse( node, value, offset, scale ); parse( node, value, offset, scale );
@ -62,6 +90,7 @@ void FGXMLAutoInput::parse( SGPropertyNode_ptr node, double aValue, double aOffs
scale = NULL; scale = NULL;
min = NULL; min = NULL;
max = NULL; max = NULL;
periodical = NULL;
if( node == NULL ) if( node == NULL )
return; return;
@ -92,6 +121,10 @@ void FGXMLAutoInput::parse( SGPropertyNode_ptr node, double aValue, double aOffs
abs = n->getBoolValue(); abs = n->getBoolValue();
} }
if( (n = node->getChild( "period" )) != NULL ) {
periodical = new FGPeriodicalValue( n );
}
SGPropertyNode *valueNode = node->getChild( "value" ); SGPropertyNode *valueNode = node->getChild( "value" );
if ( valueNode != NULL ) { if ( valueNode != NULL ) {
value = valueNode->getDoubleValue(); value = valueNode->getDoubleValue();
@ -161,6 +194,10 @@ double FGXMLAutoInput::get_value()
if( value > m ) if( value > m )
value = m; value = m;
} }
if( periodical ) {
value = periodical->normalize( value );
}
return abs ? fabs(value) : value; return abs ? fabs(value) : value;
} }
@ -246,6 +283,8 @@ void FGXMLAutoComponent::parseNode(SGPropertyNode* aNode)
umaxInput.push_back( new FGXMLAutoInput( child ) ); umaxInput.push_back( new FGXMLAutoInput( child ) );
} else if ( cname == "u_max" ) { } else if ( cname == "u_max" ) {
umaxInput.push_back( new FGXMLAutoInput( child ) ); umaxInput.push_back( new FGXMLAutoInput( child ) );
} else if ( cname == "period" ) {
periodical = new FGPeriodicalValue( child );
} else { } else {
SG_LOG(SG_AUTOPILOT, SG_ALERT, "malformed autopilot definition - unrecognized node:" SG_LOG(SG_AUTOPILOT, SG_ALERT, "malformed autopilot definition - unrecognized node:"
<< cname << " in section " << name); << cname << " in section " << name);
@ -314,6 +353,11 @@ void FGXMLAutoComponent::do_feedback_if_disabled()
double FGXMLAutoComponent::clamp( double value ) double FGXMLAutoComponent::clamp( double value )
{ {
//If this is a periodical value, normalize it into our domain
// before clamping
if( periodical )
value = periodical->normalize( value );
// clamp, if either min or max is defined // clamp, if either min or max is defined
if( uminInput.size() + umaxInput.size() > 0 ) { if( uminInput.size() + umaxInput.size() > 0 ) {
double d = umaxInput.get_value( 0.0 ); double d = umaxInput.get_value( 0.0 );

View file

@ -34,16 +34,28 @@
#include <simgear/structure/subsystem_mgr.hxx> #include <simgear/structure/subsystem_mgr.hxx>
#include <simgear/props/condition.hxx> #include <simgear/props/condition.hxx>
typedef SGSharedPtr<class FGXMLAutoInput> FGXMLAutoInput_ptr;
typedef SGSharedPtr<class FGPeriodicalValue> FGPeriodicalValue_ptr;
class FGPeriodicalValue : public SGReferenced {
private:
FGXMLAutoInput_ptr minPeriod; // The minimum value of the period
FGXMLAutoInput_ptr maxPeriod; // The maximum value of the period
public:
FGPeriodicalValue( SGPropertyNode_ptr node );
double normalize( double value );
};
class FGXMLAutoInput : public SGReferenced { class FGXMLAutoInput : public SGReferenced {
private: private:
double value; // The value as a constant or initializer for the property double value; // The value as a constant or initializer for the property
bool abs; // return absolute value bool abs; // return absolute value
SGPropertyNode_ptr property; // The name of the property containing the value SGPropertyNode_ptr property; // The name of the property containing the value
SGSharedPtr<FGXMLAutoInput> offset; // A fixed offset, defaults to zero FGXMLAutoInput_ptr offset; // A fixed offset, defaults to zero
SGSharedPtr<FGXMLAutoInput> scale; // A constant scaling factor defaults to one FGXMLAutoInput_ptr scale; // A constant scaling factor defaults to one
SGSharedPtr<FGXMLAutoInput> min; // A minimum clip defaults to no clipping FGXMLAutoInput_ptr min; // A minimum clip defaults to no clipping
SGSharedPtr<FGXMLAutoInput> max; // A maximum clip defaults to no clipping FGXMLAutoInput_ptr max; // A maximum clip defaults to no clipping
FGPeriodicalValue_ptr periodical; //
SGSharedPtr<const SGCondition> _condition; SGSharedPtr<const SGCondition> _condition;
public: public:
@ -71,9 +83,9 @@ public:
}; };
class FGXMLAutoInputList : public std::vector<SGSharedPtr<FGXMLAutoInput> > { class FGXMLAutoInputList : public std::vector<FGXMLAutoInput_ptr> {
public: public:
FGXMLAutoInput * get_active() { FGXMLAutoInput_ptr get_active() {
for (iterator it = begin(); it != end(); ++it) { for (iterator it = begin(); it != end(); ++it) {
if( (*it)->is_enabled() ) if( (*it)->is_enabled() )
return *it; return *it;
@ -82,7 +94,7 @@ class FGXMLAutoInputList : public std::vector<SGSharedPtr<FGXMLAutoInput> > {
} }
double get_value( double def = 0.0 ) { double get_value( double def = 0.0 ) {
FGXMLAutoInput * input = get_active(); FGXMLAutoInput_ptr input = get_active();
return input == NULL ? def : input->get_value(); return input == NULL ? def : input->get_value();
} }
@ -147,6 +159,7 @@ protected:
FGXMLAutoInputList referenceInput; FGXMLAutoInputList referenceInput;
FGXMLAutoInputList uminInput; FGXMLAutoInputList uminInput;
FGXMLAutoInputList umaxInput; FGXMLAutoInputList umaxInput;
FGPeriodicalValue_ptr periodical;
// debug flag // debug flag
bool debug; bool debug;
bool enabled; bool enabled;
@ -221,6 +234,8 @@ public:
bool isPropertyEnabled(); bool isPropertyEnabled();
}; };
typedef SGSharedPtr<FGXMLAutoComponent> FGXMLAutoComponent_ptr;
/** /**
* Roy Ovesen's PID controller * Roy Ovesen's PID controller
@ -384,7 +399,7 @@ public:
bool build( SGPropertyNode_ptr ); bool build( SGPropertyNode_ptr );
protected: protected:
typedef std::vector<SGSharedPtr<FGXMLAutoComponent> > comp_list; typedef std::vector<FGXMLAutoComponent_ptr> comp_list;
private: private: