Скрипт почти всегда начинается с вопроса «а где я сейчас и что у меня на борту». В kOS ответ даёт суффикс — обращение через двоеточие: SHIP:ALTITUDE, SHIP:ORBIT:PERIAPSIS. Здесь собрано то, чем реально пользуешься при написании миссии, сгруппированное по задачам, а не по внутренним классам мода.
Всё ниже проверено на сборке «Оператор» в живых полётах. Полный перечень со всеми редкими суффиксами — в официальной документации kOS; она на английском, и это не перевод, а выжимка нужного с нашими примерами.
Где я сейчас
| Что спрашиваем | Как | Что вернёт |
|---|---|---|
| Высота над уровнем моря | SHIP:ALTITUDE |
метры |
| Высота над поверхностью | ALT:RADAR |
метры, важна на посадке |
| Скорость по орбите | SHIP:VELOCITY:ORBIT |
вектор |
| Скорость относительно поверхности | SHIP:VELOCITY:SURFACE |
вектор |
| Координаты | SHIP:GEOPOSITION:LAT, :LNG |
градусы |
| Небесное тело, вокруг которого летим | SHIP:BODY |
объект Body |
| Куда «вверх» и «на север» | SHIP:UP, SHIP:NORTH |
направления |
| Состояние аппарата | SHIP:STATUS |
PRELAUNCH, FLYING, ORBITING, LANDED… |
Скорость — это вектор, а не число. Длину берём через :MAG:
PRINT "скорость по орбите: " + ROUND(SHIP:VELOCITY:ORBIT:MAG) + " м/с".
Граница атмосферы у тела своя, зашивать 70 000 в скрипт не надо:
IF SHIP:ALTITUDE > SHIP:BODY:ATM:HEIGHT { PRINT "вышли из атмосферы". }
Какая у меня орбита
Всё это живёт в SHIP:ORBIT (сокращённо OBT):
| Суффикс | Что это |
|---|---|
APOAPSIS, PERIAPSIS |
апоцентр и перицентр, метры над поверхностью |
INCLINATION |
наклонение, градусы |
LAN |
долгота восходящего узла |
ARGUMENTOFPERIAPSIS |
аргумент перицентра |
TRUEANOMALY |
истинная аномалия — где мы на витке прямо сейчас |
ECCENTRICITY |
эксцентриситет: 0 — круг |
PERIOD |
период обращения, секунды |
SEMIMAJORAXIS |
большая полуось, метры от центра тела |
ETA:APOAPSIS, ETA:PERIAPSIS |
сколько секунд до точки |
TRANSITION |
что случится дальше: ESCAPE, ENCOUNTER, FINAL |
Грабля на ровном месте. APOAPSIS считается от поверхности, а SEMIMAJORAXIS — от центра тела. Смешаешь в одной формуле — получишь ошибку в радиус планеты, шестьсот километров на Кербине. Радиус берётся как SHIP:BODY:RADIUS.
Проверка, что мы там, куда целились:
LOCAL ok IS ABS(OBT:APOAPSIS - tgtAp) / tgtAp < 0.1. // контракты обычно дают 10%
Что у меня на борту
Список деталей — SHIP:PARTS. У каждой детали:
| Суффикс | Что это |
|---|---|
NAME |
внутреннее имя, по нему ищут |
TITLE |
подпись из игры, на русском в нашей сборке |
TAG |
метка, которую ты сам поставил детали в ангаре |
STAGE |
в какой ступени отделяется |
MODULES |
список имён модулей детали |
GETMODULEBYINDEX(i) |
сам модуль по номеру |
RESOURCES |
что в ней налито |
Метка TAG — самый надёжный способ найти нужную деталь: имена меняются от версии к версии, а метку ставишь ты сам.
FOR p IN SHIP:PARTS {
IF p:TAG = "антенна-дальняя" { PRINT p:TITLE. }
}
Грабля, которая стоила нам полёта. p:GETMODULE("ModuleScienceExperiment") возвращает только первый подходящий модуль. У мачты CA-AMA научных модулей два, и половина приборов молча не срабатывала. Правильно — перебирать по индексу:
LOCAL i IS 0.
UNTIL i >= p:MODULES:LENGTH {
IF p:MODULES[i] = "ModuleScienceExperiment" {
LOCAL m IS p:GETMODULEBYINDEX(i).
// …работаем с m
}
SET i TO i + 1.
}
Наука
Научный модуль умеет:
| Обращение | Смысл |
|---|---|
m:DEPLOY() |
снять показания |
m:HASDATA |
есть ли неотправленные данные |
m:DATA |
список замеров |
m:TRANSMIT() |
передать по антенне |
m:DUMP() |
выбросить |
m:RERUNNABLE |
можно ли повторить прибор |
m:INOPERABLE |
прибор израсходован |
У каждого замера есть TITLE, SCIENCEVALUE (сколько даст при возврате) и TRANSMITVALUE (сколько дойдёт по радио). Разница между ними и есть причина, по которой одни эксперименты возят домой, а другие передают сразу.
Не отправлять пустышки — одна проверка:
LOCAL worth IS 0.
FOR d IN m:DATA { SET worth TO worth + d:TRANSMITVALUE. }
IF worth >= 0.1 { m:TRANSMIT(). } ELSE { m:DUMP(). }
Передача раскрывает антенну. Складная антенна разворачивается автоматически, когда через неё идут данные. Передашь науку на подъёме — раскроешь её в набегающий поток и оторвёшь. В атмосфере только собираем, передаём в вакууме: разбор в Частые проблемы.
Двигатели, топливо, масса
| Что | Как |
|---|---|
| Полная тяга | SHIP:MAXTHRUST |
| Доступная сейчас | SHIP:AVAILABLETHRUST |
| Масса | SHIP:MASS (тонны) |
| Сухая масса | SHIP:DRYMASS |
| Остаток ресурса | SHIP:RESOURCES или STAGE:LIQUIDFUEL |
Тяговооружённость считается через ускорение свободного падения у текущего тела и на текущей высоте, а не через 9,81:
LOCAL g IS SHIP:BODY:MU / (SHIP:BODY:RADIUS + SHIP:ALTITUDE)^2.
LOCAL twr IS SHIP:AVAILABLETHRUST / (SHIP:MASS * g).
Про автостейджинг. Считать топливо в ступени — ненадёжно: у твердотопливных и у сборок с общим баком счёт врёт. Мы пришли к простому признаку: отделяем, когда не осталось ни одного работающего двигателя. Разбор — в kOS: библиотека модулей.
Время
| Что | Как |
|---|---|
| Секунды с начала игры | TIME:SECONDS |
| Дата в игре | TIME:CALENDAR |
| Разгон времени | KUNIVERSE:TIMEWARP:WARP, :CANCELWARP() |
| Подождать до момента | WAIT UNTIL TIME:SECONDS > t |
Грабля с ожиданием. Ждать по модульной величине (вроде «пока разница долгот меньше трёх градусов») нельзя: значение может уже подходить в момент проверки, и ожидание закончится мгновенно. Считаем абсолютный момент времени и ждём его:
LOCAL tgtUT IS TIME:SECONDS + waitSeconds.
WAIT UNTIL TIME:SECONDS >= tgtUT.
Управление
| Что | Как |
|---|---|
| Курс | LOCK STEERING TO … |
| Газ | LOCK THROTTLE TO … |
| Автопилот SAS | SAS ON. / SAS OFF. |
| Двигатели ориентации | RCS ON. |
| Панели, шасси, свет | PANELS ON., GEAR ON., LIGHTS ON. |
| Отделить ступень | STAGE. |
LOCK — это не присваивание, а живая связь: выражение пересчитывается каждый кадр. SET вычисляет один раз. Перепутать — значит рулить по значению, устаревшему на минуту.
Чего не стоит делать
- Не занимай имена встроенных функций.
R,V,Q,ALT,PATH,TIME,NODE,STAGE,CONFIG,THROTTLE— всё это уже занято.PARAMETER altне скомпилируется, и узнаешь ты об этом на стартовом столе. Список и способ проверить до пуска — в kOS: отладка и лимиты. - Не забывай
WAIT 0.в цикле. Цикл без ожидания съедает бюджет инструкций и вешает корабль. - Не жди осмысленных чисел от узла, который не добавлен. Пока манёвр не добавлен в план (
ADD nd.), у него нельзя спросить:DELTAV— kOS ответит ошибкой прямо в полёте.
Готовые модули, где всё это уже собрано в рабочие блоки, — kOS: библиотека модулей. Разбор ошибок из живых запусков — Скрипт вывода на орбиту: разбор ошибок и kOS: отладка и лимиты.