diff --git a/ascent.ks b/ascent.ks index dada18f..949d427 100644 --- a/ascent.ks +++ b/ascent.ks @@ -1,5 +1,7 @@ // Inital gravity turn +// #include staging run once staging. +// #include maneuver run once maneuver. function doAscentSteering { @@ -10,6 +12,7 @@ function doAscentSteering { lock steering to tarSteer. until ship:velocity:surface:mag >= 100 { set tarSteer to heading(heading, 90 - (ship:velocity:surface:mag / 10)). + if defined UPDATE_LOG { UPDATE_LOG(). } wait 0. } @@ -53,13 +56,18 @@ function basicAscent { doAscentSteering(heading). // coast to apoapsis - wait until ship:apoapsis >= targetAltitude. + until ship:apoapsis >= targetAltitude { + if defined UPDATE_LOG { UPDATE_LOG(). } + } lock steering to ship:prograde. lock throttle to 0. // don't do futher calcs until out of the atmosphere or very close to apoapsis - wait until ship:altitude >= body:atm:height or eta:apoapsis < 60. + until ship:altitude >= body:atm:height or eta:apoapsis < 60 { + if defined UPDATE_LOG { UPDATE_LOG(). } + } executeNode(createCircularizationNode()). + print "Circularized". } \ No newline at end of file diff --git a/boot/boot.ks b/boot/boot.ks index e98fc2b..2536d0c 100644 --- a/boot/boot.ks +++ b/boot/boot.ks @@ -1,11 +1,52 @@ copyPath("0:/ascent.ks", "1:/ascent.ks"). copyPath("0:/maneuver.ks", "1:/maneuver.ks"). copyPath("0:/staging.ks", "1:/staging.ks"). +copyPath("0:/logger.ks", "1:/logger.ks"). +// #include logger +run once logger. +// #include ascent run once ascent. +createDir("1:/logs"). +set LOG to loggerCreate( + "1:/logs/flight-" + ship:shipName + "-" + time:full + ".json", + list( + "time", + "altitude", + "apoapsis", + "periapsis", + "eccentricity", + "throttle", + "pitch", + "heading", + "mass", + "stageNum" + ), + 1.0 +). +set LOG_DATA to { + return list( + time:seconds, + round(ship:altitude, 1), + round(ship:apoapsis, 1), + round(ship:periapsis, 1), + round(ship:orbit:eccentricity, 4), + round(ship:throttle, 3), + round(ship:pitch, 2), + round(ship:heading, 2), + round(ship:mass, 3), + stage:number + ). +}. + +function UPDATE_LOG { + loggerUpdate(LOG, LOG_DATA()). +} + wait until ship:unpacked. core:part:getmodule("kOSProcessor"):doevent("Open Terminal"). basicAscent(90, 80000). -core:part:getmodule("kOSProcessor"):doevent("Close Terminal"). \ No newline at end of file +core:part:getmodule("kOSProcessor"):doevent("Close Terminal"). +loggerFlush(LOG). \ No newline at end of file diff --git a/logger.ks b/logger.ks new file mode 100644 index 0000000..e8bf3af --- /dev/null +++ b/logger.ks @@ -0,0 +1,84 @@ +// ═══════════════════════════════════════════════════════════ +// logger.ks +// CSV logger with buffered writes. +// +// Usage: +// local log to loggerCreate("0:/logs/flight.csv", list("time", "altitude", "apoapsis")). +// loggerUpdate(log, list(time:seconds, altitude, apoapsis)). +// loggerFlush(log). // call at end of script to flush remaining buffer +// ═══════════════════════════════════════════════════════════ + +// ── Creates a logger and writes the CSV header. +// Parameters: +// filePath : string — destination path, e.g. "0:/logs/flight.csv" +// columns : list — ordered list of column name strings +// flushPeriod : scalar — seconds between buffer flushes (default 1.0) +// Returns a logger lexicon to be passed to loggerUpdate / loggerFlush. +function loggerCreate { + parameter filePath. + parameter columns. + parameter flushPeriod is 1.0. + + // Create or overwrite the file and write the header row + local f to open(filePath). + f:clear(). + f:writeln(_loggerFormatRow(columns)). + + local logger to lexicon( + "file", f, + "columns", columns, + "buffer", list(), + "flushPeriod", flushPeriod, + "lastFlush", time:seconds + ). + + return logger. +} + +// ── Appends a data row to the buffer. +// Values must be in the same order as the columns list passed to loggerCreate. +// Flushes the buffer to disk if the flush period has elapsed. +function loggerUpdate { + parameter logger. + parameter values. + + logger["buffer"]:add(_loggerFormatRow(values)). + + if time:seconds - logger["lastFlush"] >= logger["flushPeriod"] { + loggerFlush(logger). + } +} + +// ── Flushes all buffered rows to disk immediately. +// Call at the end of a script to ensure no data is lost. +function loggerFlush { + parameter logger. + + local f to logger["file"]. + local buf to logger["buffer"]. + + local i to 0. + until i >= buf:length { + f:writeln(buf[i]). + set i to i + 1. + } + + buf:clear(). + set logger["lastFlush"] to time:seconds. +} + +// ── Formats a list of values as a CSV row string. +function _loggerFormatRow { + parameter values. + + local row to "". + local i to 0. + + until i >= values:length { + if i > 0 { set row to row + ",". } + set row to row + values[i]. + set i to i + 1. + } + + return row. +} \ No newline at end of file diff --git a/maneuver.ks b/maneuver.ks index 2323e61..5422085 100644 --- a/maneuver.ks +++ b/maneuver.ks @@ -1,3 +1,12 @@ +// ═══════════════════════════════════════════════════════════ +// maneuver.ks +// Utility functions related to maneuvers. +// +// Usage: +// executeNode(nd: node) +// ═══════════════════════════════════════════════════════════ + +// #include staging run once staging. function executeNode { @@ -59,6 +68,7 @@ function executeNode { lock throttle to min(1, dvLive:mag / maxAcc). } + if defined UPDATE_LOG { UPDATE_LOG(). } wait 0. } diff --git a/staging.ks b/staging.ks index 63bfc85..f6e8803 100644 --- a/staging.ks +++ b/staging.ks @@ -1,3 +1,12 @@ +// ═══════════════════════════════════════════════════════════ +// staging.ks +// Utility functions related to staging and the effects of changing stages +// +// Usage: +// basicStaging() +// calcBurnTime(dvNeeded: scalar) +// ═══════════════════════════════════════════════════════════ + declare function basicStaging { when ship:maxThrust = 0 then {