/// <summary> /// Draws the Conics window. /// </summary> /// <param name="id">Identifier.</param> public void drawConicsWindow(int id) { PatchedConicSolver solver = NodeTools.getSolver(); Color defaultColor = GUI.backgroundColor; GUILayout.BeginVertical(); // Conics mode controls GUILayout.BeginHorizontal(); GUILayout.Label("Conics mode: ", GUILayout.Width(100)); GUIParts.drawButton("0", (options.conicsMode == 0?Color.yellow:defaultColor), delegate() { options.setConicsMode(0); }); GUIParts.drawButton("1", (options.conicsMode == 1?Color.yellow:defaultColor), delegate() { options.setConicsMode(1); }); GUIParts.drawButton("2", (options.conicsMode == 2?Color.yellow:defaultColor), delegate() { options.setConicsMode(2); }); GUIParts.drawButton("3", (options.conicsMode == 3?Color.yellow:defaultColor), delegate() { options.setConicsMode(3); }); GUIParts.drawButton("4", (options.conicsMode == 4?Color.yellow:defaultColor), delegate() { options.setConicsMode(4); }); GUILayout.EndHorizontal(); // conics patch limit editor. GUILayout.BeginHorizontal(); GUILayout.Label("Change Conics Samples", GUILayout.Width(200)); GUIParts.drawButton("-", Color.red, delegate() { solver.DecreasePatchLimit(); }); GUIParts.drawButton("+", Color.red, delegate() { solver.IncreasePatchLimit(); }); GUILayout.EndHorizontal(); GUILayout.EndVertical(); GUI.DragWindow(); }
/// <summary> /// Overridden function from MonoBehavior /// </summary> internal void Update() { if (!FlightDriver.Pause && canShowNodeEditor) { PatchedConicSolver solver = NodeTools.getSolver(); if (solver.maneuverNodes.Count > 0) { if (!curState.hasNode() || !solver.maneuverNodes.Contains(curState.node)) { // get the first one if we can't find the current or it's null curState = new NodeManager(solver.maneuverNodes[0]); } else if (curState.hasNode()) { curState.updateNode(); curState = curState.nextState(); } } else { if (curState.hasNode()) { curState = new NodeManager(); curState.resizeClockWindow = true; } } processKeyInput(); } intuitiveNodeGizmosManager.OnUpdate(); }
/// <summary> /// Gets the UT for the equatorial DN. /// </summary> /// <returns>The equatorial DN UT.</returns> /// <param name="o">The Orbit to calculate the UT from.</param> public static double getEquatorialDNUT(Orbit o) { //TODO: Add safeguards for bad UTs, may need to be refactored to NodeManager Vector3d DNVector = QuaternionD.AngleAxis(NodeTools.Angle360(o.LAN + 180), Planetarium.Zup.Z) * Planetarium.Zup.X; return(o.GetUTforTrueAnomaly(o.GetTrueAnomalyOfZupVector(DNVector), 2)); }
internal void pageConicsMode() { conicsMode++; if (conicsMode < 0 || conicsMode > 4) { conicsMode = 0; } NodeTools.changeConicsMode(conicsMode); }
private void drawTripWindow() { PatchedConicSolver solver = NodeTools.getSolver(); GUILayout.BeginVertical(); if (solver.maneuverNodes.Count < 1) { GUILayout.BeginHorizontal(); GUILayout.Label("No nodes to show.", GUILayout.Width(200)); GUILayout.EndHorizontal(); } else { double total = 0.0; double timeNow = Planetarium.GetUniversalTime(); GUILayout.BeginHorizontal(); GUILayout.Label("", GUILayout.Width(60)); GUILayout.Label("Δv", GUILayout.Width(90)); GUILayout.Label("Time Until", GUILayout.Width(200)); GUILayout.Label("", GUILayout.Width(120)); GUILayout.EndHorizontal(); foreach (ManeuverNode curNode in solver.maneuverNodes) { int idx = solver.maneuverNodes.IndexOf(curNode); double timeDiff = curNode.UT - timeNow; GUILayout.BeginHorizontal(); GUILayout.Label("Node " + (idx + 1), GUILayout.Width(60)); GUILayout.Label(curNode.DeltaV.magnitude.ToString("F2") + " m/s", GUILayout.Width(90)); GUILayout.Label(timeDiff.convertUTtoHumanDuration(), GUILayout.Width(200)); if (idx > 0) { GUIParts.drawButton("▲ Merge", Color.white, () => { // schedule for next layout pass to not mess up maneuver nodes while iterating over them scheduledForLayout.Add(() => { solver.maneuverNodes[idx].mergeNodeDown(); }); }); } GUILayout.EndHorizontal(); total += curNode.DeltaV.magnitude; } GUILayout.BeginHorizontal(); GUILayout.Label("Total", GUILayout.Width(60)); GUILayout.Label(total.ToString("F2") + " m/s", GUILayout.Width(90)); GUILayout.Label("", GUILayout.Width(200)); GUILayout.EndHorizontal(); } GUILayout.EndVertical(); GUI.DragWindow(); }
public NodeManager(ManeuverNode n) { curState = new NodeState(n); curNodeState = new NodeState(); node = n; updateCurrentNodeState(); if (NodeTools.findNextEncounter(n) != null) { encounter = true; } }
public NodeManager nextState() { if (nextNode != null) { return(new NodeManager(nextNode)); } if (NodeTools.findNextEncounter(node) != null) { encounter = true; } return(this); }
/// <summary> /// Overridden function from MonoBehavior /// </summary> public void OnGUI() { // Porcess any scheduled functions if (Event.current.type == EventType.Layout && !FlightDriver.Pause && scheduledForLayout.Count > 0) { foreach (Action a in scheduledForLayout) { a(); } scheduledForLayout.Clear(); } if (canShowNodeEditor) { if (Event.current.type == EventType.Layout && !FlightDriver.Pause) { // On layout we should see if we have nodes to act on. if (curState.resizeMainWindow) { options.mainWindowPos.height = 250; } if (curState.resizeClockWindow) { options.clockWindowPos.height = 65; } showEncounter = curState.encounter; // this prevents the clock window from showing the time to // next node when the next state is created during repaint. showTimeNext = curState.hasNode(); } if (!conicsLoaded) { NodeTools.changeConicsMode(options.conicsMode); conicsLoaded = true; } if (shown) { drawGUI(); } else if (canShowConicsWindow) { drawConicsGUI(); } } else if (canShowConicsWindow) { drawConicsGUI(); } if (canShowClock) { drawClockGUI(); } }
// debugging function private void drawEAngle() { // Ejection angle if (options.showEAngle) { String eangle = "n/a"; if (FlightGlobals.ActiveVessel.orbit.referenceBody.name != "Sun") { eangle = NodeTools.getEjectionAngle(FlightGlobals.ActiveVessel.orbit, curState.currentUT()).ToString("0.##") + "°"; } GUIParts.drawDoubleLabel("Ejection Angle:", 100, eangle, 130); } }
// calculation function for mergeNodeDown private static Orbit findPreviousOrbit(this ManeuverNode n) { PatchedConicSolver p = NodeTools.getSolver(); int idx = p.maneuverNodes.IndexOf(n); if (idx > 0) { return(p.maneuverNodes[idx - 1].patch); } else { return(FlightGlobals.ActiveVessel.orbit); } }
public void drawTripWindow(int id) { PatchedConicSolver solver = NodeTools.getSolver(); GUILayout.BeginVertical(); if (solver.maneuverNodes.Count < 1) { GUILayout.BeginHorizontal(); GUILayout.Label("No nodes to show.", GUILayout.Width(200)); GUILayout.EndHorizontal(); } else { double total = 0.0; double timeNow = Planetarium.GetUniversalTime(); GUILayout.BeginHorizontal(); GUILayout.Label("", GUILayout.Width(60)); GUILayout.Label("Δv", GUILayout.Width(90)); GUILayout.Label("Time Until", GUILayout.Width(200)); GUILayout.Label("", GUILayout.Width(120)); GUILayout.EndHorizontal(); foreach (ManeuverNode curNode in solver.maneuverNodes) { int idx = solver.maneuverNodes.IndexOf(curNode); double timeDiff = curNode.UT - timeNow; GUILayout.BeginHorizontal(); GUILayout.Label("Node " + idx, GUILayout.Width(60)); GUILayout.Label(curNode.DeltaV.magnitude.ToString("F2") + "m/s", GUILayout.Width(90)); GUILayout.Label(NodeTools.convertUTtoHumanDuration(timeDiff), GUILayout.Width(200)); // these will be scheduled for during the next layout pass if (idx > 0) { GUIParts.drawButton("merge ▲", Color.white, delegate() { scheduledForLayout.Add(new Action(() => { NodeTools.mergeNodeDown(solver.maneuverNodes[idx]); })); }); } GUILayout.EndHorizontal(); total += curNode.DeltaV.magnitude; } GUILayout.BeginHorizontal(); GUILayout.Label("Total", GUILayout.Width(60)); GUILayout.Label(total.ToString("F2") + "m/s", GUILayout.Width(90)); GUILayout.Label("", GUILayout.Width(200)); GUILayout.EndHorizontal(); } GUILayout.EndVertical(); GUI.DragWindow(); }
private void drawManeuverPager() { PatchedConicSolver solver = NodeTools.getSolver(); int idx = solver.maneuverNodes.IndexOf(curState.node); int count = solver.maneuverNodes.Count; GUILayout.BeginHorizontal(); GUI.enabled = count > 1; if (GUILayout.Button("◀")) { if (idx > 0) { curState.nextNode = solver.maneuverNodes[idx - 1]; } else { curState.nextNode = solver.maneuverNodes[count - 1]; } curState.clearMemory(); } GUI.enabled = true; if (GUILayout.Button("Node " + (idx + 1))) { MapView.MapCamera.SetTarget(curState.node.scaledSpaceTarget); } GUIParts.drawButton("Del", Color.red, () => { curState.node.RemoveSelf(); //solver.RemoveManeuverNode(curState.node); curState.clearMemory(); }); GUI.enabled = count > 1; if (GUILayout.Button("▶")) { if (idx < (count - 1)) { curState.nextNode = solver.maneuverNodes[idx + 1]; } else { curState.nextNode = solver.maneuverNodes[0]; } curState.clearMemory(); } GUI.enabled = true; GUILayout.EndHorizontal(); }
internal void FixedUpdate() { if (!FlightDriver.Pause) { PatchedConicSolver solver = NodeTools.getSolver(); if (options.removeUsedNodes && solver.maneuverNodes.Count > 0) { ManeuverNode node = solver.maneuverNodes[0]; if (node.GetBurnVector(FlightGlobals.ActiveVessel.orbit).magnitude < options.usedNodeThreshold) { solver.RemoveManeuverNode(node); //TODO: Clean up states after removing the node. } } } }
/// <summary> /// Gets the ejection angle of the current maneuver node. /// </summary> /// <returns>The ejection angle in degrees. Positive results are the angle from prograde, negative results are the angle from retrograde.</returns> /// <param name="nodeUT">Kerbal Spece Program Universal Time.</param> public static double getEjectionAngle(Orbit o, double nodeUT) { CelestialBody body = o.referenceBody; // Calculate the angle between the node's position and the reference body's velocity at nodeUT Vector3d prograde = body.orbit.getOrbitalVelocityAtUT(nodeUT); Vector3d position = o.getRelativePositionAtUT(nodeUT); double eangle = NodeTools.Angle360((Math.Atan2(prograde.y, prograde.x) - Math.Atan2(position.y, position.x)) * 180.0 / Math.PI); // Correct to angle from retrograde if needed. if (eangle > 180) { eangle = 180 - eangle; } return(eangle); }
private void UpdateIntuitiveManeuverHandlersList() { PatchedConicSolver solver = NodeTools.getSolver(); if (solver != null) { List <ManeuverNode> nodes = solver.maneuverNodes; for (int i = 0; i < nodes.Count; i++) { ManeuverNode node = nodes[i]; if ((node.attachedGizmo != null) && !isHandled(node)) { this.maneuverGizmoHandlers.Add(new IntuitiveNodeGizmoHandler(this, node, options)); } } } }
public static void drawManeuverPager(NodeManager curState) { PatchedConicSolver solver = NodeTools.getSolver(); GUILayout.BeginHorizontal(); if (GUILayout.Button("<")) { int count = solver.maneuverNodes.Count; if (count > 1) { // get the previous or last node int idx = solver.maneuverNodes.IndexOf(curState.node); if (idx == 0) { curState.nextNode = solver.maneuverNodes[--count]; } else { curState.nextNode = solver.maneuverNodes[--idx]; } } } if (GUILayout.Button("Editing Node " + (solver.maneuverNodes.IndexOf(curState.node) + 1))) { MapView.MapCamera.SetTarget(curState.node.scaledSpaceTarget); } if (GUILayout.Button(">")) { int count = solver.maneuverNodes.Count; if (count > 1) { // get the previous or last node int idx = solver.maneuverNodes.IndexOf(curState.node); if (idx == count - 1) { curState.nextNode = solver.maneuverNodes[0]; } else { curState.nextNode = solver.maneuverNodes[++idx]; } } } GUILayout.EndHorizontal(); }
/// <summary> /// Merges the given node into the next lowest node (n's index - 1). If there is no lower node, does nothing. /// </summary> /// <param name="n">The ManeuverNode to merge down.</param> internal static void mergeNodeDown(this ManeuverNode n) { PatchedConicSolver p = NodeTools.getSolver(); Orbit o = FlightGlobals.ActiveVessel.orbit; int nodes = p.maneuverNodes.Count; int idx = p.maneuverNodes.IndexOf(n); // if we're the last or only node, don't bother. if (idx == 0 || nodes < 2) { return; } ManeuverNode mergeInto = p.maneuverNodes[idx - 1]; Vector3d deltaV = mergeBurnVectors(mergeInto.UT, mergeInto, n.patch); mergeInto.OnGizmoUpdated(deltaV, mergeInto.UT); p.maneuverNodes.Remove(n); }
// debugging function private void drawEncounter(Color defaultColor) { // Additional Information if (options.showOrbitInfo) { // Find the next encounter, if any, in our flight plan. if (showEncounter) { Orbit nextEnc = NodeTools.findNextEncounter(curState.node); string name = "N/A"; string PeA = "N/A"; if (nextEnc != null) { name = nextEnc.referenceBody.name; PeA = NodeTools.formatMeters(nextEnc.PeA); } else { curState.encounter = false; } // Next encounter periapsis GUIParts.drawDoubleLabel("(" + name + ") Pe:", 100, PeA, 130); GUILayout.BeginHorizontal(); GUILayout.Label("", GUILayout.Width(100)); GUIParts.drawButton("Focus on " + name, defaultColor, delegate() { MapView.MapCamera.SetTarget(name); }); GUILayout.EndHorizontal(); } else { if (curState.node.solver.flightPlan.Count > 1) { // output the apoapsis and periapsis of our projected orbit. GUIParts.drawDoubleLabel("Apoapsis:", 100, NodeTools.formatMeters(curState.node.nextPatch.ApA), 100); GUIParts.drawDoubleLabel("Periapsis:", 100, NodeTools.formatMeters(curState.node.nextPatch.PeA), 130); } } } }
internal static void drawConicsControls(PreciseNodeOptions options) { PatchedConicSolver solver = NodeTools.getSolver(); Color defaultColor = GUI.backgroundColor; // Conics mode controls GUILayout.BeginHorizontal(); GUILayout.Label("Conics mode: ", GUILayout.Width(100)); for (int mode = 0; mode <= 4; mode++) { drawButton(mode.ToString(), (options.conicsMode == mode) ? Color.yellow : defaultColor, () => { options.setConicsMode(mode); }); } GUILayout.EndHorizontal(); // conics patch limit editor. GUILayout.BeginHorizontal(); GUILayout.Label("Change conics samples:", GUILayout.Width(200)); drawPlusMinusButtons(solver.IncreasePatchLimit, solver.DecreasePatchLimit); GUILayout.EndHorizontal(); }
/// <summary> /// Draws the Clock window. /// </summary> private void drawClockWindow() { Color defaultColor = GUI.backgroundColor; double timeNow = Planetarium.GetUniversalTime(); String timeUT = timeNow.ToString("F0"); String timeHuman = timeNow.convertUTtoHumanTime(); GUILayout.BeginVertical(); GUIParts.drawDoubleLabel("Time:", 35, timeHuman, 150); GUIParts.drawDoubleLabel("UT:", 35, Math.Floor(timeNow).ToString("F0"), 150); if (showTimeNext) { double next = 0.0; string labelText = ""; if (NodeTools.getSolver().maneuverNodes.Count > 0) { // protection from index out of range errors. // should probably handle this better. next = timeNow - NodeTools.getSolver().maneuverNodes[0].UT; } if (next < 0) { labelText = "T-" + next.convertUTtoHumanDuration(); } else { labelText = "T+" + next.convertUTtoHumanDuration(); } GUIParts.drawDoubleLabel("Next:", 35, labelText, 150); } GUILayout.EndVertical(); GUI.DragWindow(); }
// debugging function private void drawTimeControls(Color contentColor) { // Universal time controls GUILayout.BeginHorizontal(); GUILayout.Label((options.largeUTIncrement?"UT: (10x inc)":"UT:"), GUILayout.Width(100)); GUI.backgroundColor = Color.green; if (!curState.timeParsed) { GUI.contentColor = Color.red; } string check = GUILayout.TextField(curState.timeText, GUILayout.Width(100)); if (!curState.timeText.Equals(check, StringComparison.Ordinal)) { curState.setUT(check); } GUI.contentColor = contentColor; double ut_increment = options.increment * (options.largeUTIncrement ? 10.0 : 1.0); GUIParts.drawButton("-", Color.red, delegate() { curState.addUT(ut_increment * -1.0); }); GUIParts.drawButton("+", Color.green, delegate() { curState.addUT(ut_increment); }); GUILayout.EndHorizontal(); // extended time controls if (options.showUTControls) { GUILayout.BeginHorizontal(); GUIParts.drawButton("Peri", Color.yellow, delegate() { curState.setPeriapsis(); }); GUIParts.drawButton("DN", Color.magenta, delegate() { Orbit targ = NodeTools.getTargetOrbit(); if (targ != null) { curState.setUT(NodeTools.getTargetDNUT(curState.node.patch, targ)); } else { curState.setUT(NodeTools.getEquatorialDNUT(curState.node.patch)); } }); if (options.largeUTIncrement) { GUIParts.drawButton("-Orb", Color.red, delegate() { curState.addUT(-curState.node.patch.period); }); GUIParts.drawButton("+Orb", Color.green, delegate() { curState.addUT(curState.node.patch.period); }); } else { GUIParts.drawButton("-1K", Color.red, delegate() { curState.addUT(-1000); }); GUIParts.drawButton("+1K", Color.green, delegate() { curState.addUT(1000); }); } GUIParts.drawButton("AN", Color.cyan, delegate() { Orbit targ = NodeTools.getTargetOrbit(); if (targ != null) { curState.setUT(NodeTools.getTargetANUT(curState.node.patch, targ)); } else { curState.setUT(NodeTools.getEquatorialANUT(curState.node.patch)); } }); GUIParts.drawButton("Apo", Color.blue, delegate() { curState.setApoapsis(); }); GUILayout.EndHorizontal(); } }
/// <summary> /// Draws the Node Editor window. /// </summary> private void drawMainWindow() { Color defaultColor = GUI.backgroundColor; Color contentColor = GUI.contentColor; Color curColor = defaultColor; PatchedConicSolver solver = NodeTools.getSolver(); // Options button if (showOptions) { GUI.backgroundColor = Color.green; } if (GUI.Button(new Rect(options.mainWindowPos.width - 48, 2, 22, 18), "O")) { showOptions = !showOptions; } GUI.backgroundColor = defaultColor; // Keymapping button if (showKeymapper) { GUI.backgroundColor = Color.green; } if (GUI.Button(new Rect(options.mainWindowPos.width - 24, 2, 22, 18), "K")) { showKeymapper = !showKeymapper; } GUI.backgroundColor = defaultColor; GUILayout.BeginVertical(); if (options.showManeuverPager) { drawManeuverPager(); } // Human-readable time GUIParts.drawDoubleLabel("Time:", 100, curState.currentUT().convertUTtoHumanTime(), 150); // Increment buttons GUILayout.BeginHorizontal(); GUILayout.Label("Increment:", GUILayout.Width(100)); GUIParts.drawButton("0.01", (options.increment == 0.01?Color.yellow:defaultColor), () => { options.increment = 0.01; }); GUIParts.drawButton("0.1", (options.increment == 0.1?Color.yellow:defaultColor), () => { options.increment = 0.1; }); GUIParts.drawButton("1", (options.increment == 1?Color.yellow:defaultColor), () => { options.increment = 1; }); GUIParts.drawButton("10", (options.increment == 10?Color.yellow:defaultColor), () => { options.increment = 10; }); GUIParts.drawButton("100", (options.increment == 100?Color.yellow:defaultColor), () => { options.increment = 100; }); GUILayout.EndHorizontal(); drawTimeControls(contentColor); GUILayout.BeginHorizontal(); GUILayout.BeginVertical(); drawProgradeControls(contentColor); drawNormalControls(contentColor); drawRadialControls(contentColor); GUILayout.EndVertical(); GUILayout.BeginVertical(GUILayout.ExpandHeight(true)); GUIParts.drawButton("MS", defaultColor, () => { curState.memorize(); }, GUILayout.ExpandHeight(true)); GUI.enabled = curState.HasMemorized; GUIParts.drawButton("MR", defaultColor, () => { curState.recallMemory(); }, GUILayout.ExpandHeight(true)); GUI.enabled = true; GUILayout.EndVertical(); GUILayout.EndHorizontal(); // total delta-V display GUIParts.drawDoubleLabel("Total Δv:", 100, curState.currentMagnitude().ToString("0.##") + " m/s", 130); drawEAngle(); drawEncounter(defaultColor); // Conics mode controls if (options.showConics) { GUIParts.drawConicsControls(options); } // trip info button and vessel focus buttons GUILayout.BeginHorizontal(); GUIParts.drawButton("Trip Info", (options.showTrip?Color.yellow:defaultColor), () => { options.showTrip = !options.showTrip; }); GUIParts.drawButton("Focus on Vessel", defaultColor, () => { MapObject mapObject = PlanetariumCamera.fetch.targets.Find(o => (o.vessel != null) && o.vessel.Equals(FlightGlobals.ActiveVessel)); MapView.MapCamera.SetTarget(mapObject); }); GUILayout.EndHorizontal(); GUILayout.EndVertical(); GUI.DragWindow(); }
private void drawTimeControls(Color contentColor) { // Universal time controls GUILayout.BeginHorizontal(); GUILayout.Label((options.largeUTIncrement?"UT: (x10 inc)":"UT:"), GUILayout.Width(100)); if (!curState.timeParsed) { GUI.contentColor = Color.red; } string check = GUILayout.TextField(curState.timeText, GUILayout.Width(100)); if (!curState.timeText.Equals(check, StringComparison.Ordinal)) { curState.setUT(check); } GUI.contentColor = contentColor; double currentUT = curState.currentUT(); double ut_increment = options.increment * (options.largeUTIncrement ? 10.0 : 1.0); GUIParts.drawPlusMinusButtons(() => { curState.addUT(ut_increment); }, () => { curState.addUT(-ut_increment); }, true, curState.node.patch.isUTInsidePatch(currentUT - ut_increment)); GUILayout.EndHorizontal(); // extended time controls if (options.showUTControls) { Orbit targ = NodeTools.getTargetOrbit(); GUILayout.BeginHorizontal(); GUIParts.drawButton("Peri", Color.yellow, () => { curState.setPeriapsis(); }); GUI.enabled = curState.node.hasDN(targ); GUIParts.drawButton("DN", Color.magenta, () => { if (targ != null) { curState.setUT(curState.node.patch.getTargetDNUT(targ)); } else { curState.setUT(curState.node.patch.getEquatorialDNUT()); } }); if (options.largeUTIncrement) { GUI.enabled = curState.node.patch.isUTInsidePatch(currentUT - curState.node.patch.period); GUIParts.drawButton("-Orb", Color.red, () => { curState.addUT(-curState.node.patch.period); }); GUI.enabled = curState.node.patch.isUTInsidePatch(currentUT + curState.node.patch.period); GUIParts.drawButton("+Orb", Color.green, () => { curState.addUT(curState.node.patch.period); }); } else { GUI.enabled = curState.node.patch.isUTInsidePatch(currentUT - 1000); GUIParts.drawButton("-1K", Color.red, () => { curState.addUT(-1000); }); GUI.enabled = true; GUIParts.drawButton("+1K", Color.green, () => { curState.addUT(1000); }); } GUI.enabled = curState.node.hasAN(targ); GUIParts.drawButton("AN", Color.cyan, () => { if (targ != null) { curState.setUT(curState.node.patch.getTargetANUT(targ)); } else { curState.setUT(curState.node.patch.getEquatorialANUT()); } }); GUI.enabled = curState.node.patch.hasAP(); GUIParts.drawButton("Apo", Color.blue, () => { curState.setApoapsis(); }); GUILayout.EndHorizontal(); } GUI.enabled = true; }
/// <summary> /// Draws the Node Editor window. /// </summary> /// <param name="id">Identifier.</param> public void drawMainWindow(int id) { Color defaultColor = GUI.backgroundColor; Color contentColor = GUI.contentColor; Color curColor = defaultColor; PatchedConicSolver solver = NodeTools.getSolver(); // Options button if (showOptions) { GUI.backgroundColor = Color.green; } if (GUI.Button(new Rect(options.mainWindowPos.width - 48, 2, 22, 18), "O")) { showOptions = !showOptions; } GUI.backgroundColor = defaultColor; // Keymapping button if (showKeymapper) { GUI.backgroundColor = Color.green; } if (GUI.Button(new Rect(options.mainWindowPos.width - 24, 2, 22, 18), "K")) { showKeymapper = !showKeymapper; } GUI.backgroundColor = defaultColor; GUILayout.BeginVertical(); if (options.showManeuverPager) { GUIParts.drawManeuverPager(curState); } // Human-readable time GUIParts.drawDoubleLabel("Time:", 100, NodeTools.convertUTtoHumanTime(curState.currentUT()), 130); // Increment buttons GUILayout.BeginHorizontal(); GUILayout.Label("Increment:", GUILayout.Width(100)); GUIParts.drawButton("0.01", (options.increment == 0.01?Color.yellow:defaultColor), delegate() { options.increment = 0.01; }); GUIParts.drawButton("0.1", (options.increment == 0.1?Color.yellow:defaultColor), delegate() { options.increment = 0.1; }); GUIParts.drawButton("1", (options.increment == 1?Color.yellow:defaultColor), delegate() { options.increment = 1; }); GUIParts.drawButton("10", (options.increment == 10?Color.yellow:defaultColor), delegate() { options.increment = 10; }); GUIParts.drawButton("100", (options.increment == 100?Color.yellow:defaultColor), delegate() { options.increment = 100; }); GUILayout.EndHorizontal(); drawTimeControls(contentColor); drawProgradeControls(contentColor); drawNormalControls(contentColor); drawRadialControls(contentColor); // total delta-V display GUIParts.drawDoubleLabel("Total delta-V:", 100, curState.currentMagnitude().ToString("0.##") + "m/s", 130); drawEAngle(); drawEncounter(defaultColor); // Conics mode controls GUILayout.BeginHorizontal(); GUILayout.Label("Conics mode: ", GUILayout.Width(100)); GUIParts.drawButton("0", (options.conicsMode == 0?Color.yellow:defaultColor), delegate() { options.setConicsMode(0); }); GUIParts.drawButton("1", (options.conicsMode == 1?Color.yellow:defaultColor), delegate() { options.setConicsMode(1); }); GUIParts.drawButton("2", (options.conicsMode == 2?Color.yellow:defaultColor), delegate() { options.setConicsMode(2); }); GUIParts.drawButton("3", (options.conicsMode == 3?Color.yellow:defaultColor), delegate() { options.setConicsMode(3); }); GUIParts.drawButton("4", (options.conicsMode == 4?Color.yellow:defaultColor), delegate() { options.setConicsMode(4); }); GUILayout.EndHorizontal(); // conics patch limit editor. GUILayout.BeginHorizontal(); GUILayout.Label("Change Conics Samples", GUILayout.Width(200)); GUIParts.drawButton("-", Color.red, delegate() { solver.DecreasePatchLimit(); }); GUIParts.drawButton("+", Color.red, delegate() { solver.IncreasePatchLimit(); }); GUILayout.EndHorizontal(); // trip info button and vessel focus buttons GUILayout.BeginHorizontal(); GUIParts.drawButton("Trip Info", (options.showTrip?Color.yellow:defaultColor), delegate() { options.showTrip = !options.showTrip; }); GUIParts.drawButton("Focus on Vessel", defaultColor, delegate() { MapView.MapCamera.SetTarget(FlightGlobals.ActiveVessel.vesselName); }); GUILayout.EndHorizontal(); GUILayout.EndVertical(); GUI.DragWindow(); }
internal void setConicsMode(int mode) { conicsMode = mode; NodeTools.changeConicsMode(conicsMode); }
/// <summary> /// Processes keyboard input. /// </summary> private void processKeyInput() { if (!Input.anyKeyDown) { return; } // Fix for a bug in Linux where typing would still control game elements even if // a textbox was focused. if (GUIUtility.keyboardControl != 0) { return; } // process any key input for settings if (waitForKey) { KeyCode key = NodeTools.fetchKey(); // if the time is up or we have no key to process, reset. if (((keyWaitTime + 5.0) < Planetarium.GetUniversalTime()) || key == KeyCode.None) { currentWaitKey = Key.NONE; waitForKey = false; return; } // which key are we waiting for? switch (currentWaitKey) { case Key.PROGINC: options.progInc = key; break; case Key.PROGDEC: options.progDec = key; break; case Key.NORMINC: options.normInc = key; break; case Key.NORMDEC: options.normDec = key; break; case Key.RADIINC: options.radiInc = key; break; case Key.RADIDEC: options.radiDec = key; break; case Key.TIMEINC: options.timeInc = key; break; case Key.TIMEDEC: options.timeDec = key; break; case Key.PAGEINC: options.pageIncrement = key; break; case Key.PAGECON: options.pageConics = key; break; case Key.HIDEWINDOW: options.hideWindow = key; break; case Key.ADDWIDGET: options.addWidget = key; break; } currentWaitKey = Key.NONE; waitForKey = false; return; } // process normal keyboard input // change increment if (Input.GetKeyDown(options.pageIncrement)) { if (Event.current.alt) { options.downIncrement(); } else { options.upIncrement(); } } // prograde increment if (Input.GetKeyDown(options.progInc)) { curState.addPrograde(options.increment); } // prograde decrement if (Input.GetKeyDown(options.progDec)) { curState.addPrograde(-options.increment); } // normal increment if (Input.GetKeyDown(options.normInc)) { curState.addNormal(options.increment); } // normal decrement if (Input.GetKeyDown(options.normDec)) { curState.addNormal(-options.increment); } // radial increment if (Input.GetKeyDown(options.radiInc)) { curState.addRadial(options.increment); } // radial decrement if (Input.GetKeyDown(options.radiDec)) { curState.addRadial(-options.increment); } // UT increment if (Input.GetKeyDown(options.timeInc)) { curState.addUT(options.increment * (options.largeUTIncrement ? 10.0 : 1.0)); } // UT decrement if (Input.GetKeyDown(options.timeDec)) { curState.addUT(-options.increment * (options.largeUTIncrement ? 10.0 : 1.0)); } // Page Conics if (Input.GetKeyDown(options.pageConics)) { options.pageConicsMode(); } // hide/show window if (Input.GetKeyDown(options.hideWindow)) { shown = !shown; } // open node gizmo if (Input.GetKeyDown(options.addWidget)) { curState.node.CreateNodeGizmo(); } }