mirror of
https://github.com/OpenSpace/OpenSpace.git
synced 2026-01-07 04:00:37 -06:00
Merge branch 'feature/osirisrex' of github.com:OpenSpace/OpenSpace into feature/osirisrex
This commit is contained in:
@@ -169,7 +169,7 @@ function postInitialization()
|
||||
openspace.setPropertyValue("OsirisRex.renderable.modelrotation", {90.0, 0.0, 0.0})
|
||||
|
||||
openspace.printInfo("Done setting default values")
|
||||
openspace.loadMission("${OPENSPACE_DATA}/scene/osirisrex/osirisrex/osirisrex.mission")
|
||||
openspace.loadMission("${OPENSPACE_DATA}/scene/osirisrex/osirisrex/spice_kernel_times.mission")
|
||||
|
||||
openspace.resetCameraDirection()
|
||||
end
|
||||
@@ -184,16 +184,16 @@ return {
|
||||
},
|
||||
Modules = {
|
||||
"sun",
|
||||
"mercury",
|
||||
"venus",
|
||||
--"mercury",
|
||||
--"venus",
|
||||
"lodearth",
|
||||
"mars",
|
||||
"saturn",
|
||||
"uranus",
|
||||
"neptune",
|
||||
"stars",
|
||||
--"mars",
|
||||
--"saturn",
|
||||
--"uranus",
|
||||
--"neptune",
|
||||
--"stars",
|
||||
-- "stars-denver",
|
||||
"milkyway",
|
||||
--"milkyway",
|
||||
-- "milkyway-eso",
|
||||
--"imageplane",
|
||||
"osirisrex",
|
||||
|
||||
95
data/scene/osirisrex/osirisrex/spice_kernel_times.mission
Normal file
95
data/scene/osirisrex/osirisrex/spice_kernel_times.mission
Normal file
@@ -0,0 +1,95 @@
|
||||
return
|
||||
{ Name = "Nominal_Observations_Science", Phases = {
|
||||
{ Name = "03_Approach", Phases = {
|
||||
{ Name = "DustSearch_v1", Phases = {
|
||||
{ Name = "Phase03_AP_DustSearch_1.bc", TimeRange = { Start = "2018-SEP-11 21:31:01.183", End = "2018-SEP-12 02:18:41.183" }},
|
||||
}},
|
||||
{ Name = "LightCurve_v1", Phases = {
|
||||
{ Name = "Phase03_AP_LightCurve_1.bc", TimeRange = { Start = "2018-OCT-09 21:50:48.182", End = "2018-OCT-10 02:33:16.183" }},
|
||||
{ Name = "Phase03_AP_LightCurve_2.bc", TimeRange = { Start = "2018-OCT-10 21:50:48.182", End = "2018-OCT-11 02:33:16.183" }},
|
||||
}},
|
||||
{ Name = "NatSatSearch_v1", Phases = {
|
||||
{ Name = "Phase03_AP_SatSearch_1.bc", TimeRange = { Start = "2018-OCT-26 19:38:30.183", End = "2018-OCT-27 00:22:34.183" }},
|
||||
{ Name = "Phase03_AP_SatSearch_2.bc", TimeRange = { Start = "2018-NOV-05 17:10:20.183", End = "2018-NOV-05 21:59:48.183" }},
|
||||
}},
|
||||
{ Name = "PhaseFunction_v1", Phases = {
|
||||
{ Name = "Phase03_AP_PhaseFunction_1.bc", TimeRange = { Start = "2018-OCT-12 21:42:26.183", End = "2018-OCT-13 02:24:54.183" }},
|
||||
}},
|
||||
{ Name = "ShapeModel_v1", Phases = {
|
||||
{ Name = "Phase03_AP_ShapeModel_1.bc", TimeRange = { Start = "2018-NOV-09 11:02:59.183", End = "2018-NOV-09 15:52:27.183" }},
|
||||
{ Name = "Phase03_AP_ShapeModel_2.bc", TimeRange = { Start = "2018-NOV-10 11:02:59.183", End = "2018-NOV-10 15:52:27.183" }},
|
||||
{ Name = "Phase03_AP_ShapeModel_3.bc", TimeRange = { Start = "2018-NOV-11 11:02:59.183", End = "2018-NOV-11 15:52:27.183" }},
|
||||
{ Name = "Phase03_AP_ShapeModel_4.bc", TimeRange = { Start = "2018-NOV-12 11:02:59.183", End = "2018-NOV-12 15:52:27.183" }},
|
||||
{ Name = "Phase03_AP_ShapeModel_5.bc", TimeRange = { Start = "2018-NOV-13 11:02:59.183", End = "2018-NOV-13 15:52:27.183" }},
|
||||
{ Name = "Phase03_AP_ShapeModel_6.bc", TimeRange = { Start = "2018-NOV-14 11:03:53.183", End = "2018-NOV-14 15:51:33.183" }},
|
||||
{ Name = "Phase03_AP_ShapeModel_7.bc", TimeRange = { Start = "2018-NOV-15 11:03:53.183", End = "2018-NOV-15 15:51:33.183" }},
|
||||
{ Name = "Phase03_AP_ShapeModel_8.bc", TimeRange = { Start = "2018-NOV-16 11:03:53.183", End = "2018-NOV-16 15:51:33.183" }},
|
||||
{ Name = "Phase03_AP_ShapeModel_9_Forced4x4.bc", TimeRange = { Start = "2018-NOV-17 11:03:54.183", End = "2018-NOV-17 15:51:34.183" }},
|
||||
}},
|
||||
{ Name = "SpectraMap_v1", Phases = {
|
||||
{ Name = "Phase03_AP_SpectraMap_1.bc", TimeRange = { Start = "2018-OCT-30 20:44:53.183", End = "2018-OCT-31 01:34:21.183" }},
|
||||
}},
|
||||
}},
|
||||
{ Name = "04_PrelimSurvey", Phases = {
|
||||
{ Name = "MapCamOLA_v1", Phases = {
|
||||
{ Name = "Phase04_PS_MC_1_v1_1a.bc", TimeRange = { Start = "2018-NOV-20 01:13:12.183", End = "2018-NOV-20 06:13:04.183" }},
|
||||
{ Name = "Phase04_PS_MC_2_v1_1a.bc", TimeRange = { Start = "2018-NOV-28 01:13:12.183", End = "2018-NOV-28 06:13:04.183" }},
|
||||
}},
|
||||
{ Name = "OLA_v1", Phases = {
|
||||
{ Name = "Phase04_PS_OLA_Nominal_1.bc", TimeRange = { Start = "2018-NOV-19 22:30:00.184", End = "2018-NOV-19 23:19:28.183" }},
|
||||
{ Name = "Phase04_PS_OLA_Nominal_2.bc", TimeRange = { Start = "2018-NOV-23 22:19:34.184", End = "2018-NOV-23 23:19:26.183" }},
|
||||
{ Name = "Phase04_PS_OLA_Nominal_3.bc", TimeRange = { Start = "2018-NOV-24 00:48:38.184", End = "2018-NOV-24 01:38:06.184" }},
|
||||
{ Name = "Phase04_PS_OLA_Nominal_4.bc", TimeRange = { Start = "2018-NOV-27 22:29:58.184", End = "2018-NOV-27 23:19:26.183" }},
|
||||
}},
|
||||
{ Name = "PolyCam_v1", Phases = {
|
||||
{ Name = "Phase04_PS_PolyCam_1.bc", TimeRange = { Start = "2018-NOV-19 12:00:33.183", End = "2018-NOV-19 16:46:25.183" }},
|
||||
{ Name = "Phase04_PS_PolyCam_2.bc", TimeRange = { Start = "2018-NOV-20 07:10:26.183", End = "2018-NOV-20 12:10:18.183" }},
|
||||
{ Name = "Phase04_PS_PolyCam_3.bc", TimeRange = { Start = "2018-NOV-23 11:51:29.184", End = "2018-NOV-23 16:51:21.184" }},
|
||||
{ Name = "Phase04_PS_PolyCam_4.bc", TimeRange = { Start = "2018-NOV-24 07:17:39.184", End = "2018-NOV-24 12:03:31.184" }},
|
||||
{ Name = "Phase04_PS_PolyCam_5.bc", TimeRange = { Start = "2018-NOV-27 12:00:20.184", End = "2018-NOV-27 16:46:12.184" }},
|
||||
{ Name = "Phase04_PS_PolyCam_6.bc", TimeRange = { Start = "2018-NOV-28 07:10:35.183", End = "2018-NOV-28 12:10:27.183" }},
|
||||
}},
|
||||
}},
|
||||
{ Name = "06_DetailedSurvey", Phases = {
|
||||
{ Name = "BaseballDiamond_v2", Phases = {
|
||||
{ Name = "atl_19013_18_BBD1_v2.bc", TimeRange = { Start = "2019-JAN-13 18:59:31.195", End = "2019-JAN-13 23:59:29.179" }},
|
||||
{ Name = "atl_19014_16_BBD2_v2.bc", TimeRange = { Start = "2019-JAN-14 16:56:01.185", End = "2019-JAN-14 21:55:58.219" }},
|
||||
{ Name = "atl_19020_18_BBD3_v2.bc", TimeRange = { Start = "2019-JAN-20 18:59:15.211", End = "2019-JAN-20 23:59:13.195" }},
|
||||
{ Name = "atl_19021_19_BBD4_v2.bc", TimeRange = { Start = "2019-JAN-21 19:26:47.179", End = "2019-JAN-22 00:26:44.213" }},
|
||||
}},
|
||||
{ Name = "EquatorialStations_v1", Phases = {
|
||||
{ Name = "Phase06_DS_Equatorial_Stations_1.bc", TimeRange = { Start = "2019-JAN-27 10:36:24.185", End = "2019-JAN-27 15:20:28.185" }},
|
||||
{ Name = "Phase06_DS_Equatorial_Stations_2.bc", TimeRange = { Start = "2019-FEB-03 10:35:30.185", End = "2019-FEB-03 15:21:22.185" }},
|
||||
{ Name = "Phase06_DS_Equatorial_Stations_3.bc", TimeRange = { Start = "2019-FEB-10 10:51:50.185", End = "2019-FEB-10 15:51:42.185" }},
|
||||
{ Name = "Phase06_DS_Equatorial_Stations_4.bc", TimeRange = { Start = "2019-FEB-17 10:29:11.186", End = "2019-FEB-17 15:29:03.186" }},
|
||||
{ Name = "Phase06_DS_Equatorial_Stations_5.bc", TimeRange = { Start = "2019-FEB-24 10:08:28.186", End = "2019-FEB-24 15:08:20.185" }},
|
||||
{ Name = "Phase06_DS_Equatorial_Stations_6.bc", TimeRange = { Start = "2019-MAR-03 09:52:58.186", End = "2019-MAR-03 14:42:26.186" }},
|
||||
{ Name = "Phase06_DS_Equatorial_Stations_7.bc", TimeRange = { Start = "2019-MAR-10 09:57:47.186", End = "2019-MAR-10 14:36:33.186" }},
|
||||
}},
|
||||
{ Name = "PlumeSearch_v1", Phases = {
|
||||
{ Name = "Phase06_DS_Plume_Search_1.bc", TimeRange = { Start = "2019-JAN-28 10:34:36.185", End = "2019-JAN-28 15:22:16.185" }},
|
||||
{ Name = "Phase06_DS_Plume_Search_2.bc", TimeRange = { Start = "2019-FEB-18 10:29:11.186", End = "2019-FEB-18 15:29:03.186" }},
|
||||
}},
|
||||
}},
|
||||
{ Name = "07_OrbitalB", Phases = {
|
||||
{ Name = "CandidateSampleSite_v1", Phases = {
|
||||
{ Name = "Phase07_OB_CSS_Mapping_1.bc", TimeRange = { Start = "2019-APR-08 10:35:27.186", End = "2019-APR-08 15:22:06.186" }},
|
||||
{ Name = "Phase07_OB_CSS_Mapping_2.bc", TimeRange = { Start = "2019-APR-08 16:16:06.186", End = "2019-APR-11 10:38:58.186" }},
|
||||
{ Name = "Phase07_OB_CSS_Mapping_3.bc", TimeRange = { Start = "2019-APR-22 17:51:23.186", End = "2019-APR-29 19:41:03.186" }},
|
||||
}},
|
||||
}},
|
||||
{ Name = "08_Recon", Phases = {
|
||||
{ Name = "225m_Sortie_v2", Phases = {
|
||||
{ Name = "Recon_225mSortie_Case02_0Latitude.bc", TimeRange = { Start = "2019-MAY-25 03:50:31.195", End = "2019-MAY-25 04:32:17.227" }},
|
||||
{ Name = "Recon_225mSortie_Case05_20negLatitude.bc", TimeRange = { Start = "2019-MAY-25 03:50:48.216", End = "2019-MAY-25 04:37:10.209" }},
|
||||
{ Name = "Recon_225mSortie_Case08_40negLatitude.bc", TimeRange = { Start = "2019-MAY-25 04:02:43.176", End = "2019-MAY-25 04:54:41.179" }},
|
||||
{ Name = "Recon_225mSortie_Case11_60negLatitude.bc", TimeRange = { Start = "2019-MAY-25 04:21:46.161", End = "2019-MAY-25 05:18:44.232" }},
|
||||
}},
|
||||
{ Name = "525m_Sortie_v2", Phases = {
|
||||
{ Name = "Recon_525mSortie_Case02_0Latitude.bc", TimeRange = { Start = "2019-MAY-25 04:06:39.220", End = "2019-MAY-25 04:44:17.198" }},
|
||||
{ Name = "Recon_525mSortie_Case05_20negLatitude.bc", TimeRange = { Start = "2019-MAY-25 04:11:39.201", End = "2019-MAY-25 04:49:37.224" }},
|
||||
{ Name = "Recon_525mSortie_Case05_NominalProfile.bc", TimeRange = { Start = "2019-MAY-25 03:01:50.184", End = "2019-MAY-25 06:38:50.232" }},
|
||||
{ Name = "Recon_525mSortie_Case08_NominalProfile.bc", TimeRange = { Start = "2019-MAY-25 03:01:50.184", End = "2019-MAY-25 06:38:50.232" }},
|
||||
}},
|
||||
}},
|
||||
}}
|
||||
@@ -98,7 +98,33 @@ MissionPhase::MissionPhase(const ghoul::Dictionary& dict) {
|
||||
}
|
||||
};
|
||||
|
||||
std::list<const MissionPhase*> MissionPhase::phaseTrace(double time, int maxDepth) const {
|
||||
std::list<const MissionPhase*> trace;
|
||||
if (_timeRange.includes(time)) {
|
||||
trace.push_back(this);
|
||||
phaseTrace(time, trace, maxDepth);
|
||||
}
|
||||
return std::move(trace);
|
||||
}
|
||||
|
||||
bool MissionPhase::phaseTrace(double time, std::list<const MissionPhase*>& trace, int maxDepth) const {
|
||||
if (maxDepth == 0) {
|
||||
return false;
|
||||
}
|
||||
|
||||
for (int i = 0; i < _subphases.size(); ++i) {
|
||||
if (_subphases[i]._timeRange.includes(time)) {
|
||||
trace.push_back(&_subphases[i]);
|
||||
_subphases[i].phaseTrace(time, trace, maxDepth - 1);
|
||||
return true; // only add the first one
|
||||
}
|
||||
// Since time ranges are sorted we can do early termination
|
||||
else if (_subphases[i]._timeRange.start > time) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -27,6 +27,7 @@
|
||||
|
||||
|
||||
#include <vector>
|
||||
#include <list>
|
||||
#include <string>
|
||||
#include <unordered_map>
|
||||
#include <openspace/util/timerange.h>
|
||||
@@ -64,8 +65,13 @@ public:
|
||||
*/
|
||||
const MissionPhase& phase(size_t i) const { return _subphases[i]; }
|
||||
|
||||
std::list<const MissionPhase*> phaseTrace(double time, int maxDepth = -1) const;
|
||||
|
||||
protected:
|
||||
|
||||
bool phaseTrace(double time, std::list<const MissionPhase*>& trace, int maxDepth) const;
|
||||
|
||||
|
||||
std::string _name;
|
||||
std::string _description;
|
||||
TimeRange _timeRange;
|
||||
|
||||
@@ -1267,12 +1267,12 @@ RenderEngine::RendererImplementation RenderEngine::rendererFromString(const std:
|
||||
|
||||
std::string RenderEngine::progressToStr(int size, double t) {
|
||||
std::string progress = "|";
|
||||
int g = static_cast<int>((t * 24) + 1);
|
||||
int g = static_cast<int>((t * (size - 1)) + 1);
|
||||
g = std::max(g, 0);
|
||||
for (int i = 0; i < g; i++)
|
||||
progress.append("-");
|
||||
progress.append(">");
|
||||
for (int i = 0; i < 25 - g; i++)
|
||||
for (int i = 0; i < size - g; i++)
|
||||
progress.append(" ");
|
||||
progress.append("|");
|
||||
return progress;
|
||||
@@ -1370,60 +1370,75 @@ void RenderEngine::renderInformation() {
|
||||
const Mission& mission = MissionManager::ref().currentMission();
|
||||
|
||||
if (mission.phases().size() > 0) {
|
||||
glm::vec4 inactiveColor(0.3, 0.3, 0.3, 1);
|
||||
glm::vec4 nextMissionColor(0.3, 0.4, 0.7, 1);
|
||||
glm::vec4 activeMissionColor(0.3, 0.6, 1.0, 1);
|
||||
static const glm::vec4 nextMissionColor(0.7, 0.3, 0.3, 1);
|
||||
//static const glm::vec4 missionProgressColor(0.4, 1.0, 1.0, 1);
|
||||
static const glm::vec4 currentMissionColor(0.0, 0.5, 0.5, 1);
|
||||
static const glm::vec4 missionProgressColor = currentMissionColor;// (0.4, 1.0, 1.0, 1);
|
||||
static const glm::vec4 currentLeafMissionColor = missionProgressColor;
|
||||
static const glm::vec4 nonCurrentMissionColor(0.3, 0.3, 0.3, 1);
|
||||
|
||||
size_t nextMissionPhaseIndex = -1;
|
||||
size_t currentMissionPhaseIndex = -1;
|
||||
|
||||
for (size_t i = 0; i < mission.phases().size(); i++) {
|
||||
if (mission.phase(i).timeRange().includes(currentTime)) {
|
||||
RenderFontCr(*_fontInfo, penPosition, activeMissionColor, "Current Mission Phase Progress:" );
|
||||
double remaining = mission.phase(i).timeRange().end - currentTime;
|
||||
float t = static_cast<float>(1.0 - remaining / mission.phase(i).timeRange().duration());
|
||||
std::string progress = progressToStr(25, t);
|
||||
RenderFontCr(*_fontInfo,
|
||||
penPosition,
|
||||
activeMissionColor,
|
||||
"%s %.1f %%",
|
||||
progress.c_str(), t * 100
|
||||
);
|
||||
currentMissionPhaseIndex = i;
|
||||
break;
|
||||
}
|
||||
else if (mission.phase(i).timeRange().start > currentTime) {
|
||||
RenderFontCr(*_fontInfo, penPosition, nextMissionColor, "Next Mission Phase:");
|
||||
if (i > 0) {
|
||||
double remaining = mission.phase(i).timeRange().start - currentTime;
|
||||
double duration = mission.phase(i).timeRange().start - mission.phase(i - 1).timeRange().end;
|
||||
float t = static_cast<float>(1.0 - remaining / duration);
|
||||
std::string progress = progressToStr(25, t);
|
||||
RenderFontCr(*_fontInfo,
|
||||
penPosition,
|
||||
nextMissionColor,
|
||||
"%s %.1f %%",
|
||||
progress.c_str(), t * 100
|
||||
);
|
||||
}
|
||||
nextMissionPhaseIndex = i;
|
||||
break;
|
||||
}
|
||||
int maxDepth = 2;
|
||||
std::list<const MissionPhase*> phaseTrace = mission.phaseTrace(currentTime, maxDepth);
|
||||
|
||||
if (phaseTrace.size()) {
|
||||
std::string title = "Current Mission Phase: " + phaseTrace.back()->name();
|
||||
RenderFontCr(*_fontInfo, penPosition, missionProgressColor, title.c_str());
|
||||
double remaining = phaseTrace.back()->timeRange().end - currentTime;
|
||||
float t = static_cast<float>(1.0 - remaining / phaseTrace.back()->timeRange().duration());
|
||||
std::string progress = progressToStr(25, t);
|
||||
//RenderFontCr(*_fontInfo, penPosition, missionProgressColor,
|
||||
// "%.0f s %s %.1f %%", remaining, progress.c_str(), t * 100);
|
||||
}
|
||||
else {
|
||||
RenderFontCr(*_fontInfo, penPosition, nextMissionColor, "Next Mission:");
|
||||
double remaining = mission.timeRange().start - currentTime;
|
||||
RenderFontCr(*_fontInfo, penPosition, nextMissionColor,
|
||||
"%.0f s", remaining);
|
||||
}
|
||||
|
||||
bool showAllPhases = false;
|
||||
|
||||
for (size_t i = 0; i < mission.phases().size(); i++) {
|
||||
if (i == currentMissionPhaseIndex || i == nextMissionPhaseIndex) {
|
||||
RenderFontCr(*_fontInfo,
|
||||
penPosition,
|
||||
currentMissionPhaseIndex != -1 ? activeMissionColor : nextMissionColor,
|
||||
mission.phase(i).name().c_str()
|
||||
typedef std::pair<const MissionPhase*, int> PhaseWithDepth;
|
||||
std::stack<PhaseWithDepth> S;
|
||||
int pixelIndentation = 20;
|
||||
S.push({ &mission, 0 });
|
||||
while (!S.empty()) {
|
||||
const MissionPhase* phase = S.top().first;
|
||||
int depth = S.top().second;
|
||||
S.pop();
|
||||
|
||||
bool isCurrentPhase = phase->timeRange().includes(currentTime);
|
||||
//bool isCurrentLeafPhase = phaseTrace.size() && phase == phaseTrace.back();
|
||||
glm::vec4 color = /*isCurrentLeafPhase ? currentLeafMissionColor :*/ isCurrentPhase ? currentMissionColor : nonCurrentMissionColor;
|
||||
|
||||
|
||||
penPosition.x += depth * pixelIndentation;
|
||||
if (isCurrentPhase) {
|
||||
double remaining = phase->timeRange().end - currentTime;
|
||||
float t = static_cast<float>(1.0 - remaining / phase->timeRange().duration());
|
||||
std::string progress = progressToStr(25, t);
|
||||
RenderFontCr(*_fontInfo, penPosition, color,
|
||||
"%s %s %.1f %%",
|
||||
phase->name().c_str(),
|
||||
progress.c_str(),
|
||||
t * 100
|
||||
);
|
||||
}
|
||||
else {
|
||||
RenderFontCr(*_fontInfo, penPosition, inactiveColor, mission.phase(i).name().c_str());
|
||||
RenderFontCr(*_fontInfo, penPosition, color, phase->name().c_str());
|
||||
}
|
||||
penPosition.x -= depth * pixelIndentation;
|
||||
|
||||
if((isCurrentPhase || showAllPhases) && depth < maxDepth){
|
||||
// phases are sorted increasingly by start time, and will be popped
|
||||
// last-in-first-out from the stack, so add them in reversed order.
|
||||
int indexLastPhase = phase->phases().size() - 1;
|
||||
for (int i = indexLastPhase; 0 <= i; --i) {
|
||||
S.push({ &phase->phase(i), depth + 1 });
|
||||
}
|
||||
}
|
||||
}
|
||||
RenderFontCr(*_fontInfo, penPosition, inactiveColor, " " );
|
||||
RenderFontCr(*_fontInfo, penPosition, nonCurrentMissionColor, " " );
|
||||
}
|
||||
|
||||
double remaining = openspace::ImageSequencer::ref().getNextCaptureTime() - currentTime;
|
||||
|
||||
123
support/mission/ckbrief2mission.js
Normal file
123
support/mission/ckbrief2mission.js
Normal file
@@ -0,0 +1,123 @@
|
||||
var USAGE_TEXT = '\n\
|
||||
USAGE:\n\
|
||||
node spice2mission.js <input directory> [,<ckbrief arguments...>] \n\
|
||||
\n\
|
||||
PURPOSE:\n\
|
||||
This script takes a root directory containing SPICE files (*.bc) \n\
|
||||
and prints lua code representing the contents for a .mission-file\n\
|
||||
to std out. The directory structure is used to create the hierarchy\n\
|
||||
of mission phases.\
|
||||
';
|
||||
|
||||
const exec = require('child_process').exec;
|
||||
|
||||
var KEY_START = 'start';
|
||||
var KEY_END = 'end';
|
||||
var FILE_START = 'Summary for: ';
|
||||
var TIME_START = 'Begin ET: ';
|
||||
var SPACES = ' ';
|
||||
|
||||
var inputDir = process.argv[2];
|
||||
var additionalArguments = process.argv.splice(3);
|
||||
|
||||
|
||||
run();
|
||||
|
||||
function run(){
|
||||
if(process.argv.length == 2){
|
||||
console.log('Error: expected at least one (1) argument');
|
||||
console.log(USAGE_TEXT);
|
||||
return;
|
||||
}
|
||||
|
||||
execute('find ' + inputDir + ' -type f -name *.bc*', (files) => {
|
||||
files = files.split('\n').join(' ');
|
||||
//console.log(files);
|
||||
var cmd = "ckbrief.exe " + additionalArguments.join(" ") + " " + files + '-g';
|
||||
execute(cmd, handleCkbriefOutput);
|
||||
});
|
||||
}
|
||||
|
||||
function onSuccess(cb){
|
||||
return (error, stdout, stderr) => {
|
||||
if(error) return console.error('exec error: ' + error);
|
||||
if(stderr) return console.error(stderr);
|
||||
cb(stdout);
|
||||
}
|
||||
}
|
||||
|
||||
function execute(cmd, cb){
|
||||
//console.log('executing: ' + cmd);
|
||||
exec(cmd, onSuccess(cb));
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the output from the shell command
|
||||
* $ find <inputDit> -type f -name *.bc | xargs ckbrief.exe <additional arguments...> -g
|
||||
*/
|
||||
function handleCkbriefOutput(output){
|
||||
var mission = {};
|
||||
var currentLeaf = null;
|
||||
var lines = output.split('\n');
|
||||
for (var i = 0; i < lines.length; i++) {
|
||||
var line = lines[i].trim();
|
||||
if(line.startsWith(FILE_START)){
|
||||
var pathToFile = line.substr(FILE_START.length);
|
||||
//console.log(currentLeaf);
|
||||
currentLeaf = addPathToTree(mission, pathToFile);
|
||||
}
|
||||
else if(line.startsWith(TIME_START)){
|
||||
var startTime = line.substr(TIME_START.length + 0, TIME_START.length + 14);
|
||||
var endTime = line.substr(TIME_START.length + 34).trim();
|
||||
if(currentLeaf[KEY_START] === undefined) {
|
||||
currentLeaf[KEY_START] = startTime;
|
||||
}
|
||||
currentLeaf[KEY_END] = endTime;
|
||||
}
|
||||
}
|
||||
//console.log(JSON.stringify(mission, null, 2));
|
||||
|
||||
var luaStr = toLuaTable(mission, 0);
|
||||
console.log(luaStr);
|
||||
}
|
||||
|
||||
function toLuaTable(mission, d){
|
||||
if(d === undefined) d = 0;
|
||||
if(mission === undefined) return '';
|
||||
//if(d > 2) return '';
|
||||
var str = d ? "" : "return ";
|
||||
|
||||
var indent = SPACES.substr(0, d*2);
|
||||
for (var phaseName in mission) {
|
||||
if (mission.hasOwnProperty(phaseName)) {
|
||||
var phase = mission[phaseName];
|
||||
str += '\n' + indent + '{ Name = "' + phaseName + '", ';
|
||||
if(phase[KEY_START] !== undefined && phase[KEY_END] !== undefined){
|
||||
str += 'TimeRange = { Start = "' + phase[KEY_START] + '", End = "' + phase[KEY_END] + '" }';
|
||||
}
|
||||
else {
|
||||
str += 'Phases = {' + toLuaTable(phase, d + 1) + '\n' + indent + '}';
|
||||
}
|
||||
str += '},';
|
||||
}
|
||||
}
|
||||
|
||||
// strip out last ','.
|
||||
return str.substr(0, str.length-1);
|
||||
}
|
||||
|
||||
function addPathToTree(obj, components){
|
||||
if(typeof components === 'string') {
|
||||
components = components.split('/');
|
||||
}
|
||||
|
||||
var o = obj;
|
||||
var key;
|
||||
for (var i = 0; i < components.length; i++) {
|
||||
key = components[i];
|
||||
if(o[key] === undefined) o[key] = {};
|
||||
o = o[key];
|
||||
}
|
||||
|
||||
return o; // returning the leaf component
|
||||
}
|
||||
Reference in New Issue
Block a user