import("library/lib_math"). declare function WaitForEngineStart{ wait until AnyEngineActive(). } declare function GetDrag{ parameter localGravity. return ship:sensors:acc:mag + localGravity. } declare function GetDragDir{ parameter localGravity. parameter dir. return vDot(ship:sensors:acc, dir) + localGravity. } declare function AnyEngineActive{ list engines in allEngines. for eng in allEngines{ if eng:ignition { return true. } } return false. } declare function GetIsp{ LIST ENGINES IN allEngines. declare local totalThrust is ship:maxThrust. local sum is 0. local weights is 0. for eng in allEngines{ if eng:IGNITION and not eng:flameout{ local w is eng:AVAILABLETHRUST / totalThrust. local ispW is eng:isp * w. set sum to sum + ispW. set weights to weights + w. } } return sum / weights. } declare function GetIspForStage{ parameter engineState. parameter pressure is 0. LIST ENGINES IN allEngines. local totalThrust is GetThrustOfStage(engineState). local sum is 0. local weights is 0. for eng in allEngines{ if eng:stage = engineState { local w is eng:POSSIBLETHRUST / totalThrust. local ispW is eng:ispat(pressure) * w. set sum to sum + ispW. set weights to weights + w. } } return sum / weights. } declare function GetMaxMassFlow{ LIST ENGINES IN allEngines. local sum is 0. for eng in allEngines{ if eng:IGNITION and not eng:flameout{ set sum to sum + eng:maxmassflow. } } return sum. } declare function CalculateSuicideBurnDuration { parameter isp. return CalculateBurnDuration(verticalSpeed, isp, ship:mass, GetMaxMassFlow() * 1000). } declare function CalculateBurnDuration { parameter dv. parameter burnIsp. parameter initialMass. parameter massFlow. set dv to abs(dv). local exp is -dv / (burnIsp * constant:g0). local massRatio is ApproximateExp(-exp). local finalMass is initialMass / massRatio. local fuelUsed is initialMass - finalMass. if massFlow <= 0{ return 0. } return fuelUsed / massFlow. } declare function CalculateSuicideBurnAltitude { parameter vertSpeed. parameter localGravity. parameter tgtAltitude is 0.0. parameter drag is 0.0. local vertAcc is CalculateAverageDecceleration(localGravity, drag). local burnAltitude is ((vertSpeed^2) / (2 * (vertAcc))). return burnAltitude + tgtAltitude. } declare function CalculateAverageDecceleration{ parameter localGravity. parameter drag is 0. local maxVertAcc is (ship:availablethrust / ship:mass) - localGravity. return maxVertAcc + drag. } declare function GetLocalGravity{ parameter curAltitude is -1. if curAltitude = -1 { set curAltitude to altitude. } return body:mu / (curAltitude + body:radius)^2. } declare function CalculateTimeToImpact{ parameter vertSpeed. parameter curAltitude. parameter gravity. parameter tgtAltitude is 0.0. if gravity <= 0 or curAltitude <= 0{ print "[warn]: invalid altitude or gravity.". return 0.0. } local vs is abs(vertSpeed). local g is gravity. local hRel is curAltitude - tgtAltitude. local disc is ((vs^2) + (2 * g * hRel)). return (vs + sqrt(disc)) / g. } function CalculateMultiStageBurnDuration{ parameter dv. if ship:deltav:current >= dv { print "one stage" at (0, 5). return GetBurnTime(dv, ship:maxthrust, ship:mass). }else{ print "multi stage" at (0, 5). local burnTime is 0. local remDv is dv. from {local s is ship:stagenum. } until s = 0 step { set s to s-1.} do { if remDv <= 0 { return burnTime. } local cdv is ship:stagedeltav(s):current. local cmass is GetMassOfStage(s). local cthrust is GetThrustOfStage(s). local cisp is GetIspForStage(s). if cdv >= remDv { set burnTime to burnTime + GetBurnTime(remDv, cmass, cthrust, cisp). }else{ set burnTime to burnTime + GetBurnTime(cdv, cmass, cthrust, cisp). } set remDv to remDv - cdv. } return burnTime. } } // Burn time from rocket equation function GetBurnTime { parameter deltaV. parameter stagethrust is 0. parameter stagemass is 0. parameter isp is 0. if deltaV:typename() = "Vector" { set deltaV to deltaV:mag. } if isp = 0 { set isp to GetIsp(). } if stagethrust = 0 { set stagethrust to ship:thrust. } if stagemass = 0 { set stagemass to ship:mass. } local burnTime is -1. if stagethrust <> 0 { set burnTime to stagemass * (1 - CONSTANT:E ^ (-deltaV / isp)) / (stagethrust / isp). } return burnTime. } function GetThrustOfStage { parameter st. local totalThrust is 0. LIST ENGINES IN allEngines. for eng in allEngines{ if eng:stage = st { set totalThrust to totalThrust + eng:POSSIBLETHRUST. } } return totalThrust. } function GetMassOfStage { parameter st. local total is 0. LIST PARTS IN allP. for p in allP { if p:stage <= st { set total to total + p:mass. } } return total. }