From: cybutek Date: Wed, 04 Nov 2015 18:19:53 +0000 Subject: Fixed issue with angle to prograde/retrograde calculations on highly inclined orbits. (resolves #63) X-Git-Url: http://git.toad.homelinux.net/projects/VesselSimulator.git/commitdiff/8f1da91 --- Fixed issue with angle to prograde/retrograde calculations on highly inclined orbits. (resolves #63) --- --- a/Documents/CHANGES.txt +++ b/Documents/CHANGES.txt @@ -1,3 +1,25 @@ +1.0.19.0 + Added: Added current vessel name readout. (antplant) + Added: 'Relative Radial Velocity' and 'Time To Rendezvous' readouts. (itwtx) + Added: Readout help strings. (harryyoung) + Changed: The 'Torque' value in the editor is now precise to two decimal places. + Changed: Time formatting reference (Kerbin/Earth) is now based on the in-game setting. + Fixed: Optimised time formatting. (itwtx) + Fixed: TimeToAtmosphere checks that the Apoapsis is outside atmosphere. (Kerbas-ad-astra) + Fixed: Issue with stage priority flow. Caused Rapier calculations to fail if LF and O are drawn from different tanks. (Padishar) + Fixed: Issue with angle to prograde/retrograde calculations on highly inclined orbits. + Removed: Time Formatter readout as it's not required anymore. + +1.0.18.0 + Added: Orbital readouts - "Speed at Periapsis" and "Speed at Apoapsis". (Padishar) + Added: Manoeuvre readouts - "Post-burn Apoapsis" and "Post-burn Periapsis". (Padishar) + Added: Orbital readout - "Time to Atmosphere". + Fixed: Synched the minimum simulation time sliders and stopped them from snapping back after 999ms. (saybur) + Fixed: Added workaround for the bug in Vessel.horizontalSrfSpeed (Padishar) + Fixed: Physically insignificant part mass was not being correctly cascaded down through multiple parent parts. + Fixed: Intake air demand calculation not working. + Fixed: Some build engineer settings labels do not scale with UI size. + 1.0.17.0 Added: 'Mach Number' readout under the 'Surface' category and included it on the default surface HUD. Added: Stock sections in the Flight Engineer can now become HUDs. @@ -18,8 +40,8 @@ Changed: Mach on the Build Engineer now accurate to 2 decimal places. Changed: Max mach in the Build Engineer defaults to 1.00 even when no jet engines are present. - Changed: Increased eccentricity readout to 5 decimal places. - Changed: Implemented Sarbian's object pooling. + Changed: Increased eccentricity readout to 5 decimal places. + Changed: Implemented Sarbian's object pooling. Changed: The default selected body is now assigned via 'Planitarium.Home'. Changed: HUDs to clamp fully inside the screen instead of allowing them to run off the edge by a certain amount. Fixed: Physically insignificant part mass is now associated with the parent part. @@ -73,7 +95,7 @@ 1.0.15.1, 13-02-2015 Rebuild - + 1.0.15.0, 08-02-2015 Padishar's Fixes: Added: Support KIDS ISP thrust correction. @@ -83,7 +105,7 @@ 1.0.14.1, 28-12-2014 Fixed: Missing texture on the ER-7500 model. - + 1.0.14.0, 28-12-2014 Added: Career mode that limits the Flight Engineer by: - Requiring an Engineer Kerbal of any level, or placement of an Engineer Chip or ER-7500 part. @@ -203,7 +225,7 @@ Added: New readout to the surface category: - Vertical Acceleration - Horizontal Acceleration - + Changed: Atmospheric efficiency readout now shows as a percentage. Changed: Atmospheric settings (pressure/velocity) in the editor condensed onto a single line. Fixed: Bug where the overlays in the editor would stay open outside of parts screen. @@ -360,6 +382,7 @@ Added: Stock toolbar support in the Flight Engineer. Changed: Orbital Period has higher precision. Fixed: Various NullRefs in editor window and overlay. - + 1.0.0.0, 24-07-2014 Initial release for public testing. + --- a/KerbalEngineer/Editor/BuildAdvanced.cs +++ b/KerbalEngineer/Editor/BuildAdvanced.cs @@ -523,12 +523,12 @@ GUILayout.EndHorizontal(); GUILayout.BeginHorizontal(); - GUILayout.Label("Simulate using vectored thrust values:"); + GUILayout.Label("Simulate using vectored thrust values:", settingStyle); SimManager.vectoredThrust = GUILayout.Toggle(SimManager.vectoredThrust, "ENABLED", buttonStyle, GUILayout.Width(100.0f * GuiDisplaySize.Offset)); GUILayout.EndHorizontal(); GUILayout.BeginHorizontal(); - GUILayout.Label("Verbose Simulation Log:"); + GUILayout.Label("Verbose Simulation Log:", settingStyle); SimManager.logOutput = GUILayout.Toggle(SimManager.logOutput, "ENABLED", buttonStyle, GUILayout.Width(100.0f * GuiDisplaySize.Offset)); GUILayout.EndHorizontal(); --- a/KerbalEngineer/EngineerGlobals.cs +++ b/KerbalEngineer/EngineerGlobals.cs @@ -25,7 +25,7 @@ /// /// Current version of the Kerbal Engineer assembly. /// - public const string ASSEMBLY_VERSION = "1.0.17.0"; + public const string ASSEMBLY_VERSION = "1.0.18.1"; private static string assemblyFile; private static string assemblyName; --- a/KerbalEngineer/Extensions/OrbitExtensions.cs +++ b/KerbalEngineer/Extensions/OrbitExtensions.cs @@ -61,12 +61,15 @@ return 0.0; } - var angle = AngleHelper.GetAngleBetweenVectors(orbit.getRelativePositionAtUT(universalTime), - Vector3d.Exclude(orbit.GetOrbitNormal(), orbit.referenceBody.orbit.getRelativePositionAtUT(universalTime))); + Vector3d orbitVector = orbit.getRelativePositionAtUT(universalTime); + orbitVector.z = 0.0; - angle = AngleHelper.Clamp360(angle - 90.0); + Vector3d bodyVector = orbit.referenceBody.orbit.getOrbitalVelocityAtUT(universalTime); + bodyVector.z = 0.0; - return orbit.inclination > 90.0 ? angle : 360.0 - angle; + double angle = AngleHelper.GetAngleBetweenVectors(bodyVector, orbitVector); + + return AngleHelper.Clamp360(orbit.inclination < 90.0 ? angle : 360.0 - angle); } public static double GetAngleToRetrograde(this Orbit orbit) @@ -81,12 +84,15 @@ return 0.0; } - var angle = AngleHelper.GetAngleBetweenVectors(orbit.getRelativePositionAtUT(universalTime), - Vector3d.Exclude(orbit.GetOrbitNormal(), orbit.referenceBody.orbit.getRelativePositionAtUT(universalTime))); + Vector3d orbitVector = orbit.getRelativePositionAtUT(universalTime); + orbitVector.z = 0.0; - angle = AngleHelper.Clamp360(angle + 90.0); + Vector3d bodyVector = orbit.referenceBody.orbit.getOrbitalVelocityAtUT(universalTime); + bodyVector.z = 0.0; - return orbit.inclination > 90.0 ? angle : 360.0 - angle; + double angle = AngleHelper.GetAngleBetweenVectors(-bodyVector, orbitVector); + + return AngleHelper.Clamp360(orbit.inclination < 90.0 ? angle : 360.0 - angle); } public static double GetAngleToTrueAnomaly(this Orbit orbit, double trueAnomaly) --- a/KerbalEngineer/Flight/Readouts/Miscellaneous/Separator.cs +++ b/KerbalEngineer/Flight/Readouts/Miscellaneous/Separator.cs @@ -45,7 +45,7 @@ { this.Name = "Separator"; this.Category = ReadoutCategory.GetCategory("Miscellaneous"); - this.HelpString = String.Empty; + this.HelpString = "Creats a line to help seperate subsections in a module."; this.IsDefault = false; this.Cloneable = true; --- a/KerbalEngineer/Flight/Readouts/Miscellaneous/SystemTime.cs +++ b/KerbalEngineer/Flight/Readouts/Miscellaneous/SystemTime.cs @@ -40,7 +40,7 @@ { this.Name = "System Time"; this.Category = ReadoutCategory.GetCategory("Miscellaneous"); - this.HelpString = String.Empty; + this.HelpString = "Shows the System Time in 12 hour format (AM/PM)"; this.IsDefault = false; } --- a/KerbalEngineer/Flight/Readouts/Miscellaneous/TimeReference.cs +++ /dev/null @@ -1,66 +1,1 @@ -// -// Kerbal Engineer Redux -// -// Copyright (C) 2014 CYBUTEK -// -// This program is free software: you can redistribute it and/or modify -// it under the terms of the GNU General Public License as published by -// the Free Software Foundation, either version 3 of the License, or -// (at your option) any later version. -// -// This program is distributed in the hope that it will be useful, -// but WITHOUT ANY WARRANTY; without even the implied warranty of -// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -// GNU General Public License for more details. -// -// You should have received a copy of the GNU General Public License -// along with this program. If not, see . -// -#region Using Directives - -using System; - -using KerbalEngineer.Flight.Sections; -using KerbalEngineer.Helpers; - -using UnityEngine; - -#endregion - -namespace KerbalEngineer.Flight.Readouts.Miscellaneous -{ - public class TimeReference : ReadoutModule - { - #region Constructors - - public TimeReference() - { - this.Name = "Time Reference Adjuster"; - this.Category = ReadoutCategory.GetCategory("Miscellaneous"); - this.HelpString = String.Empty; - this.IsDefault = false; - } - - #endregion - - #region Methods: public - - public override void Draw(SectionModule section) - { - GUILayout.BeginHorizontal(); - GUILayout.Label("Time Ref.: " + TimeFormatter.Reference, this.NameStyle); - if (GUILayout.Button("Earth", this.ButtonStyle)) - { - TimeFormatter.SetReference(); - } - if (GUILayout.Button("Kerbin", this.ButtonStyle)) - { - TimeFormatter.SetReference(PSystemManager.Instance.localBodies.Find(body => body.bodyName.Equals("Kerbin"))); - } - GUILayout.EndHorizontal(); - } - - #endregion - } -} --- a/KerbalEngineer/Flight/Readouts/Orbital/AngleToEquatorialAscendingNode.cs +++ b/KerbalEngineer/Flight/Readouts/Orbital/AngleToEquatorialAscendingNode.cs @@ -34,7 +34,7 @@ { this.Name = "Angle to Equ. AN"; this.Category = ReadoutCategory.GetCategory("Orbital"); - this.HelpString = string.Empty; + this.HelpString = "Angular Distance from the vessel to crossing the Equator of the central body, going north of it."; this.IsDefault = false; } --- a/KerbalEngineer/Flight/Readouts/Orbital/AngleToEquatorialDescendingNode.cs +++ b/KerbalEngineer/Flight/Readouts/Orbital/AngleToEquatorialDescendingNode.cs @@ -34,7 +34,7 @@ { this.Name = "Angle to Equ. DN"; this.Category = ReadoutCategory.GetCategory("Orbital"); - this.HelpString = string.Empty; + this.HelpString = "Angular Distance from the vessel to crossing the Equator of the central body, going south of it."; this.IsDefault = false; } --- a/KerbalEngineer/Flight/Readouts/Orbital/AngleToPrograde.cs +++ b/KerbalEngineer/Flight/Readouts/Orbital/AngleToPrograde.cs @@ -36,7 +36,7 @@ { this.Name = "Angle to Prograde"; this.Category = ReadoutCategory.GetCategory("Orbital"); - this.HelpString = String.Empty; + this.HelpString = "Angular Distance from the vessel to crossing the Orbit of the central body on it's retrograde side."; this.IsDefault = true; } --- a/KerbalEngineer/Flight/Readouts/Orbital/AngleToRetrograde.cs +++ b/KerbalEngineer/Flight/Readouts/Orbital/AngleToRetrograde.cs @@ -36,7 +36,7 @@ { this.Name = "Angle to Retrograde"; this.Category = ReadoutCategory.GetCategory("Orbital"); - this.HelpString = String.Empty; + this.HelpString = "Angular Distance from the vessel to crossing the Orbit of the central body on it's retrograde side."; this.IsDefault = true; } --- a/KerbalEngineer/Flight/Readouts/Orbital/ApoapsisHeight.cs +++ b/KerbalEngineer/Flight/Readouts/Orbital/ApoapsisHeight.cs @@ -34,7 +34,7 @@ { this.Name = "Apoapsis Height"; this.Category = ReadoutCategory.GetCategory("Orbital"); - this.HelpString = "Shows the vessel's apoapsis height relative to sea level. (Apoapsis is the highest point of an orbit.)"; + this.HelpString = "Shows the vessel's apoapsis height relative to sea level. (Apoapsis is the highest point of an orbit.)"; this.IsDefault = true; } --- a/KerbalEngineer/Flight/Readouts/Orbital/Inclination.cs +++ b/KerbalEngineer/Flight/Readouts/Orbital/Inclination.cs @@ -34,7 +34,7 @@ { this.Name = "Inclination"; this.Category = ReadoutCategory.GetCategory("Orbital"); - this.HelpString = "Shows the vessel's orbital inclination."; + this.HelpString = "Shows the vessel's orbital inclination relative to the Equator."; this.IsDefault = true; } --- a/KerbalEngineer/Flight/Readouts/Orbital/ManoeuvreNode/ManoeuvreProcessor.cs +++ b/KerbalEngineer/Flight/Readouts/Orbital/ManoeuvreNode/ManoeuvreProcessor.cs @@ -63,6 +63,10 @@ public static double NormalDeltaV { get; private set; } + public static double PostBurnAp { get; private set; } + + public static double PostBurnPe { get; private set; } + public static double ProgradeDeltaV { get; private set; } public static double RadialDeltaV { get; private set; } @@ -110,6 +114,8 @@ NormalDeltaV = deltaV.y; RadialDeltaV = deltaV.x; TotalDeltaV = node.GetBurnVector(FlightGlobals.ship_orbit).magnitude; + PostBurnAp = node.nextPatch != null ? node.nextPatch.ApA : 0; + PostBurnPe = node.nextPatch != null ? node.nextPatch.PeA : 0; UniversalTime = FlightGlobals.ActiveVessel.patchedConicSolver.maneuverNodes[0].UT; AngleToPrograde = FlightGlobals.ActiveVessel.patchedConicSolver.maneuverNodes[0].patch.GetAngleToPrograde(UniversalTime); --- a/KerbalEngineer/Flight/Readouts/Orbital/ManoeuvreNode/NodeAngleToPrograde.cs +++ b/KerbalEngineer/Flight/Readouts/Orbital/ManoeuvreNode/NodeAngleToPrograde.cs @@ -36,7 +36,7 @@ { this.Name = "Manoeuvre Node Angle to Prograde"; this.Category = ReadoutCategory.GetCategory("Orbital"); - this.HelpString = String.Empty; + this.HelpString = "Angular Distance from the Node to crossing the Orbit of the central body on it's prograde side."; this.IsDefault = true; } --- a/KerbalEngineer/Flight/Readouts/Orbital/ManoeuvreNode/NodeAngleToRetrograde.cs +++ b/KerbalEngineer/Flight/Readouts/Orbital/ManoeuvreNode/NodeAngleToRetrograde.cs @@ -36,7 +36,7 @@ { this.Name = "Manoeuvre Node Angle to Retrograde"; this.Category = ReadoutCategory.GetCategory("Orbital"); - this.HelpString = String.Empty; + this.HelpString = "Angular Distance from the Node to crossing the Orbit of the central body on it's retrograde side."; this.IsDefault = true; } --- a/KerbalEngineer/Flight/Readouts/Orbital/ManoeuvreNode/NodeBurnTime.cs +++ b/KerbalEngineer/Flight/Readouts/Orbital/ManoeuvreNode/NodeBurnTime.cs @@ -36,7 +36,7 @@ { this.Name = "Manoeuvre Node Burn Time"; this.Category = ReadoutCategory.GetCategory("Orbital"); - this.HelpString = String.Empty; + this.HelpString = "The burn's total duration."; this.IsDefault = true; } --- a/KerbalEngineer/Flight/Readouts/Orbital/ManoeuvreNode/NodeHalfBurnTime.cs +++ b/KerbalEngineer/Flight/Readouts/Orbital/ManoeuvreNode/NodeHalfBurnTime.cs @@ -36,7 +36,7 @@ { this.Name = "Manoeuvre Node Half Burn Time"; this.Category = ReadoutCategory.GetCategory("Orbital"); - this.HelpString = String.Empty; + this.HelpString = "Half of the burn's total duration."; this.IsDefault = true; } --- a/KerbalEngineer/Flight/Readouts/Orbital/ManoeuvreNode/NodeNormalDeltaV.cs +++ b/KerbalEngineer/Flight/Readouts/Orbital/ManoeuvreNode/NodeNormalDeltaV.cs @@ -36,7 +36,7 @@ { this.Name = "Manoeuvre Node DeltaV (Normal)"; this.Category = ReadoutCategory.GetCategory("Orbital"); - this.HelpString = String.Empty; + this.HelpString = "Normal component of the total change in velocity."; this.IsDefault = true; } --- a/KerbalEngineer/Flight/Readouts/Orbital/ManoeuvreNode/NodeProgradeDeltaV.cs +++ b/KerbalEngineer/Flight/Readouts/Orbital/ManoeuvreNode/NodeProgradeDeltaV.cs @@ -36,7 +36,7 @@ { this.Name = "Manoeuvre Node DeltaV (Prograde)"; this.Category = ReadoutCategory.GetCategory("Orbital"); - this.HelpString = String.Empty; + this.HelpString = "Prograde/Retrograde component of the total change in velocity."; this.IsDefault = true; } --- a/KerbalEngineer/Flight/Readouts/Orbital/ManoeuvreNode/NodeRadialDeltaV.cs +++ b/KerbalEngineer/Flight/Readouts/Orbital/ManoeuvreNode/NodeRadialDeltaV.cs @@ -36,7 +36,7 @@ { this.Name = "Manoeuvre Node DeltaV (Radial)"; this.Category = ReadoutCategory.GetCategory("Orbital"); - this.HelpString = String.Empty; + this.HelpString = "Radial component of the total change in velocity."; this.IsDefault = true; } --- a/KerbalEngineer/Flight/Readouts/Orbital/ManoeuvreNode/NodeTimeToHalfBurn.cs +++ b/KerbalEngineer/Flight/Readouts/Orbital/ManoeuvreNode/NodeTimeToHalfBurn.cs @@ -36,7 +36,7 @@ { this.Name = "Time to Manoeuvre Burn"; this.Category = ReadoutCategory.GetCategory("Orbital"); - this.HelpString = String.Empty; + this.HelpString = "Time until the Manoeuvre should be started."; this.IsDefault = true; } --- a/KerbalEngineer/Flight/Readouts/Orbital/ManoeuvreNode/NodeTimeToManoeuvre.cs +++ b/KerbalEngineer/Flight/Readouts/Orbital/ManoeuvreNode/NodeTimeToManoeuvre.cs @@ -36,7 +36,7 @@ { this.Name = "Time to Manoeuvre Node"; this.Category = ReadoutCategory.GetCategory("Orbital"); - this.HelpString = String.Empty; + this.HelpString = "Time until the vessel reaches the position of the Manoeuvre Node."; this.IsDefault = true; } --- a/KerbalEngineer/Flight/Readouts/Orbital/ManoeuvreNode/NodeTotalDeltaV.cs +++ b/KerbalEngineer/Flight/Readouts/Orbital/ManoeuvreNode/NodeTotalDeltaV.cs @@ -36,7 +36,7 @@ { this.Name = "Manoeuvre Node DeltaV (Total)"; this.Category = ReadoutCategory.GetCategory("Orbital"); - this.HelpString = String.Empty; + this.HelpString = "Total change in velocity during the burn."; this.IsDefault = true; } --- /dev/null +++ b/KerbalEngineer/Flight/Readouts/Orbital/ManoeuvreNode/PostBurnApoapsis.cs @@ -1,1 +1,69 @@ +// +// Kerbal Engineer Redux +// +// Copyright (C) 2014 CYBUTEK +// +// This program is free software: you can redistribute it and/or modify +// it under the terms of the GNU General Public License as published by +// the Free Software Foundation, either version 3 of the License, or +// (at your option) any later version. +// +// This program is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU General Public License for more details. +// +// You should have received a copy of the GNU General Public License +// along with this program. If not, see . +// +#region Using Directives + +using System; + +using KerbalEngineer.Extensions; +using KerbalEngineer.Flight.Sections; + +#endregion + +namespace KerbalEngineer.Flight.Readouts.Orbital.ManoeuvreNode +{ + public class PostBurnApoapsis : ReadoutModule + { + #region Constructors + + public PostBurnApoapsis() + { + this.Name = "Post-burn Apoapsis"; + this.Category = ReadoutCategory.GetCategory("Orbital"); + this.HelpString = "Farthest point of the vessel's ofbit after the burn."; + this.IsDefault = false; + } + + #endregion + + #region Methods: public + + public override void Draw(SectionModule section) + { + if (!ManoeuvreProcessor.ShowDetails) + { + return; + } + + this.DrawLine("Post-burn Apoapsis", ManoeuvreProcessor.PostBurnAp.ToDistance(), section.IsHud); + } + + public override void Reset() + { + ManoeuvreProcessor.Reset(); + } + + public override void Update() + { + ManoeuvreProcessor.RequestUpdate(); + } + + #endregion + } +} --- /dev/null +++ b/KerbalEngineer/Flight/Readouts/Orbital/ManoeuvreNode/PostBurnPeriapsis.cs @@ -1,1 +1,69 @@ +// +// Kerbal Engineer Redux +// +// Copyright (C) 2014 CYBUTEK +// +// This program is free software: you can redistribute it and/or modify +// it under the terms of the GNU General Public License as published by +// the Free Software Foundation, either version 3 of the License, or +// (at your option) any later version. +// +// This program is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU General Public License for more details. +// +// You should have received a copy of the GNU General Public License +// along with this program. If not, see . +// +#region Using Directives + +using System; + +using KerbalEngineer.Extensions; +using KerbalEngineer.Flight.Sections; + +#endregion + +namespace KerbalEngineer.Flight.Readouts.Orbital.ManoeuvreNode +{ + public class PostBurnPeriapsis : ReadoutModule + { + #region Constructors + + public PostBurnPeriapsis() + { + this.Name = "Post-burn Periapsis"; + this.Category = ReadoutCategory.GetCategory("Orbital"); + this.HelpString = "Closest point of the vessel's ofbit after the burn."; + this.IsDefault = false; + } + + #endregion + + #region Methods: public + + public override void Draw(SectionModule section) + { + if (!ManoeuvreProcessor.ShowDetails) + { + return; + } + + this.DrawLine("Post-burn Periapsis", ManoeuvreProcessor.PostBurnPe.ToDistance(), section.IsHud); + } + + public override void Reset() + { + ManoeuvreProcessor.Reset(); + } + + public override void Update() + { + ManoeuvreProcessor.RequestUpdate(); + } + + #endregion + } +} --- a/KerbalEngineer/Flight/Readouts/Orbital/PeriapsisHeight.cs +++ b/KerbalEngineer/Flight/Readouts/Orbital/PeriapsisHeight.cs @@ -34,7 +34,7 @@ { this.Name = "Periapsis Height"; this.Category = ReadoutCategory.GetCategory("Orbital"); - this.HelpString = "Shows the vessel's periapsis height relative to sea level. (Periapsis is the lowest point of an orbit."; + this.HelpString = "Shows the vessel's periapsis height relative to sea level. (Periapsis is the lowest point of an orbit.)"; this.IsDefault = true; } --- /dev/null +++ b/KerbalEngineer/Flight/Readouts/Orbital/SpeedAtApoapsis.cs @@ -1,1 +1,68 @@ +// +// Kerbal Engineer Redux +// +// Copyright (C) 2014 CYBUTEK +// +// This program is free software: you can redistribute it and/or modify +// it under the terms of the GNU General Public License as published by +// the Free Software Foundation, either version 3 of the License, or +// (at your option) any later version. +// +// This program is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU General Public License for more details. +// +// You should have received a copy of the GNU General Public License +// along with this program. If not, see . +// +#region Using Directives + +using System; +using KerbalEngineer.Flight.Sections; +using KerbalEngineer.Helpers; +using KerbalEngineer.Extensions; + +#endregion + +namespace KerbalEngineer.Flight.Readouts.Orbital +{ + public class SpeedAtApoapsis : ReadoutModule + { + #region Constructors + + public SpeedAtApoapsis() + { + this.Name = "Speed at Apoapsis"; + this.Category = ReadoutCategory.GetCategory("Orbital"); + this.HelpString = "Shows the orbital speed of the vessel when at apoapsis, the highest point of the orbit."; + this.IsDefault = false; + } + + #endregion + + #region Methods: public + + public override void Draw(SectionModule section) + { + // Vis-viva: v^2 = GM(2/r - 1/a) + // All this is easily got from the ships orbit (and reference body) + String str; + Orbit orbit = FlightGlobals.ship_orbit; + if (orbit.eccentricity > 1.0) + str = "---m/s"; + else + { + double speedsqr = orbit.referenceBody.gravParameter * ((2 / orbit.ApR) - (1 / orbit.semiMajorAxis)); + if (Double.IsNaN(speedsqr) || speedsqr < 0) + str = "---m/s"; // Don't think this is possible barring bugs in the Orbit class + else + str = Math.Sqrt(speedsqr).ToSpeed(); + } + this.DrawLine(str, section.IsHud); + } + + #endregion + } +} --- /dev/null +++ b/KerbalEngineer/Flight/Readouts/Orbital/SpeedAtPeriapsis.cs @@ -1,1 +1,64 @@ +// +// Kerbal Engineer Redux +// +// Copyright (C) 2014 CYBUTEK +// +// This program is free software: you can redistribute it and/or modify +// it under the terms of the GNU General Public License as published by +// the Free Software Foundation, either version 3 of the License, or +// (at your option) any later version. +// +// This program is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU General Public License for more details. +// +// You should have received a copy of the GNU General Public License +// along with this program. If not, see . +// +#region Using Directives + +using System; +using KerbalEngineer.Flight.Sections; +using KerbalEngineer.Helpers; +using KerbalEngineer.Extensions; + +#endregion + +namespace KerbalEngineer.Flight.Readouts.Orbital +{ + public class SpeedAtPeriapsis : ReadoutModule + { + #region Constructors + + public SpeedAtPeriapsis() + { + this.Name = "Speed at Periapsis"; + this.Category = ReadoutCategory.GetCategory("Orbital"); + this.HelpString = "Shows the orbital speed of the vessel when at periapsis, the lowest point of the orbit."; + this.IsDefault = false; + } + + #endregion + + #region Methods: public + + public override void Draw(SectionModule section) + { + // Vis-viva: v^2 = GM(2/r - 1/a) + // All this is easily got from the ships orbit (and reference body) + String str; + Orbit orbit = FlightGlobals.ship_orbit; + double oneovera = (orbit.eccentricity == 1) ? 0 : (1 / orbit.semiMajorAxis); + double speedsqr = orbit.referenceBody.gravParameter * ((2 / orbit.PeR) - oneovera); + if (Double.IsNaN(speedsqr) || speedsqr < 0) + str = "---m/s"; + else + str = Math.Sqrt(speedsqr).ToSpeed(); + this.DrawLine(str, section.IsHud); + } + + #endregion + } +} --- /dev/null +++ b/KerbalEngineer/Flight/Readouts/Orbital/TimeToAtmosphere.cs @@ -1,1 +1,99 @@ +// +// Kerbal Engineer Redux +// +// Copyright (C) 2014 CYBUTEK +// +// This program is free software: you can redistribute it and/or modify +// it under the terms of the GNU General Public License as published by +// the Free Software Foundation, either version 3 of the License, or +// (at your option) any later version. +// +// This program is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU General Public License for more details. +// +// You should have received a copy of the GNU General Public License +// along with this program. If not, see . +// +#region Using Directives + +using System; +using KerbalEngineer.Flight.Sections; +using KerbalEngineer.Helpers; + +#endregion + +namespace KerbalEngineer.Flight.Readouts.Orbital +{ + public class TimeToAtmosphere : ReadoutModule + { + //private LogMsg log = new LogMsg(); + + #region Constructors + + public TimeToAtmosphere() + { + this.Name = "Time to Atmosphere"; + this.Category = ReadoutCategory.GetCategory("Orbital"); + this.HelpString = "Shows the time until the vessel enters or leaves the atmosphere."; + this.IsDefault = false; + } + + #endregion + + #region Methods: public + + public override void Draw(SectionModule section) + { + String str; + Orbit orbit = FlightGlobals.ship_orbit; + + if (orbit.referenceBody.atmosphere && orbit.PeA < orbit.referenceBody.atmosphereDepth && orbit.ApA > orbit.referenceBody.atmosphereDepth) + { + double tA = orbit.TrueAnomalyAtRadius(orbit.referenceBody.atmosphereDepth + orbit.referenceBody.Radius); + //log.buf.AppendFormat("tA = {0}\n", tA); + double utTime = Planetarium.GetUniversalTime(); + //log.buf.AppendFormat("utTime = {0}\n", utTime); + double timeAtRad1 = orbit.GetUTforTrueAnomaly(tA, orbit.period * 0.5); + //log.buf.AppendFormat("timeAtRad1 = {0}\n", timeAtRad1); + if (timeAtRad1 < utTime) + { + timeAtRad1 += orbit.period; + //log.buf.AppendFormat("timeAtRad1 = {0}\n", timeAtRad1); + } + double timeAtRad2 = orbit.GetUTforTrueAnomaly(-tA, orbit.period * 0.5); + //log.buf.AppendFormat("timeAtRad2 = {0}\n", timeAtRad2); + if (timeAtRad2 < utTime) + { + timeAtRad2 += orbit.period; + //log.buf.AppendFormat("timeAtRad2 = {0}\n", timeAtRad2); + } + double time = Math.Min(timeAtRad1, timeAtRad2) - utTime; + //log.buf.AppendFormat("time = {0}\n", time); + + if (Double.IsNaN(time)) + { + str = "---s"; + //log.buf.AppendLine("time is NaN"); + } + else + { + str = TimeFormatter.ConvertToString(time); + //log.buf.AppendFormat("str = {0}\n", str); + } + } + else + { + str = "---s"; + //log.buf.AppendLine("no atmosphere, pe > atmosphere, or ap < atmosphere"); + } + + //log.Flush(); + this.DrawLine(str, section.IsHud); + } + + #endregion + } +} --- a/KerbalEngineer/Flight/Readouts/Orbital/TimeToEquatorialAscendingNode.cs +++ b/KerbalEngineer/Flight/Readouts/Orbital/TimeToEquatorialAscendingNode.cs @@ -35,7 +35,7 @@ { this.Name = "Time to Equ. AN"; this.Category = ReadoutCategory.GetCategory("Orbital"); - this.HelpString = string.Empty; + this.HelpString = "Shows the time until the vessel corsses the Equator, going north of it."; this.IsDefault = false; } --- a/KerbalEngineer/Flight/Readouts/Orbital/TimeToEquatorialDescendingNode.cs +++ b/KerbalEngineer/Flight/Readouts/Orbital/TimeToEquatorialDescendingNode.cs @@ -35,7 +35,7 @@ { this.Name = "Time to Equ. DN"; this.Category = ReadoutCategory.GetCategory("Orbital"); - this.HelpString = string.Empty; + this.HelpString = "Shows the time until the vessel corsses the Equator, going south of it."; this.IsDefault = false; } --- a/KerbalEngineer/Flight/Readouts/ReadoutLibrary.cs +++ b/KerbalEngineer/Flight/Readouts/ReadoutLibrary.cs @@ -91,6 +91,11 @@ readouts.Add(new NodeTimeToHalfBurn()); readouts.Add(new NodeAngleToPrograde()); readouts.Add(new NodeAngleToRetrograde()); + readouts.Add(new PostBurnApoapsis()); + readouts.Add(new PostBurnPeriapsis()); + readouts.Add(new SpeedAtApoapsis()); + readouts.Add(new SpeedAtPeriapsis()); + readouts.Add(new TimeToAtmosphere()); // Surface readouts.Add(new AltitudeSeaLevel()); @@ -115,6 +120,7 @@ readouts.Add(new ImpactBiome()); // Vessel + readouts.Add(new Name()); readouts.Add(new DeltaVStaged()); readouts.Add(new DeltaVCurrent()); readouts.Add(new DeltaVTotal()); @@ -162,6 +168,8 @@ readouts.Add(new Rendezvous.OrbitalPeriod()); readouts.Add(new Rendezvous.SemiMajorAxis()); readouts.Add(new Rendezvous.SemiMinorAxis()); + readouts.Add(new Rendezvous.RelativeRadialVelocity()); + readouts.Add(new Rendezvous.TimeToRendezvous()); // Thermal readouts.Add(new InternalFlux()); @@ -182,7 +190,6 @@ readouts.Add(new Separator()); readouts.Add(new GuiSizeAdjustor()); readouts.Add(new SimulationDelay()); - readouts.Add(new TimeReference()); readouts.Add(new VectoredThrustToggle()); readouts.Add(new SystemTime()); --- a/KerbalEngineer/Flight/Readouts/Rendezvous/AltitudeSeaLevel.cs +++ b/KerbalEngineer/Flight/Readouts/Rendezvous/AltitudeSeaLevel.cs @@ -34,7 +34,7 @@ { this.Name = "Altitude (Sea Level)"; this.Category = ReadoutCategory.GetCategory("Rendezvous"); - this.HelpString = string.Empty; + this.HelpString = "Shows the target's altitude above sea level."; this.IsDefault = true; } --- a/KerbalEngineer/Flight/Readouts/Rendezvous/AngleToRelativeAscendingNode.cs +++ b/KerbalEngineer/Flight/Readouts/Rendezvous/AngleToRelativeAscendingNode.cs @@ -34,7 +34,7 @@ { this.Name = "Angle to Rel. AN"; this.Category = ReadoutCategory.GetCategory("Rendezvous"); - this.HelpString = string.Empty; + this.HelpString = "Angular Distance from the vessel to crossing the orbit of the target object, going north of it."; this.IsDefault = false; } --- a/KerbalEngineer/Flight/Readouts/Rendezvous/AngleToRelativeDescendingNode.cs +++ b/KerbalEngineer/Flight/Readouts/Rendezvous/AngleToRelativeDescendingNode.cs @@ -34,7 +34,7 @@ { this.Name = "Angle to Rel. DN"; this.Category = ReadoutCategory.GetCategory("Rendezvous"); - this.HelpString = string.Empty; + this.HelpString = "Angular Distance from the vessel to crossing the orbit of the target object, going south of it."; this.IsDefault = false; } --- a/KerbalEngineer/Flight/Readouts/Rendezvous/ApoapsisHeight.cs +++ b/KerbalEngineer/Flight/Readouts/Rendezvous/ApoapsisHeight.cs @@ -34,7 +34,7 @@ { this.Name = "Apoapsis Height"; this.Category = ReadoutCategory.GetCategory("Rendezvous"); - this.HelpString = string.Empty; + this.HelpString = "Shows the targets's apoapsis height relative to sea level. (Apoapsis is the highest point of an orbit.)"; this.IsDefault = true; } --- a/KerbalEngineer/Flight/Readouts/Rendezvous/Distance.cs +++ b/KerbalEngineer/Flight/Readouts/Rendezvous/Distance.cs @@ -34,7 +34,7 @@ { this.Name = "Distance"; this.Category = ReadoutCategory.GetCategory("Rendezvous"); - this.HelpString = string.Empty; + this.HelpString = "Current distance between the vessel and the target object."; this.IsDefault = true; } --- a/KerbalEngineer/Flight/Readouts/Rendezvous/OrbitalPeriod.cs +++ b/KerbalEngineer/Flight/Readouts/Rendezvous/OrbitalPeriod.cs @@ -34,7 +34,7 @@ { this.Name = "Orbital Period"; this.Category = ReadoutCategory.GetCategory("Rendezvous"); - this.HelpString = string.Empty; + this.HelpString = "Shows the amount of time it will take the target object to complete a full orbit."; this.IsDefault = false; } --- a/KerbalEngineer/Flight/Readouts/Rendezvous/PeriapsisHeight.cs +++ b/KerbalEngineer/Flight/Readouts/Rendezvous/PeriapsisHeight.cs @@ -34,7 +34,7 @@ { this.Name = "Periapsis Height"; this.Category = ReadoutCategory.GetCategory("Rendezvous"); - this.HelpString = string.Empty; + this.HelpString = "Shows the targets's periapsis height relative to sea level. (Periapsis is the lowest point of an orbit.)"; this.IsDefault = true; } --- a/KerbalEngineer/Flight/Readouts/Rendezvous/PhaseAngle.cs +++ b/KerbalEngineer/Flight/Readouts/Rendezvous/PhaseAngle.cs @@ -34,7 +34,7 @@ { this.Name = "Phase Angle"; this.Category = ReadoutCategory.GetCategory("Rendezvous"); - this.HelpString = string.Empty; + this.HelpString = "Angular distance of the vessel relative to the target object."; this.IsDefault = true; } --- /dev/null +++ b/KerbalEngineer/Flight/Readouts/Rendezvous/RelativeRadialVelocity.cs @@ -1,1 +1,66 @@ +// +// Kerbal Engineer Redux +// +// Copyright (C) 2014 CYBUTEK +// +// This program is free software: you can redistribute it and/or modify +// it under the terms of the GNU General Public License as published by +// the Free Software Foundation, either version 3 of the License, or +// (at your option) any later version. +// +// This program is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU General Public License for more details. +// +// You should have received a copy of the GNU General Public License +// along with this program. If not, see . +// +#region Using Directives + +using KerbalEngineer.Extensions; +using KerbalEngineer.Flight.Sections; + +#endregion + +namespace KerbalEngineer.Flight.Readouts.Rendezvous +{ + public class RelativeRadialVelocity : ReadoutModule + { + #region Constructors + + public RelativeRadialVelocity() + { + this.Name = "Relative Radial Velocity"; + this.Category = ReadoutCategory.GetCategory("Rendezvous"); + this.HelpString = "Relative radial velocity between your vessel and the target object"; + this.IsDefault = false; + } + + #endregion + + #region Methods: public + + public override void Draw(SectionModule section) + { + if (RendezvousProcessor.ShowDetails) + { + this.DrawLine(RendezvousProcessor.RelativeRadialVelocity.ToSpeed(), section.IsHud); + } + } + + public override void Reset() + { + FlightEngineerCore.Instance.AddUpdatable(RendezvousProcessor.Instance); + } + + public override void Update() + { + RendezvousProcessor.RequestUpdate(); + } + + #endregion + } +} + --- a/KerbalEngineer/Flight/Readouts/Rendezvous/RendezvousProcessor.cs +++ b/KerbalEngineer/Flight/Readouts/Rendezvous/RendezvousProcessor.cs @@ -135,6 +135,16 @@ /// Gets the target's time to periapsis. /// public static double TimeToPeriapsis { get; private set; } + + /// + /// Gets the relative radial velocity. + /// + public static double RelativeRadialVelocity { get; private set; } + + /// + /// Gets approximate (linearly) time to the minimum distance between objects. + /// + public static double TimeToRendezvous { get; private set; } /// /// Gets and sets whether the updatable object should be updated. @@ -193,6 +203,14 @@ Distance = Vector3d.Distance(targetOrbit.pos, originOrbit.pos); OrbitalPeriod = targetOrbit.period; + + // beware that the order/sign of coordinates is inconsistent across different exposed variables + // in particular, v below does not equal to FlightGlobals.ship_tgtVelocity + Vector3d x = targetOrbit.pos - originOrbit.pos; + Vector3d v = targetOrbit.vel - originOrbit.vel; + double xv = Vector3d.Dot(x, v); + TimeToRendezvous = - xv / Vector3d.SqrMagnitude(v); + RelativeRadialVelocity = xv / Vector3d.Magnitude(x); } private double CalcInterceptAngle() --- a/KerbalEngineer/Flight/Readouts/Rendezvous/SemiMajorAxis.cs +++ b/KerbalEngineer/Flight/Readouts/Rendezvous/SemiMajorAxis.cs @@ -36,7 +36,7 @@ { this.Name = "Semi-major Axis"; this.Category = ReadoutCategory.GetCategory("Rendezvous"); - this.HelpString = String.Empty; + this.HelpString = "Shows the distance from the centre of the target's orbit to the farthest edge."; this.IsDefault = true; } --- a/KerbalEngineer/Flight/Readouts/Rendezvous/SemiMinorAxis.cs +++ b/KerbalEngineer/Flight/Readouts/Rendezvous/SemiMinorAxis.cs @@ -36,7 +36,7 @@ { this.Name = "Semi-minor Axis"; this.Category = ReadoutCategory.GetCategory("Rendezvous"); - this.HelpString = String.Empty; + this.HelpString = "Shows the distance from the centre of the target's orbit to the nearest edge."; this.IsDefault = false; } --- a/KerbalEngineer/Flight/Readouts/Rendezvous/TimeToApoapsis.cs +++ b/KerbalEngineer/Flight/Readouts/Rendezvous/TimeToApoapsis.cs @@ -34,7 +34,7 @@ { this.Name = "Time to Apoapsis"; this.Category = ReadoutCategory.GetCategory("Rendezvous"); - this.HelpString = string.Empty; + this.HelpString = "Shows the time until the target reaches apoapsis, the highest point of the orbit."; this.IsDefault = false; } --- a/KerbalEngineer/Flight/Readouts/Rendezvous/TimeToPeriapsis.cs +++ b/KerbalEngineer/Flight/Readouts/Rendezvous/TimeToPeriapsis.cs @@ -34,7 +34,7 @@ { this.Name = "Time to Periapsis"; this.Category = ReadoutCategory.GetCategory("Rendezvous"); - this.HelpString = string.Empty; + this.HelpString = "Shows the time until the target reaches periapsis, the lowest point of the orbit."; this.IsDefault = false; } --- a/KerbalEngineer/Flight/Readouts/Rendezvous/TimeToRelativeAscendingNode.cs +++ b/KerbalEngineer/Flight/Readouts/Rendezvous/TimeToRelativeAscendingNode.cs @@ -34,7 +34,7 @@ { this.Name = "Time to Rel. AN"; this.Category = ReadoutCategory.GetCategory("Rendezvous"); - this.HelpString = string.Empty; + this.HelpString = "Time until the vessel crosses the target's orbit, going north."; this.IsDefault = true; } --- a/KerbalEngineer/Flight/Readouts/Rendezvous/TimeToRelativeDescendingNode.cs +++ b/KerbalEngineer/Flight/Readouts/Rendezvous/TimeToRelativeDescendingNode.cs @@ -34,7 +34,7 @@ { this.Name = "Time to Rel. DN"; this.Category = ReadoutCategory.GetCategory("Rendezvous"); - this.HelpString = string.Empty; + this.HelpString = "Time until the vessel crosses the target's orbit, going south."; this.IsDefault = true; } --- /dev/null +++ b/KerbalEngineer/Flight/Readouts/Rendezvous/TimeToRendezvous.cs @@ -1,1 +1,65 @@ +// +// Kerbal Engineer Redux +// +// Copyright (C) 2014 CYBUTEK +// +// This program is free software: you can redistribute it and/or modify +// it under the terms of the GNU General Public License as published by +// the Free Software Foundation, either version 3 of the License, or +// (at your option) any later version. +// +// This program is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU General Public License for more details. +// +// You should have received a copy of the GNU General Public License +// along with this program. If not, see . +// +#region Using Directives + +using KerbalEngineer.Flight.Sections; +using KerbalEngineer.Helpers; + +#endregion + +namespace KerbalEngineer.Flight.Readouts.Rendezvous +{ + public class TimeToRendezvous : ReadoutModule + { + #region Constructors + + public TimeToRendezvous() + { + this.Name = "Time to Rendezvous"; + this.Category = ReadoutCategory.GetCategory("Rendezvous"); + this.HelpString = "Approximate (linearly) time to the minimum distance between objects."; + this.IsDefault = false; + } + + #endregion + + #region Methods: public + + public override void Draw(SectionModule section) + { + if (RendezvousProcessor.ShowDetails) + { + this.DrawLine(TimeFormatter.ConvertToString(RendezvousProcessor.TimeToRendezvous), section.IsHud); + } + } + + public override void Reset() + { + FlightEngineerCore.Instance.AddUpdatable(RendezvousProcessor.Instance); + } + + public override void Update() + { + RendezvousProcessor.RequestUpdate(); + } + + #endregion + } +} --- a/KerbalEngineer/Flight/Readouts/Surface/HorizontalSpeed.cs +++ b/KerbalEngineer/Flight/Readouts/Surface/HorizontalSpeed.cs @@ -21,6 +21,7 @@ using KerbalEngineer.Extensions; using KerbalEngineer.Flight.Sections; +using System; #endregion @@ -44,7 +45,11 @@ public override void Draw(SectionModule section) { - this.DrawLine(FlightGlobals.ActiveVessel.horizontalSrfSpeed.ToSpeed(), section.IsHud); + // Used to do this but the bug-fix to horizontalSrfSpeed in KSP 1.0.3 actually made it worse so workaround + //this.DrawLine(FlightGlobals.ActiveVessel.horizontalSrfSpeed.ToSpeed(), section.IsHud); + var ves = FlightGlobals.ActiveVessel; + double horizSpeed = Math.Sqrt(ves.srfSpeed * ves.srfSpeed - ves.verticalSpeed * ves.verticalSpeed); + this.DrawLine(horizSpeed.ToSpeed(), section.IsHud); } #endregion --- a/KerbalEngineer/Flight/Readouts/Surface/ImpactAltitude.cs +++ b/KerbalEngineer/Flight/Readouts/Surface/ImpactAltitude.cs @@ -34,7 +34,7 @@ { this.Name = "Impact Altitude"; this.Category = ReadoutCategory.GetCategory("Surface"); - this.HelpString = string.Empty; + this.HelpString = "Altitude at which the Vessel will impact."; this.IsDefault = false; } --- a/KerbalEngineer/Flight/Readouts/Surface/ImpactBiome.cs +++ b/KerbalEngineer/Flight/Readouts/Surface/ImpactBiome.cs @@ -33,7 +33,7 @@ { this.Name = "Impact Biome"; this.Category = ReadoutCategory.GetCategory("Surface"); - this.HelpString = string.Empty; + this.HelpString = "Biome the Vessel will impact in."; this.IsDefault = true; } --- a/KerbalEngineer/Flight/Readouts/Surface/ImpactLatitude.cs +++ b/KerbalEngineer/Flight/Readouts/Surface/ImpactLatitude.cs @@ -34,7 +34,7 @@ { this.Name = "Impact Latitude"; this.Category = ReadoutCategory.GetCategory("Surface"); - this.HelpString = string.Empty; + this.HelpString = "Latitude of the impact position."; this.IsDefault = false; } --- a/KerbalEngineer/Flight/Readouts/Surface/ImpactLongitude.cs +++ b/KerbalEngineer/Flight/Readouts/Surface/ImpactLongitude.cs @@ -34,7 +34,7 @@ { this.Name = "Impact Longitude"; this.Category = ReadoutCategory.GetCategory("Surface"); - this.HelpString = string.Empty; + this.HelpString = "Longditude of the impact position."; this.IsDefault = false; } --- a/KerbalEngineer/Flight/Readouts/Surface/ImpactTime.cs +++ b/KerbalEngineer/Flight/Readouts/Surface/ImpactTime.cs @@ -34,7 +34,7 @@ { this.Name = "Impact Time"; this.Category = ReadoutCategory.GetCategory("Surface"); - this.HelpString = string.Empty; + this.HelpString = "Shows time until the vessel impacts the central object."; this.IsDefault = true; } --- a/KerbalEngineer/Flight/Readouts/Surface/Latitude.cs +++ b/KerbalEngineer/Flight/Readouts/Surface/Latitude.cs @@ -34,7 +34,7 @@ { this.Name = "Latitude"; this.Category = ReadoutCategory.GetCategory("Surface"); - this.HelpString = "Shows the vessel's latitude position around the celestial body. Latitude is the angle from the equator to poles."; + this.HelpString = "Shows the vessel's latitude position around the celestial body. Latitude is the angle from the equator to poles."; this.IsDefault = true; } --- a/KerbalEngineer/Flight/Readouts/Surface/Longitude.cs +++ b/KerbalEngineer/Flight/Readouts/Surface/Longitude.cs @@ -28,7 +28,7 @@ { Name = "Longitude"; Category = ReadoutCategory.GetCategory("Surface"); - HelpString = "Shows the vessel's longitude around a celestial body. Longitude is the angle from the bodies prime meridian."; + HelpString = "Shows the vessel's longitude around a celestial body. Longitude is the angle from the bodies prime meridian."; IsDefault = true; } --- a/KerbalEngineer/Flight/Readouts/Surface/Situation.cs +++ b/KerbalEngineer/Flight/Readouts/Surface/Situation.cs @@ -33,7 +33,7 @@ { this.Name = "Situation"; this.Category = ReadoutCategory.GetCategory("Surface"); - this.HelpString = string.Empty; + this.HelpString = "Shows the vessel's current scientific situation. (Landed, Splashed, Flying Low/High, In Space Low/High)"; this.IsDefault = true; } --- a/KerbalEngineer/Flight/Readouts/Thermal/CoolestPart.cs +++ b/KerbalEngineer/Flight/Readouts/Thermal/CoolestPart.cs @@ -27,7 +27,7 @@ { Name = "Coolest Part"; Category = ReadoutCategory.GetCategory("Thermal"); - HelpString = string.Empty; + HelpString = "The part of the vessel that is enduring the lowest temperature."; IsDefault = true; } --- a/KerbalEngineer/Flight/Readouts/Thermal/CoolestSkinTemperature.cs +++ b/KerbalEngineer/Flight/Readouts/Thermal/CoolestSkinTemperature.cs @@ -28,7 +28,7 @@ { Name = "Coolest Skin Temperature"; Category = ReadoutCategory.GetCategory("Thermal"); - HelpString = string.Empty; + HelpString = "Lowest external Temperature on the Vessel."; IsDefault = true; } --- a/KerbalEngineer/Flight/Readouts/Thermal/CoolestTemperature.cs +++ b/KerbalEngineer/Flight/Readouts/Thermal/CoolestTemperature.cs @@ -28,7 +28,7 @@ { Name = "Coolest Temperature"; Category = ReadoutCategory.GetCategory("Thermal"); - HelpString = string.Empty; + HelpString = "Lowest internal Temperature on the Vessel."; IsDefault = true; } --- a/KerbalEngineer/Flight/Readouts/Thermal/CriticalPart.cs +++ b/KerbalEngineer/Flight/Readouts/Thermal/CriticalPart.cs @@ -27,7 +27,7 @@ { Name = "Critical Part"; Category = ReadoutCategory.GetCategory("Thermal"); - HelpString = string.Empty; + HelpString = "This part is structually most critical. If it endures too high temperature there is a high chance for major structual failure!"; IsDefault = true; } --- a/KerbalEngineer/Flight/Readouts/Thermal/CriticalSkinTemperature.cs +++ b/KerbalEngineer/Flight/Readouts/Thermal/CriticalSkinTemperature.cs @@ -28,7 +28,7 @@ { Name = "Critical Skin Temperature"; Category = ReadoutCategory.GetCategory("Thermal"); - HelpString = string.Empty; + HelpString = "Highest external Temperature on the part of the Vessel that is structually most critical."; IsDefault = true; } --- a/KerbalEngineer/Flight/Readouts/Thermal/CriticalTemperature.cs +++ b/KerbalEngineer/Flight/Readouts/Thermal/CriticalTemperature.cs @@ -28,7 +28,7 @@ { Name = "Critical Temperature"; Category = ReadoutCategory.GetCategory("Thermal"); - HelpString = string.Empty; + HelpString = "Internal Temperature on the part of the Vessel that is structually most critical."; IsDefault = true; } --- a/KerbalEngineer/Flight/Readouts/Thermal/CriticalThermalPercentage.cs +++ b/KerbalEngineer/Flight/Readouts/Thermal/CriticalThermalPercentage.cs @@ -28,7 +28,7 @@ { Name = "Critical Thermal Percentage"; Category = ReadoutCategory.GetCategory("Thermal"); - HelpString = string.Empty; + HelpString = "Shows how high a temperature the critical Part is enduring relative to it's maximal temperature."; IsDefault = true; } --- a/KerbalEngineer/Flight/Readouts/Thermal/HottestPart.cs +++ b/KerbalEngineer/Flight/Readouts/Thermal/HottestPart.cs @@ -27,7 +27,7 @@ { Name = "Hottest Part"; Category = ReadoutCategory.GetCategory("Thermal"); - HelpString = string.Empty; + HelpString = "The part of the vessel that is enduring the highest temperature."; IsDefault = true; } --- a/KerbalEngineer/Flight/Readouts/Thermal/HottestSkinTemperature.cs +++ b/KerbalEngineer/Flight/Readouts/Thermal/HottestSkinTemperature.cs @@ -28,7 +28,7 @@ { Name = "Hottest Skin Temperature"; Category = ReadoutCategory.GetCategory("Thermal"); - HelpString = string.Empty; + HelpString = "Highest external Temperature on the Vessel."; IsDefault = true; } --- a/KerbalEngineer/Flight/Readouts/Thermal/HottestTemperature.cs +++ b/KerbalEngineer/Flight/Readouts/Thermal/HottestTemperature.cs @@ -28,7 +28,7 @@ { Name = "Hottest Temperature"; Category = ReadoutCategory.GetCategory("Thermal"); - HelpString = string.Empty; + HelpString = "Highest internal Temperature on the Vessel."; IsDefault = true; } --- a/KerbalEngineer/Flight/Readouts/Vessel/Acceleration.cs +++ b/KerbalEngineer/Flight/Readouts/Vessel/Acceleration.cs @@ -34,7 +34,7 @@ { this.Name = "Acceleration"; this.Category = ReadoutCategory.GetCategory("Vessel"); - this.HelpString = string.Empty; + this.HelpString = "Shows the current and maximum acceleration of the craft."; this.IsDefault = true; } --- a/KerbalEngineer/Flight/Readouts/Vessel/Heading.cs +++ b/KerbalEngineer/Flight/Readouts/Vessel/Heading.cs @@ -34,7 +34,7 @@ { this.Name = "Heading"; this.Category = ReadoutCategory.GetCategory("Vessel"); - this.HelpString = string.Empty; + this.HelpString = "Shows the current Heading."; this.IsDefault = false; } --- a/KerbalEngineer/Flight/Readouts/Vessel/HeadingRate.cs +++ b/KerbalEngineer/Flight/Readouts/Vessel/HeadingRate.cs @@ -34,7 +34,7 @@ { this.Name = "Heading Rate"; this.Category = ReadoutCategory.GetCategory("Vessel"); - this.HelpString = string.Empty; + this.HelpString = "Shows the current change in Heading."; this.IsDefault = false; } --- a/KerbalEngineer/Flight/Readouts/Vessel/IntakeAirDemand.cs +++ b/KerbalEngineer/Flight/Readouts/Vessel/IntakeAirDemand.cs @@ -39,7 +39,7 @@ { this.Name = "Intake Air (Demand)"; this.Category = ReadoutCategory.GetCategory("Vessel"); - this.HelpString = string.Empty; + this.HelpString = "Displays the Amount of Intake Air required."; this.IsDefault = false; } --- a/KerbalEngineer/Flight/Readouts/Vessel/IntakeAirDemandSupply.cs +++ b/KerbalEngineer/Flight/Readouts/Vessel/IntakeAirDemandSupply.cs @@ -42,7 +42,7 @@ { this.Name = "Intake Air (D/S)"; this.Category = ReadoutCategory.GetCategory("Vessel"); - this.HelpString = string.Empty; + this.HelpString = "Displays the Ration between required and available Intake Air."; this.IsDefault = false; } @@ -55,10 +55,11 @@ var demand = 0.0; foreach (var part in FlightGlobals.ActiveVessel.Parts) { - if (part.Modules.Contains("ModuleEngines")) + for (int i = 0; i < part.Modules.Count; i++) { - var engine = part.Modules["ModuleEngines"] as ModuleEngines; - if (engine.isOperational) + PartModule partmod = part.Modules[i]; + var engine = partmod as ModuleEngines; + if (engine != null && engine.isOperational) { demand += engine.propellants .Where(p => p.name == "IntakeAir") --- a/KerbalEngineer/Flight/Readouts/Vessel/IntakeAirSupply.cs +++ b/KerbalEngineer/Flight/Readouts/Vessel/IntakeAirSupply.cs @@ -39,7 +39,7 @@ { this.Name = "Intake Air (Supply)"; this.Category = ReadoutCategory.GetCategory("Vessel"); - this.HelpString = string.Empty; + this.HelpString = "Displays the available Intake Air."; this.IsDefault = false; } --- a/KerbalEngineer/Flight/Readouts/Vessel/IntakeAirUsage.cs +++ b/KerbalEngineer/Flight/Readouts/Vessel/IntakeAirUsage.cs @@ -42,7 +42,7 @@ { this.Name = "Intake Air (Usage)"; this.Category = ReadoutCategory.GetCategory("Vessel"); - this.HelpString = string.Empty; + this.HelpString = "Displays the consumption of Intake Air."; this.IsDefault = true; } --- a/KerbalEngineer/Flight/Readouts/Vessel/Mass.cs +++ b/KerbalEngineer/Flight/Readouts/Vessel/Mass.cs @@ -34,7 +34,7 @@ { this.Name = "Mass"; this.Category = ReadoutCategory.GetCategory("Vessel"); - this.HelpString = string.Empty; + this.HelpString = "Displays the total Mass of the Vessel."; this.IsDefault = true; } --- /dev/null +++ b/KerbalEngineer/Flight/Readouts/Vessel/Name.cs @@ -1,1 +1,55 @@ +// +// Kerbal Engineer Redux +// +// Copyright (C) 2014 CYBUTEK +// +// This program is free software: you can redistribute it and/or modify +// it under the terms of the GNU General Public License as published by +// the Free Software Foundation, either version 3 of the License, or +// (at your option) any later version. +// +// This program is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU General Public License for more details. +// +// You should have received a copy of the GNU General Public License +// along with this program. If not, see . +// +#region Using Directives + +using KerbalEngineer.Flight.Sections; +using KerbalEngineer.Helpers; + +#endregion + +namespace KerbalEngineer.Flight.Readouts.Vessel +{ + public class Name : ReadoutModule + { + #region Constructors + + public Name() + { + Name = "Name"; + Category = ReadoutCategory.GetCategory("Vessel"); + HelpString = "Displays the name of the current vessel."; + IsDefault = true; + } + + #endregion + + #region Methods: public + + public override void Draw(SectionModule section) + { + if (SimulationProcessor.ShowDetails) + { + DrawLine(FlightGlobals.ActiveVessel.vesselName); + } + } + + #endregion + } +} --- a/KerbalEngineer/Flight/Readouts/Vessel/PartCount.cs +++ b/KerbalEngineer/Flight/Readouts/Vessel/PartCount.cs @@ -34,7 +34,7 @@ { this.Name = "Part Count"; this.Category = ReadoutCategory.GetCategory("Vessel"); - this.HelpString = string.Empty; + this.HelpString = "Shows the total number of Parts the current and next stage."; this.IsDefault = true; } --- a/KerbalEngineer/Flight/Readouts/Vessel/Pitch.cs +++ b/KerbalEngineer/Flight/Readouts/Vessel/Pitch.cs @@ -34,7 +34,7 @@ { this.Name = "Pitch"; this.Category = ReadoutCategory.GetCategory("Vessel"); - this.HelpString = string.Empty; + this.HelpString = "Shows the current Pitch angle."; this.IsDefault = false; } --- a/KerbalEngineer/Flight/Readouts/Vessel/PitchRate.cs +++ b/KerbalEngineer/Flight/Readouts/Vessel/PitchRate.cs @@ -34,7 +34,7 @@ { this.Name = "Pitch Rate"; this.Category = ReadoutCategory.GetCategory("Vessel"); - this.HelpString = string.Empty; + this.HelpString = "Shows the current Pitch speed."; this.IsDefault = false; } --- a/KerbalEngineer/Flight/Readouts/Vessel/Roll.cs +++ b/KerbalEngineer/Flight/Readouts/Vessel/Roll.cs @@ -34,7 +34,7 @@ { this.Name = "Roll"; this.Category = ReadoutCategory.GetCategory("Vessel"); - this.HelpString = string.Empty; + this.HelpString = "Shows the current Roll angle."; this.IsDefault = false; } --- a/KerbalEngineer/Flight/Readouts/Vessel/RollRate.cs +++ b/KerbalEngineer/Flight/Readouts/Vessel/RollRate.cs @@ -34,7 +34,7 @@ { this.Name = "Roll Rate"; this.Category = ReadoutCategory.GetCategory("Vessel"); - this.HelpString = string.Empty; + this.HelpString = "Shows the current Roll speed."; this.IsDefault = false; } --- a/KerbalEngineer/Flight/Readouts/Vessel/SpecificImpulse.cs +++ b/KerbalEngineer/Flight/Readouts/Vessel/SpecificImpulse.cs @@ -33,7 +33,7 @@ { this.Name = "Specific Impulse"; this.Category = ReadoutCategory.GetCategory("Vessel"); - this.HelpString = string.Empty; + this.HelpString = "Shows the average Specific Impulse of all engines in the current stage."; this.IsDefault = false; } --- a/KerbalEngineer/Flight/Readouts/Vessel/Thrust.cs +++ b/KerbalEngineer/Flight/Readouts/Vessel/Thrust.cs @@ -34,7 +34,7 @@ { this.Name = "Thrust"; this.Category = ReadoutCategory.GetCategory("Vessel"); - this.HelpString = string.Empty; + this.HelpString = "Shows the current and maximum thrust the vessel can put out."; this.IsDefault = true; } --- a/KerbalEngineer/Helpers/TimeFormatter.cs +++ b/KerbalEngineer/Helpers/TimeFormatter.cs @@ -1,7 +1,5 @@ // -// Kerbal Engineer Redux -// -// Copyright (C) 2014 CYBUTEK +// Copyright (C) 2015 CYBUTEK // // This program is free software: you can redistribute it and/or modify // it under the terms of the GNU General Public License as published by @@ -17,147 +15,46 @@ // along with this program. If not, see . // -#region Using Directives - -using System; - -using KerbalEngineer.Settings; - -#endregion - namespace KerbalEngineer.Helpers { public static class TimeFormatter { - #region Constructors - - static TimeFormatter() - { - SetReference(false); - Load(); - } - - #endregion - - #region Properties - - public static string Reference { get; set; } - - public static double SecondsPerDay { get; set; } - - public static double SecondsPerHour { get; set; } - - public static double SecondsPerMinute { get; set; } - - public static double SecondsPerYear { get; set; } - - #endregion - - #region Methods: public - public static string ConvertToString(double seconds, string format = "F1") { - var years = 0; - while (seconds >= SecondsPerYear) + int years = 0; + int days = 0; + int hours = 0; + int minutes = 0; + + if (seconds > 0.0) { - years++; - seconds -= SecondsPerYear; - } + years = (int)(seconds / KSPUtil.Year); + seconds -= years * KSPUtil.Year; - var days = 0; - while (seconds >= SecondsPerDay) - { - days++; - seconds -= SecondsPerDay; - } + days = (int)(seconds / KSPUtil.Day); + seconds -= days * KSPUtil.Day; - var hours = 0; - while (seconds >= SecondsPerHour) - { - hours++; - seconds -= SecondsPerHour; - } + hours = (int)(seconds / 3600.0); + seconds -= hours * 3600.0; - var minutes = 0; - while (seconds >= SecondsPerMinute) - { - minutes++; - seconds -= SecondsPerMinute; + minutes = (int)(seconds / 60.0); + seconds -= minutes * 60.0; } if (years > 0) { - return String.Format("{0}y {1}d {2}h {3}m {4}s", years, days, hours, minutes, seconds.ToString(format)); + return string.Format("{0}y {1}d {2}h {3}m {4}s", years, days, hours, minutes, seconds.ToString(format)); } if (days > 0) { - return String.Format("{0}d {1}h {2}m {3}s", days, hours, minutes, seconds.ToString(format)); + return string.Format("{0}d {1}h {2}m {3}s", days, hours, minutes, seconds.ToString(format)); } if (hours > 0) { - return String.Format("{0}h {1}m {2}s", hours, minutes, seconds.ToString(format)); + return string.Format("{0}h {1}m {2}s", hours, minutes, seconds.ToString(format)); } - return minutes > 0 ? String.Format("{0}m {1}s", minutes, seconds.ToString(format)) : String.Format("{0}s", seconds.ToString(format)); + return minutes > 0 ? string.Format("{0}m {1}s", minutes, seconds.ToString(format)) : string.Format("{0}s", seconds.ToString(format)); } - - public static void Load() - { - var handler = SettingHandler.Load("TimeFormatter.xml"); - SecondsPerMinute = handler.Get("SecondsPerMinute", SecondsPerMinute); - SecondsPerHour = handler.Get("SecondsPerHour", SecondsPerHour); - SecondsPerDay = handler.Get("SecondsPerDay", SecondsPerDay); - SecondsPerYear = handler.Get("SecondsPerYear", SecondsPerYear); - Reference = handler.Get("Reference", Reference); - } - - public static void Save() - { - var handler = SettingHandler.Load("TimeFormatter.xml"); - handler.Set("SecondsPerMinute", SecondsPerMinute); - handler.Set("SecondsPerHour", SecondsPerHour); - handler.Set("SecondsPerDay", SecondsPerDay); - handler.Set("SecondsPerYear", SecondsPerYear); - handler.Set("Reference", Reference); - handler.Save("TimeFormatter.xml"); - } - - public static void SetReference(bool save = true) - { - const double minute = 60.0; - const double hour = minute * 60.0; - const double day = hour * 24.0; - const double year = day * 365.0; - SetReference(minute, hour, day, year, "Earth", save); - } - - public static void SetReference(CelestialBody body, bool save = true) - { - SetReference(SecondsPerMinute, SecondsPerHour, body.rotationPeriod, body.orbit.period, body.bodyName, save); - } - - public static void SetReference(double minute, double hour, double day, double year, string reference, bool save = true) - { - SecondsPerMinute = minute; - SecondsPerHour = hour; - SecondsPerDay = day; - SecondsPerYear = year; - Reference = reference; - - if (save) - { - Save(); - } - } - - public new static string ToString() - { - return String.Format("SecondsPerMinute: {0}", SecondsPerMinute) + Environment.NewLine + - String.Format("SecondsPerHour: {0}", SecondsPerHour) + Environment.NewLine + - String.Format("SecondsPerDay: {0}", SecondsPerDay) + Environment.NewLine + - String.Format("SecondsPerYear: {0}", SecondsPerYear) + Environment.NewLine; - } - - #endregion } } --- a/KerbalEngineer/Helpers/Units.cs +++ b/KerbalEngineer/Helpers/Units.cs @@ -205,7 +205,7 @@ public static string ToTorque(double value) { - return value.ToString((value < 100.0) ? (Math.Abs(value) < Double.Epsilon) ? "N0" : "N1" : "N0") + "kNm"; + return value.ToString((value < 100.0) ? (Math.Abs(value) < Double.Epsilon) ? "N0" : "N2" : "N0") + "kNm"; } } } --- a/KerbalEngineer/KerbalEngineer.csproj +++ b/KerbalEngineer/KerbalEngineer.csproj @@ -53,7 +53,6 @@ - @@ -71,11 +70,21 @@ + + + + Code + + + + Code + + @@ -105,6 +114,7 @@ + @@ -161,7 +171,6 @@ - @@ -221,6 +230,8 @@ + + --- a/KerbalEngineer/LogMsg.cs +++ b/KerbalEngineer/LogMsg.cs @@ -15,7 +15,8 @@ public void Flush() { - MonoBehaviour.print(this.buf); + if (this.buf.Length > 0) + MonoBehaviour.print(this.buf); this.buf.Length = 0; } } --- a/KerbalEngineer/VesselSimulator/EngineSim.cs +++ b/KerbalEngineer/VesselSimulator/EngineSim.cs @@ -273,14 +273,36 @@ HashSet visited = new HashSet(); + public void DumpSourcePartSets(String msg) + { + MonoBehaviour.print("DumpSourcePartSets " + msg); + foreach (int type in sourcePartSets.Keys) + { + MonoBehaviour.print("SourcePartSet for " + ResourceContainer.GetResourceName(type)); + HashSet sourcePartSet = sourcePartSets[type]; + if (sourcePartSet.Count > 0) + { + foreach (PartSim partSim in sourcePartSet) + { + MonoBehaviour.print("Part " + partSim.name + ":" + partSim.partId); + } + } + else + { + MonoBehaviour.print("No parts"); + } + } + } + public bool SetResourceDrains(List allParts, List allFuelLines, HashSet drainingParts) { LogMsg log = null; - + //DumpSourcePartSets("before clear"); foreach (HashSet sourcePartSet in sourcePartSets.Values) { sourcePartSet.Clear(); } + //DumpSourcePartSets("after clear"); for (int index = 0; index < this.resourceConsumptions.Types.Count; index++) { @@ -338,20 +360,27 @@ maxStage = stage; } - if (!stagePartSets.TryGetValue(stage, out sourcePartSet)) + HashSet tempPartSet; + if (!stagePartSets.TryGetValue(stage, out tempPartSet)) { - sourcePartSet = new HashSet(); - stagePartSets.Add(stage, sourcePartSet); + tempPartSet = new HashSet(); + stagePartSets.Add(stage, tempPartSet); } - sourcePartSet.Add(aPartSim); - } - - for (int j = 0; j <= maxStage; j++) + tempPartSet.Add(aPartSim); + } + + for (int j = maxStage; j >= 0; j--) { HashSet stagePartSet; if (stagePartSets.TryGetValue(j, out stagePartSet) && stagePartSet.Count > 0) { - sourcePartSet = stagePartSet; + // We have to copy the contents of the set here rather than copying the set reference or + // bad things (tm) happen + foreach (PartSim aPartSim in stagePartSet) + { + sourcePartSet.Add(aPartSim); + } + break; } } break; @@ -376,11 +405,9 @@ break; } - - if (sourcePartSet.Count > 0) - { - sourcePartSets[type] = sourcePartSet; - if (SimManager.logOutput) + if (SimManager.logOutput) + { + if (sourcePartSet.Count > 0) { log = new LogMsg(); log.buf.AppendLine("Source parts for " + ResourceContainer.GetResourceName(type) + ":"); @@ -391,6 +418,8 @@ MonoBehaviour.print(log.buf); } } + + //DumpSourcePartSets("after " + ResourceContainer.GetResourceName(type)); } // If we don't have sources for all the needed resources then return false without setting up any drains @@ -409,6 +438,7 @@ return false; } } + // Now we set the drains on the members of the sets and update the draining parts set for (int i = 0; i < this.resourceConsumptions.Types.Count; i++) { --- a/KerbalEngineer/VesselSimulator/Simulation.cs +++ b/KerbalEngineer/VesselSimulator/Simulation.cs @@ -30,6 +30,7 @@ namespace KerbalEngineer.VesselSimulator { + using System.ComponentModel; using CompoundParts; using Extensions; using Helpers; @@ -675,21 +676,28 @@ for (int i = 0; i < this.allParts.Count; i++) { PartSim part = this.allParts[i]; - // If the part has a parent - if (part.parent != null) - { - if (part.isNoPhysics) - { - if (part.parent.isNoPhysics && part.parent.parent != null) - { - part.baseMass = 0d; - part.baseMassForCoM = 0d; - } - else - { - part.parent.baseMassForCoM += part.baseMassForCoM; - part.baseMassForCoM = 0d; - } + + // Check if part should pass it's mass onto its parent. + if (part.isNoPhysics && part.parent != null) + { + PartSim partParent = part.parent; + + // Loop through all parents until a physically significant parent is found. + while (partParent != null) + { + // Check if parent is physically significant. + if (partParent.isNoPhysics == false) + { + // Apply the mass to the parent and remove it from the originating part. + partParent.baseMassForCoM += part.baseMassForCoM; + part.baseMassForCoM = 0.0; + + // Break out of the recursive loop. + break; + } + + // Recursively loop through the parent parts. + partParent = partParent.parent; } } } --- a/Output/KerbalEngineer/KerbalEngineer.version +++ b/Output/KerbalEngineer/KerbalEngineer.version @@ -1,11 +1,11 @@ { - "NAME":"Kerbal Engineer Redux 1.0", + "NAME":"Kerbal Engineer Redux", "URL":"http://ksp-avc.cybutek.net/version.php?id=6", "VERSION": { "MAJOR":1, "MINOR":0, - "PATCH":17, + "PATCH":18, "BUILD":0 }, "KSP_VERSION": @@ -15,3 +15,4 @@ "PATCH":4 } } +