From a8de43efa6e0e6af8a90309f398a9569927cd2d6 Mon Sep 17 00:00:00 2001 From: "Casper V. Kristensen" Date: Thu, 19 Jul 2018 14:42:03 +0200 Subject: [PATCH] First commit --- autopilot/boot/default.ks | 5 +++ autopilot/launch.ks | 82 +++++++++++++++++++++++++++++++++++++++ autopilot/node.ks | 72 ++++++++++++++++++++++++++++++++++ autopilot/test.ks | 3 ++ autopilot/util.ks | 11 ++++++ autopilot/vectors.ks | 43 ++++++++++++++++++++ 6 files changed, 216 insertions(+) create mode 100755 autopilot/boot/default.ks create mode 100755 autopilot/launch.ks create mode 100755 autopilot/node.ks create mode 100755 autopilot/test.ks create mode 100755 autopilot/util.ks create mode 100755 autopilot/vectors.ks diff --git a/autopilot/boot/default.ks b/autopilot/boot/default.ks new file mode 100755 index 0000000..90ebf22 --- /dev/null +++ b/autopilot/boot/default.ks @@ -0,0 +1,5 @@ +CLEARSCREEN. +print "=================== BOOTING ===================". +switch to 0. + +print "============= BOOT SEQUENCE COMPLETE =============". \ No newline at end of file diff --git a/autopilot/launch.ks b/autopilot/launch.ks new file mode 100755 index 0000000..1865524 --- /dev/null +++ b/autopilot/launch.ks @@ -0,0 +1,82 @@ +run once util. +run once vectors. +run once node. + +print "====================== LAUNCHING ======================". + +parameter orbit_height is 100_000. +parameter pitchover_tilt is 20. +parameter pitchover_altitude is 1000. +parameter pitchover_velocity is 100. + + +// Auto-stage when the stage has no solid- and liquid fuel left +when (STAGE:SOLIDFUEL + STAGE:LIQUIDFUEL < 1) and STAGE:READY then { + print "STAGING (zero fuel)". + STAGE. + return true. // preserve trigger +} + +// Automatically deploy solar panels at 0 atmosphere +when SHIP:DYNAMICPRESSURE = 0 then { + print "Deploying solar panels (zero pressure)". + PANELS ON. +} + +// Disable engine gimbal when engine is off +on (not THROTTLE) { // using not to cast to boolean + list engines in engines_list. + for engine in engines_list { + if engine:HASGIMBAL set engine:GIMBAL:LOCK to not THROTTLE. + } + return true. // preserve trigger +} + + +// VERTICAL CLIMB + +print "VERTICAL CLIMB to " + pitchover_altitude + "m or " + pitchover_velocity + "m/s". +SAS OFF. +set NAVMODE to "SURFACE". +lock THROTTLE to 1.0. +lock STEERING to HEADING(90,90). + +// Once a certain altitude is reached, a slight turn is made, called the pitchover maneuver +wait until SHIP:ALTITUDE > pitchover_altitude + or SHIP:VELOCITY:SURFACE:MAG > pitchover_velocity. + + +// PITCHOVER MANEUVER + +print "PITCHOVER by " + pitchover_tilt + "°". +lock STEERING to HEADING(90,90-pitchover_tilt). + +wait until actual_prograde_pitch() > pitchover_tilt. + + +// GRAVITY TURN + +print "GRAVITY TURN". +lock STEERING to HEADING(90, 90-actual_prograde_pitch()). // follow prograde to get 0 deg angle of attack, but force compass heading 90 (east) + +wait until APOAPSIS > orbit_height. +lock THROTTLE TO 0. +unlock STEERING. + + +// CREATE AND EXECUTE CIRCULARIZATION MANEUVER NODE +create_circularization_node(). +execute_node(). + + +// EPILOGUE + +// Ensure that the throttle will be 0 when execution stops +set SHIP:CONTROL:PILOTMAINTHROTTLE to 0. + +// Ensure that the player is not locked out of control. +set SHIP:CONTROL:NEUTRALIZE to true. +unlock STEERING. +unlock THROTTLE. + +print "====================== LAUNCH SEQUENCE COMPLETE ======================". \ No newline at end of file diff --git a/autopilot/node.ks b/autopilot/node.ks new file mode 100755 index 0000000..eb67388 --- /dev/null +++ b/autopilot/node.ks @@ -0,0 +1,72 @@ +run once util. + +function execute_node { + parameter node is NEXTNODE. + + print "EXECUTE MANEUVER NODE". + + // Calculate estimated burn time + // https://en.wikipedia.org/wiki/Tsiolkovsky_rocket_equation + // https://space.stackexchange.com/questions/27375/how-do-i-calculate-a-rockets-burn-time-from-required-velocity + local isp_sum is 0. + list ENGINES in engines_list. + for engine in engines_list { + if engine:STAGE = STAGE:NUMBER set ISP_sum to ISP_sum + engine:VISP. + } + + local ve is ISP_sum * (CONSTANT:G * KERBIN:MASS). // exhaust velocity + local burn_time is ((SHIP:MASS * ve) / SHIP:MAXTHRUST) * (1 - CONSTANT:E^(-node:BURNVECTOR:MAG/ve)). + + print "Estimated burn time: " + ROUND(burn_time). + + print "Aligning ship with burn vector". + SAS OFF. + lock STEERING to node:BURNVECTOR. + wait until VANG(SHIP:FACING:VECTOR, node:BURNVECTOR) < 0.1. + + print "Initializing warp". + unlock STEERING. // TODO: Doesnt work? + warp_for(MAX(0, node:ETA - (burn_time/2) - 5)). // Warp until 5s before node + + print "Approaching". + lock STEERING to node:BURNVECTOR. + wait until node:ETA <= burn_time/2. + + print "Burn!". + lock THROTTLE to 1.0. + + //throttle is 100% until there is less than 1 second of time left to burn + //when there is less than 1 second - decrease the throttle linearly + // TODO: Smooth at the end + wait until node:DELTAV:MAG < 5.0. // TODO + set THROTTLE to 0.0. + + print "DONE! Removing node and unlocking steering". + remove node. + + unlock STEERING. + unlock THROTTLE. + SET SHIP:CONTROL:PILOTMAINTHROTTLE TO 0. +} + + +function create_circularization_node { + // parameter where. + + print "CREATE CIRCULARIZATION NODE". + + local node is NODE(TIME:SECONDS + ETA:APOAPSIS, 0, 0, 0). + add node. + + // Calculate required velocity to acheive orbit at altitude equal to apoapsis + // https://en.wikipedia.org/wiki/Orbital_speed#Mean_orbital_speed + local orbital_speed is SQRT((CONSTANT:G * ORBIT:BODY:MASS) / (ORBIT:BODY:RADIUS + APOAPSIS)). + + // Calculate the difference between the required velocity and our velocity at apoapsis + set node:PROGRADE to orbital_speed - VELOCITYAT(SHIP, TIME:SECONDS + ETA:APOAPSIS):ORBIT:MAG. +} + + +function create_orbitchange_node { + parameter what. +} \ No newline at end of file diff --git a/autopilot/test.ks b/autopilot/test.ks new file mode 100755 index 0000000..1d72380 --- /dev/null +++ b/autopilot/test.ks @@ -0,0 +1,3 @@ +print "TEST". + +run once vectors. diff --git a/autopilot/util.ks b/autopilot/util.ks new file mode 100755 index 0000000..5685b41 --- /dev/null +++ b/autopilot/util.ks @@ -0,0 +1,11 @@ +function warp_to { + parameter timestamp. + + KUNIVERSE:TIMEWARP:WARPTO(timestamp). // todo: improve. +} + +function warp_for { + parameter seconds. + + return warp_to(TIME:SECONDS + seconds). +} \ No newline at end of file diff --git a/autopilot/vectors.ks b/autopilot/vectors.ks new file mode 100755 index 0000000..311edd4 --- /dev/null +++ b/autopilot/vectors.ks @@ -0,0 +1,43 @@ +// Define actual_prograde, which automatically switches from SHIP:SRFPROGRADE to SHIP:PROGRADE +local function set_actual_prograde { + if NAVMODE = "SURFACE" { + print "Switched actual_prograde to surface SRFPROGRADE". + lock actual_prograde to SHIP:SRFPROGRADE. + } else { + print "Switched actual_prograde to orbit PROGRADE". + lock actual_prograde to SHIP:PROGRADE. + } + return true. // preserve trigger +} +on NAVMODE {return set_actual_prograde().} +set_actual_prograde(). + + +// ANGLES +lock actual_prograde_pitch to VANG(actual_prograde:VECTOR, UP:VECTOR). + + + +// // the following are all vectors, mainly for use in the roll, pitch, and angle of attack calculations +// lock rightrotation to ship:facing*r(0,90,0). +// lock right to rightrotation:vector. //right and left are directly along wings +// lock left to (-1)*right. +// lock up to ship:up:vector. //up and down are skyward and groundward +// lock down to (-1)*up. +// lock fore to ship:facing:vector. //fore and aft point to the nose and tail +// lock aft to (-1)*fore. +// lock righthor to vcrs(up,fore). //right and left horizons +// lock lefthor to (-1)*righthor. +// lock forehor to vcrs(righthor,up). //forward and backward horizons +// lock afthor to (-1)*forehor. +// lock top to vcrs(fore,right). //above the cockpit, through the floor +// lock bottom to (-1)*top. + +// // the following are all angles, useful for control programs +// lock absaoa to vang(fore,srfprograde:vector). //absolute angle of attack +// lock aoa to vang(top,srfprograde:vector)-90. //pitch component of angle of attack +// lock sideslip to vang(right,srfprograde:vector)-90. //yaw component of aoa +// lock rollangle to vang(right,righthor)*((90-vang(top,righthor))/abs(90-vang(top,righthor))). //roll angle, 0 at level flight +// lock pitchangle to vang(fore,forehor)*((90-vang(fore,up))/abs(90-vang(fore,up))). //pitch angle, 0 at level flight +// lock glideslope to vang(srfprograde:vector,forehor)*((90-vang(srfprograde:vector,up))/abs(90-vang(srfprograde:vector,up))). +// lock ascentangle to vang(srfprograde:vector, forehor). //angle of surface prograde above horizon \ No newline at end of file