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:
parent
9b33107551
commit
97b75a79bf
6 changed files with 45 additions and 5 deletions
|
@ -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;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -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,
|
||||
|
|
|
@ -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);
|
||||
}
|
||||
|
||||
|
|
|
@ -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
|
||||
|
|
|
@ -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)
|
||||
|
||||
|
|
|
@ -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
|
||||
|
|
Loading…
Add table
Reference in a new issue