Beispiel #1
0
void FGRocket::Calculate(void)
{
  if (FDMExec->IntegrationSuspended()) return;

  RunPreFunctions();

  PropellantFlowRate = (FuelExpended + OxidizerExpended)/in.TotalDeltaT;
  TotalPropellantExpended += FuelExpended + OxidizerExpended;
  // If Isp has been specified as a function, override the value of Isp to that, otherwise
  // assume a constant value is given.
  if (isp_function) Isp = isp_function->GetValue();

  // If there is a thrust table, it is a function of propellant burned. The
  // engine is started when the throttle is advanced to 1.0. After that, it
  // burns without regard to throttle setting.

  if (ThrustTable != 0L) { // Thrust table given -> Solid fuel used

    if ((in.ThrottlePos[EngineNumber] == 1 || BurnTime > 0.0 ) && !Starved) {

      VacThrust = ThrustTable->GetValue(TotalPropellantExpended)
                * (ThrustVariation + 1)
                * (TotalIspVariation + 1);
      if (BurnTime <= BuildupTime && BuildupTime > 0.0) {
        VacThrust *= sin((BurnTime/BuildupTime)*M_PI/2.0);
        // VacThrust *= (1-cos((BurnTime/BuildupTime)*M_PI))/2.0; // 1 - cos approach
      }
      BurnTime += in.TotalDeltaT; // Increment burn time
    } else {
      VacThrust = 0.0;
    }

  } else { // liquid fueled rocket assumed

    if (in.ThrottlePos[EngineNumber] < MinThrottle || Starved) { // Combustion not supported

      PctPower = 0.0; // desired thrust
      Flameout = true;
      VacThrust = 0.0;

    } else { // Calculate thrust

      // PctPower = Throttle / MaxThrottle; // Min and MaxThrottle range from 0.0 to 1.0, normally.
      
      PctPower = in.ThrottlePos[EngineNumber];
      Flameout = false;
      VacThrust = Isp * PropellantFlowRate;

    }

  } // End thrust calculations

  LoadThrusterInputs();
  It += Thruster->Calculate(VacThrust) * in.TotalDeltaT;
  ItVac += VacThrust * in.TotalDeltaT;

  RunPostFunctions();
}
Beispiel #2
0
void FGPiston::Calculate(void)
{
  // Input values.

  p_amb = in.Pressure * psftopa;
  double p = in.TotalPressure * psftopa;
  p_ram = (p - p_amb) * Ram_Air_Factor + p_amb;
  T_amb = RankineToKelvin(in.Temperature);

  RunPreFunctions();

  TotalDeltaT = ( in.TotalDeltaT < 1e-9 ) ? 1.0 : in.TotalDeltaT;

/* The thruster controls the engine RPM because it encapsulates the gear ratio and other transmission variables */
  RPM = Thruster->GetEngineRPM();

  MeanPistonSpeed_fps =  ( RPM * Stroke) / (360); // AKA 2 * (RPM/60) * ( Stroke / 12) or 2NS

  IAS = in.Vc;

  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 (IndicatedHorsePower < 0.1250) Running = false;

  doEGT();
  doCHT();
  doOilTemperature();
  doOilPressure();

  if (Thruster->GetType() == FGThruster::ttPropeller) {
    ((FGPropeller*)Thruster)->SetAdvance(in.PropAdvance[EngineNumber]);
    ((FGPropeller*)Thruster)->SetFeather(in.PropFeather[EngineNumber]);
  }

  LoadThrusterInputs();
  Thruster->Calculate(HP * hptoftlbssec);

  RunPostFunctions();
}
Beispiel #3
0
void FGElectric::Calculate(void)
{
  RunPreFunctions();

  if (Thruster->GetType() == FGThruster::ttPropeller) {
    ((FGPropeller*)Thruster)->SetAdvance(in.PropAdvance[EngineNumber]);
    ((FGPropeller*)Thruster)->SetFeather(in.PropFeather[EngineNumber]);
  } 

  RPM = Thruster->GetRPM() * Thruster->GetGearRatio();

  HP = PowerWatts * in.ThrottlePos[EngineNumber] / hptowatts;
  
  LoadThrusterInputs();
  Thruster->Calculate(HP * hptoftlbssec);

  RunPostFunctions();
}
Beispiel #4
0
void FGTurboProp::Calculate(void)
{
  RunPreFunctions();

  TAT = in.TAT_c;

  ThrottlePos = in.ThrottlePos[EngineNumber];

/* The thruster controls the engine RPM because it encapsulates the gear ratio and other transmission variables */
  RPM = Thruster->GetEngineRPM();
  if (thrusterType == FGThruster::ttPropeller) {
    ((FGPropeller*)Thruster)->SetAdvance(in.PropAdvance[EngineNumber]);
    ((FGPropeller*)Thruster)->SetFeather(in.PropFeather[EngineNumber]);
    ((FGPropeller*)Thruster)->SetReverse(Reversed);
    if (Reversed) {
      ((FGPropeller*)Thruster)->SetReverseCoef(ThrottlePos);
    } else {
      ((FGPropeller*)Thruster)->SetReverseCoef(0.0);
    }

    if (Reversed) {
      if (ThrottlePos < BetaRangeThrottleEnd) {
          ThrottlePos = 0.0;  // idle when in Beta-range
      } else {
        // when reversed:
        ThrottlePos = (ThrottlePos-BetaRangeThrottleEnd)/(1-BetaRangeThrottleEnd) * ReverseMaxPower;
      }
    }
  }

  // When trimming is finished check if user wants engine OFF or RUNNING
  if ((phase == tpTrim) && (in.TotalDeltaT > 0)) {
    if (Running && !Starved) {
      phase = tpRun;
      N2 = IdleN2;
      N1 = IdleN1;
      OilTemp_degK = 366.0;
      Cutoff = false;
    } else {
      phase = tpOff;
      Cutoff = true;
      Eng_ITT_degC = TAT;
      Eng_Temperature = TAT;
      OilTemp_degK = TAT+273.15;
    }
  }

  if (!Running && Starter) {
    if (phase == tpOff) {
      phase = tpSpinUp;
      if (StartTime < 0) StartTime=0;
    }
  }
  if (!Running && !Cutoff && (N1 > 15.0)) {
    phase = tpStart;
    StartTime = -1;
  }
  if (Cutoff && (phase != tpSpinUp)) phase = tpOff;
  if (in.TotalDeltaT == 0) phase = tpTrim;
  if (Starved) phase = tpOff;
  if (Condition >= 10) {
    phase = tpOff;
    StartTime=-1;
  }

  // limiter intervention wanted?
  if (Ielu_max_torque > 0.0) {
    double torque = 0.0;
    
    if (thrusterType == FGThruster::ttPropeller) {
      torque = ((FGPropeller*)(Thruster))->GetTorque();
    } else if (thrusterType == FGThruster::ttRotor) {
      torque = ((FGRotor*)(Thruster))->GetTorque();
    }

    if (Condition < 1) {
      if ( abs(torque) > Ielu_max_torque && ThrottlePos >= OldThrottle ) {
        ThrottlePos = OldThrottle - 0.1 * in.TotalDeltaT; //IELU down
        Ielu_intervent = true;
      } else if ( Ielu_intervent && ThrottlePos >= OldThrottle) {
        ThrottlePos = OldThrottle + 0.05 * in.TotalDeltaT; //IELU up
        Ielu_intervent = true;
      } else {
        Ielu_intervent = false;
      }
    } else {
      Ielu_intervent = false;
    }
    OldThrottle = ThrottlePos;
  }

  switch (phase) {
    case tpOff:    HP = Off(); break;
    case tpRun:    HP = Run(); break;
    case tpSpinUp: HP = SpinUp(); break;
    case tpStart:  HP = Start(); break;
    default: HP = 0;
  }
 
  LoadThrusterInputs();
  Thruster->Calculate(HP * hptoftlbssec);

  RunPostFunctions();
}