fgpiston.cpp

来自「6 DOF Missle Simulation」· C++ 代码 · 共 910 行 · 第 1/3 页

CPP
910
字号
//%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%FGPiston::~FGPiston(){  delete Lookup_Combustion_Efficiency;  delete Power_Mixture_Correlation;  delete Mixture_Efficiency_Correlation;  Debug(1); // Call Debug() routine from constructor if needed}//%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%void FGPiston::ResetToIC(void){  FGEngine::ResetToIC();  ManifoldPressure_inHg = Atmosphere->GetPressure() * psftoinhg; // psf to in Hg  MAP = Atmosphere->GetPressure() * psftopa;  double airTemperature_degK = RankineToKelvin(Atmosphere->GetTemperature());  OilTemp_degK = airTemperature_degK;  CylinderHeadTemp_degK = airTemperature_degK;  ExhaustGasTemp_degK = airTemperature_degK;  EGT_degC = ExhaustGasTemp_degK - 273;  Thruster->SetRPM(0.0);  RPM = 0.0;  OilPressure_psi = 0.0;}//%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%double FGPiston::Calculate(void){  if (FuelFlow_gph > 0.0) ConsumeFuel();  Throttle = FCS->GetThrottlePos(EngineNumber);  ThrottlePos = MinThrottle+((MaxThrottle-MinThrottle)*Throttle );  Mixture = FCS->GetMixturePos(EngineNumber);  //  // Input values.  //  p_amb = Atmosphere->GetPressure() * psftopa;  p_amb_sea_level = Atmosphere->GetPressureSL() * psftopa;  T_amb = RankineToKelvin(Atmosphere->GetTemperature());  RPM = Thruster->GetRPM() * Thruster->GetGearRatio();  IAS = Auxiliary->GetVcalibratedKTS();  doEngineStartup();  if (Boosted) doBoostControl();  doMAP();  doAirFlow();  doFuelFlow();  //Now that the fuel flow is done check if the mixture is too lean to run the engine  //Assume lean limit at 22 AFR for now - thats a thi of 0.668  //This might be a bit generous, but since there's currently no audiable warning of impending  //cutout in the form of misfiring and/or rough running its probably reasonable for now.//  if (equivalence_ratio < 0.668)//    Running = false;  doEnginePower();if(HP<0.1250)  Running = false;  doEGT();  doCHT();  doOilTemperature();  doOilPressure();  if (Thruster->GetType() == FGThruster::ttPropeller) {    ((FGPropeller*)Thruster)->SetAdvance(FCS->GetPropAdvance(EngineNumber));    ((FGPropeller*)Thruster)->SetFeather(FCS->GetPropFeather(EngineNumber));  }  PowerAvailable = (HP * hptoftlbssec) - Thruster->GetPowerRequired();  return Thruster->Calculate(PowerAvailable);}//%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%double FGPiston::CalcFuelNeed(void){  double dT = State->Getdt() * Propulsion->GetRate();  FuelFlow_pph = FuelFlow_gph * 6.0; // Assumes 6 lbs / gallon  FuelFlowRate = FuelFlow_pph / 3600.0;  FuelExpended = FuelFlowRate * dT;  return FuelExpended;}//%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%int FGPiston::InitRunning(void) {  Magnetos=3;  //Thruster->SetRPM( 1.1*IdleRPM/Thruster->GetGearRatio() );  Thruster->SetRPM( 1000 );  Running=true;  return 1;}//%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%/** * Start or stop the engine. */void FGPiston::doEngineStartup(void){  // Check parameters that may alter the operating state of the engine.  // (spark, fuel, starter motor etc)  bool spark;  bool fuel;  // Check for spark  Magneto_Left = false;  Magneto_Right = false;  // Magneto positions:  // 0 -> off  // 1 -> left only  // 2 -> right only  // 3 -> both  if (Magnetos != 0) {    spark = true;  } else {    spark = false;  }  // neglects battery voltage, master on switch, etc for now.  if ((Magnetos == 1) || (Magnetos > 2)) Magneto_Left = true;  if (Magnetos > 1)  Magneto_Right = true;  // Assume we have fuel for now  fuel = !Starved;  // Check if we are turning the starter motor  if (Cranking != Starter) {    // This check saves .../cranking from getting updated every loop - they    // only update when changed.    Cranking = Starter;    crank_counter = 0;  }  if (Cranking) crank_counter++;  //Check mode of engine operation  if (!Running && spark && fuel) {  // start the engine if revs high enough    if (Cranking) {      if ((RPM > IdleRPM*0.8) && (crank_counter > 175)) // Add a little delay to startup        Running = true;                         // on the starter    } else {      if (RPM > IdleRPM*0.8)                            // This allows us to in-air start        Running = true;                         // when windmilling    }  }  // Cut the engine *power* - Note: the engine may continue to  // spin if the prop is in a moving airstream  if ( Running && (!spark || !fuel) ) Running = false;  // Check for stalling (RPM = 0).  if (Running) {    if (RPM == 0) {      Running = false;    } else if ((RPM <= IdleRPM *0.8 ) && (Cranking)) {      Running = false;    }  }}//%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%/** * Calculate the Current Boost Speed * * This function calculates the current turbo/supercharger boost speed * based on altitude and the (automatic) boost-speed control valve configuration. * * Inputs: p_amb, BoostSwitchPressure, BoostSwitchHysteresis * * Outputs: BoostSpeed */void FGPiston::doBoostControl(void){  if(BoostSpeed < BoostSpeeds - 1) {    // Check if we need to change to a higher boost speed    if(p_amb < BoostSwitchPressure[BoostSpeed] - BoostSwitchHysteresis) {      BoostSpeed++;    }  } else if(BoostSpeed > 0) {    // Check if we need to change to a lower boost speed    if(p_amb > BoostSwitchPressure[BoostSpeed - 1] + BoostSwitchHysteresis) {      BoostSpeed--;    }  }}//%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%/** * Calculate the manifold absolute pressure (MAP) in inches hg * * This function calculates manifold absolute pressure (MAP) * from the throttle position, turbo/supercharger boost control * system, engine speed and local ambient air density. * * TODO: changes in MP should not be instantaneous -- introduce * a lag between throttle changes and MP changes, to allow pressure * to build up or disperse. * * Inputs: minMAP, maxMAP, p_amb, Throttle * * Outputs: MAP, ManifoldPressure_inHg */void FGPiston::doMAP(void){    suction_loss = RPM > 0.0 ? ThrottlePos * MaxRPM / RPM : 1.0;    if (suction_loss > 1.0) suction_loss = 1.0;    MAP = p_amb * suction_loss;    if(Boosted) {      // If takeoff boost is fitted, we currently assume the following throttle map:      // (In throttle % - actual input is 0 -> 1)      // 99 / 100 - Takeoff boost      // 96 / 97 / 98 - Rated boost      // 0 - 95 - Idle to Rated boost (MinManifoldPressure to MaxManifoldPressure)      // In real life, most planes would be fitted with a mechanical 'gate' between      // the rated boost and takeoff boost positions.      double T = Throttle; // processed throttle value.      bool bTakeoffPos = false;      if(bTakeoffBoost) {        if(Throttle > 0.98) {          //cout << "Takeoff Boost!!!!\n";          bTakeoffPos = true;        } else if(Throttle <= 0.95) {          bTakeoffPos = false;          T *= 1.0 / 0.95;        } else {          bTakeoffPos = false;          //cout << "Rated Boost!!\n";          T = 1.0;        }      }      // Boost the manifold pressure.      double boost_factor = BoostMul[BoostSpeed] * suction_loss * RPM/RatedRPM[BoostSpeed];      if (boost_factor < 1.0) boost_factor = 1.0;  // boost will never reduce the MAP      MAP *= boost_factor;      // Now clip the manifold pressure to BCV or Wastegate setting.      if(bTakeoffPos) {        if(MAP > TakeoffMAP[BoostSpeed]) {          MAP = TakeoffMAP[BoostSpeed];        }      } else {        if(MAP > RatedMAP[BoostSpeed]) {          MAP = RatedMAP[BoostSpeed];        }      }    }  // And set the value in American units as well  ManifoldPressure_inHg = MAP / inhgtopa;}//%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%/** * Calculate the air flow through the engine. * Also calculates ambient air density * (used in CHT calculation for air-cooled engines). * * Inputs: p_amb, R_air, T_amb, MAP, Displacement, *   RPM, volumetric_efficiency, ThrottlePos * * TODO: Model inlet manifold air temperature. * * Outputs: rho_air, m_dot_air */void FGPiston::doAirFlow(void){  rho_air = p_amb / (R_air * T_amb);  double displacement_SI = Displacement * in3tom3;  double swept_volume = (displacement_SI * (RPM/60)) / 2;  double v_dot_air = swept_volume * volumetric_efficiency * suction_loss;  double rho_air_manifold = MAP / (R_air * T_amb);  m_dot_air = v_dot_air * rho_air_manifold;}//%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%/** * Calculate the fuel flow into the engine. * * Inputs: Mixture, thi_sea_level, p_amb_sea_level, p_amb, m_dot_air * * Outputs: equivalence_ratio, m_dot_fuel */void FGPiston::doFuelFlow(void){  double thi_sea_level = 1.3 * Mixture; // Allows an AFR of infinity:1 to 11.3075:1  equivalence_ratio = thi_sea_level * 101325.0 / p_amb;

⌨️ 快捷键说明

复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?