1
0
Fork 0

Inspired by a patch from Vivian, this adds a settable "WASTEGATE"

control to piston engines that allows external scripts to control the
turbo/supercharger boost programatically by setting this axis to
values in the range [0:1].  It also adds a "turbo-lag" attribute (a
time in seconds) to engines implementing turbocharger spooling delays.

This isn't terribly well tested, but doesn't seem to have broken
anything.
This commit is contained in:
andy 2006-02-27 23:35:02 +00:00
parent 9b33107551
commit 97b75a79bf
6 changed files with 45 additions and 5 deletions

View file

@ -215,6 +215,9 @@ void ControlMap::applyControls(float dt)
case BOOST:
((PistonEngine*)((Thruster*)obj)->getEngine())->setBoost(lval);
break;
case WASTEGATE:
((PistonEngine*)((Thruster*)obj)->getEngine())->setWastegate(lval);
break;
}
}
}

View file

@ -15,7 +15,7 @@ public:
INCIDENCE, FLAP0, FLAP1, SLAT, SPOILER, VECTOR,
BOOST, CASTERING, PROPPITCH, PROPFEATHER,
COLLECTIVE, CYCLICAIL, CYCLICELE, ROTORENGINEON,
REVERSE_THRUST };
REVERSE_THRUST, WASTEGATE };
enum { OPT_SPLIT = 0x01,
OPT_INVERT = 0x02,

View file

@ -701,6 +701,9 @@ void FGFDM::parsePistonEngine(XMLAttributes* a)
eng->setTurboParams(mul, mp);
}
if(a->hasAttribute("supercharger"))
eng->setSupercharger(attrb(a, "supercharger"));
((PropEngine*)_currObj)->setEngine(eng);
}

View file

@ -36,6 +36,9 @@ PistonEngine::PistonEngine(float power, float speed)
_turbo = 1;
_maxMP = 1e6; // No waste gate on non-turbo engines.
_wastegate = 1;
_charge = 1;
_chargeTarget = 1;
// Guess at reasonable values for these guys. Displacements run
// at about 2 cubic inches per horsepower or so, at least for
@ -100,11 +103,16 @@ float PistonEngine::getEGT()
void PistonEngine::stabilize()
{
_oilTemp = _oilTempTarget;
_charge = _chargeTarget;
}
void PistonEngine::integrate(float dt)
{
_oilTemp += (_dOilTempdt * dt);
// See comments in Jet.cpp for how this decay constant works
float decay = 1.5f * 2.3f / _turboLag;
_charge = (_charge + dt*decay * _chargeTarget) / (1 + dt*decay);
}
void PistonEngine::calc(float pressure, float temp, float speed)
@ -128,17 +136,27 @@ void PistonEngine::calc(float pressure, float temp, float speed)
float B = 0.55620178;
float C = 1.246708471;
float rpm_factor = A * Math::pow(B, rpm_norm) * Math::pow(rpm_norm, C);
_chargeTarget = 1 + (_boost * (_turbo-1) * rpm_factor);
if(_hasSuper) {
// Superchargers have no lag
_charge = _chargeTarget;
} else if(!_running) {
// Turbochargers only work when the engine is actually
// running. The 25% number is a guesstimate from Vivian.
_chargeTarget = 1 + (_chargeTarget - 1) * 0.25;
}
// We need to adjust the minimum manifold pressure to get a
// reasonable idle speed (a "closed" throttle doesn't suck a total
// vacuum in real manifolds). This is a hack.
float _minMP = (-0.008 * _turbo ) + 0.1;
_mp = pressure * _charge;
// Scale to throttle setting, clamp to wastegate
if(_running) {
_mp = pressure * (1 + (_boost * (_turbo-1) * rpm_factor));
if(_running)
_mp *= _minMP + (1 -_minMP) * _throttle;
}
if(_mp > _maxMP) _mp = _maxMP;
// The "boost" is the delta above ambient

View file

@ -14,6 +14,9 @@ public:
void setTurboParams(float mul, float maxMP);
void setDisplacement(float d);
void setCompression(float c);
void setWastegate(float norm) { _wastegate = norm; }
void setSupercharger(float hasSuper) { _hasSuper = hasSuper; }
void setTurboLag(float lag) { _turboLag = lag; }
bool isCranking();
float getMP();
@ -36,7 +39,12 @@ private:
float _f0; // "ideal" fuel flow at P0/omega0
float _mixCoeff; // fuel flow per omega at full mixture
float _turbo; // (or super-)charger pressure multiplier
float _maxMP; // wastegate setting
bool _hasSuper; // true indicates gear-driven (not turbo)
float _turboLag; // turbo lag time in seconds
float _charge; // current {turbo|super}charge multiplier
float _chargeTarget; // eventual charge value
float _maxMP; // static maximum pressure
float _wastegate; // wastegate setting, [0:1]
float _displacement; // piston stroke volume
float _compression; // compression ratio (>1)

View file

@ -127,6 +127,14 @@ void PropEngine::stabilize()
_eng->calc(_pressure, _temp, _omega);
_eng->stabilize();
// Do it again -- the turbo sets the target MP in the first
// run, stabilize sets the current to the target, then we need
// to run again to get the correct output torque. Clumsy, but
// it works without side effects (other than solver
// performance). In the future, the Engine objects should
// store state to allow them to do the work themselves.
_eng->calc(_pressure, _temp, _omega);
// Compute torque as seen by the engine's end of the gearbox.
// The propeller will be moving more slowly (for gear ratios
// less than one), so it's torque will be higher than the