// GUI private void WindowGUI(int windowID) { // General GUI window information GUIStyle mySty = new GUIStyle(GUI.skin.button); mySty.normal.textColor = mySty.focused.textColor = Color.white; mySty.hover.textColor = mySty.active.textColor = Color.yellow; mySty.onNormal.textColor = mySty.onFocused.textColor = mySty.onHover.textColor = mySty.onActive.textColor = Color.green; mySty.padding = new RectOffset(2, 2, 2, 2); GUILayout.BeginVertical(); GUILayout.Label("Buoyancy on:"); currentSelection = GUILayout.SelectionGrid(currentSelection, selStringArray, 1); currentBody = BodyRef[currentSelection]; GUILayout.Label("Envelope Volume: " + TotalEnvelopeVolume); string mass = "?"; double buoyancy = ComputeMaxBuoyancy(); mass = TotalMass.ToString("00.00"); // weight double weight = TotalMass * FlightGlobals.Bodies[currentBody].GeeASL * 9.81; double netForce = buoyancy - weight; GUILayout.Label("Vessel Mass: " + mass + "T"); GUILayout.Label("Net Buoyancy: " + netForce.ToString("00.00") + "KN"); try { if (netForce > 0) { float tippingPoint = 0f; Keyframe[] frames = null; float maxAltitude = 100000; int frameIndex = 0; bool useCurve = true; if (useCurve) { frames = FlightGlobals.Bodies[currentBody].atmosphereTemperatureCurve.Curve.keys; maxAltitude = frames[frames.Length - 1].time; } // compute equilibrium altitude for (float i = 100f; i < maxAltitude; i += 100f) { double pressure = FlightGlobals.Bodies[currentBody].GetPressure(i); // Compute the buoyant force // KSP provides the density based on local atmospheric pressure. double atmosDensity = pressure / (287.058 * FlightGlobals.Bodies[currentBody].atmosphereTemperatureSeaLevel); if (useCurve) { // walk the curve forward if needed if (frameIndex < frames.Length - 1 && i > frames[frameIndex + 1].time) { frameIndex++; } // linear interpolation is close enough for now float tempCurve = ((i - frames[frameIndex].time) / (frames[frameIndex + 1].time - frames[frameIndex].time)) * (frames[frameIndex + 1].value - frames[frameIndex].value) + frames[frameIndex].value; atmosDensity = pressure / (287.058 * tempCurve); } // The maximum buoyancy of the envelope is equal to the weight of the displaced air // Force (Newtons) = - Gravitational Acceleration (meters per second squared) * Density (kilograms / meter cubed) * Volume (meters cubed) double maxBuoyancy = FlightGlobals.Bodies[currentBody].GeeASL * 9.81 * atmosDensity * TotalEnvelopeVolume; if (maxBuoyancy < weight) { tippingPoint = i; break; } } if (tippingPoint > 0) { GUILayout.Label("Equilibrium Altitude : " + tippingPoint.ToString() + "m"); } } else { GUILayout.Label("Equilibrium Altitude : Won't Fly"); } } catch (Exception) { GUILayout.Label("Equilibrium Altitude : Unknown"); } GUILayout.EndVertical(); GUI.DragWindow(new Rect(0, 0, 500, 20)); }