VOID_DataLogger: Misc improvements to file structure.
VOID_DataLogger: Misc improvements to file structure.

--- a/Properties/AssemblyInfo.cs
+++ b/Properties/AssemblyInfo.cs
@@ -39,7 +39,7 @@
 // The assembly version has the format "{Major}.{Minor}.{Build}.{Revision}".
 // The form "{Major}.{Minor}.*" will automatically update the build and revision,
 // and "{Major}.{Minor}.{Build}.*" will update just the revision.
-[assembly: AssemblyVersion("0.14.3.*")]
+[assembly: AssemblyVersion("0.15.*")]
 // The following attributes are used to specify the signing key for the assembly,
 // if desired. See the Mono documentation for more information about signing.
 //[assembly: AssemblyDelaySign(false)]

--- a/VOID_Core.cs
+++ b/VOID_Core.cs
@@ -120,9 +120,8 @@
 		protected int _windowID = 0;
 
 		protected bool GUIStylesLoaded = false;
-		protected Dictionary<string, GUIStyle> _LabelStyles = new Dictionary<string, GUIStyle>();
-
-		protected CelestialBody _Kerbin;
+
+		protected CelestialBody _homeBody;
 
 		[AVOID_SaveValue("togglePower")]
 		public VOID_SaveValue<bool> togglePower = true;
@@ -230,14 +229,6 @@
 			}
 		}
 
-		public Dictionary<string, GUIStyle> LabelStyles
-		{
-			get
-			{
-				return this._LabelStyles;
-			}
-		}
-
 		public List<CelestialBody> allBodies
 		{
 			get
@@ -252,19 +243,19 @@
 			private set;
 		}
 
-		public CelestialBody Kerbin
-		{
-			get
-			{
-				if (this._Kerbin == null)
-				{
-					if (FlightGlobals.Bodies != null)
+		public CelestialBody HomeBody
+		{
+			get
+			{
+				if (this._homeBody == null)
+				{
+					if (Planetarium.fetch != null)
 					{
-						this._Kerbin = FlightGlobals.Bodies.First(b => b.name == "Kerbin");
+						this._homeBody = Planetarium.fetch.Home;
 					}
 				}
 
-				return this._Kerbin;
+				return this._homeBody;
 			}
 		}
 

--- a/VOID_Data.cs
+++ b/VOID_Data.cs
@@ -37,6 +37,15 @@
 {
 	public static class VOID_Data
 	{
+		private static Dictionary<int, IVOID_DataValue> dataValues = new Dictionary<int, IVOID_DataValue>();
+		public static Dictionary<int, IVOID_DataValue> DataValues
+		{
+			get
+			{
+				return dataValues;
+			}
+		}
+
 		#region Constants
 
 		private static double kerbinGee;
@@ -47,7 +56,7 @@
 			{
 				if (kerbinGee == default(double))
 				{
-					kerbinGee = core.Kerbin.gravParameter / (core.Kerbin.Radius * core.Kerbin.Radius);
+					kerbinGee = core.HomeBody.gravParameter / (core.HomeBody.Radius * core.HomeBody.Radius);
 				}
 
 				return kerbinGee;

--- a/VOID_DataLogger.cs
+++ b/VOID_DataLogger.cs
@@ -53,6 +53,8 @@
 
 		protected double csvWriteTimer;
 		protected double csvCollectTimer;
+
+		protected System.Text.UTF8Encoding enc;
 
 		protected List<string> csvList = new List<string>();
 
@@ -197,12 +199,34 @@
 
 		private void Innsewerants_writeData(string[] csvArray)
 		{
-			var efile = KSP.IO.File.AppendText<VOID_Core>(vessel.vesselName + "_data.csv", null);
+			if (this.enc == null)
+			{
+				this.enc = new System.Text.UTF8Encoding(true, true);
+			}
+
+			KSP.IO.FileStream bFile;
+
+			if (KSP.IO.File.Exists<VOID_Core>(vessel.vesselName + "_data.csv", null))
+			{
+				bFile = KSP.IO.File.Open<VOID_Core>(vessel.vesselName + "_data.csv", KSP.IO.FileMode.Append, null);
+			}
+			else
+			{
+				bFile = KSP.IO.File.Open<VOID_Core>(vessel.vesselName + "_data.csv", KSP.IO.FileMode.Create, null);
+
+				byte[] bom = enc.GetPreamble();
+
+				bFile.Write(bom, 0, bom.Length);
+			}
+
 			foreach (string line in csvArray)
 			{
-				efile.Write(line);
-			}
-			efile.Close();
+				byte[] lineBytes = enc.GetBytes(line);
+
+				bFile.Write(lineBytes, 0, lineBytes.Length);
+			}
+
+			bFile.Dispose();
 		}
 
 		private void line_to_csvList()
@@ -212,87 +236,90 @@
 
 			StringBuilder line = new StringBuilder();
 
-			if (first_write && !KSP.IO.File.Exists<VOID_Core>(vessel.vesselName + "_data.csv", null))
+			if (first_write)
 			{
 				first_write = false;
 				line.Append(
-					"Mission Elapsed Time (s);" +
-					"Altitude ASL (m);" +
-					"Altitude above terrain (m);" +
-					"Surface Latitude (°);" +
-					"Surface Longitude (°);" +
-					"Orbital Velocity (m/s);" +
-					"Surface Velocity (m/s);" +
-					"Vertical Speed (m/s);" +
-					"Horizontal Speed (m/s);" +
-					"Gee Force (gees);" +
-					"Temperature (°C);" +
-					"Gravity (m/s²);" +
-					"Atmosphere Density (g/m³);" +
-					"Downrange Distance  (m);" +
+					"\"Mission Elapsed Time (s)\t\"," +
+					"\"Altitude ASL (m)\"," +
+					"\"Altitude above terrain (m)\"," +
+					"\"Surface Latitude (°)\"," +
+					"\"Surface Longitude (°)\"," +
+					"\"Orbital Velocity (m/s)\"," +
+					"\"Surface Velocity (m/s)\"," +
+					"\"Vertical Speed (m/s)\"," +
+					"\"Horizontal Speed (m/s)\"," +
+					"\"Gee Force (gees)\"," +
+					"\"Temperature (°C)\"," +
+					"\"Gravity (m/s²)\"," +
+					"\"Atmosphere Density (g/m³)\"," +
+					"\"Downrange Distance  (m)\"," +
 					"\n"
 				);
 			}
 
 			//Mission time
 			line.Append(vessel.missionTime.ToString("F3"));
-			line.Append(';');
+			line.Append(',');
 
 			//Altitude ASL
 			line.Append(vessel.orbit.altitude.ToString("F3"));
-			line.Append(';');
+			line.Append(',');
 
 			//Altitude (true)
 			double alt_true = vessel.orbit.altitude - vessel.terrainAltitude;
 			if (vessel.terrainAltitude < 0) alt_true = vessel.orbit.altitude;
 			line.Append(alt_true.ToString("F3"));
-			line.Append(';');
+			line.Append(',');
 
 			// Surface Latitude
+			line.Append('"');
 			line.Append(VOID_Data.surfLatitude.Value);
-			line.Append(';');
+			line.Append('"');
+			line.Append(',');
 
 			// Surface Longitude
+			line.Append('"');
 			line.Append(VOID_Data.surfLongitude.Value);
-			line.Append(';');
+			line.Append('"');
+			line.Append(',');
 
 			//Orbital velocity
 			line.Append(vessel.orbit.vel.magnitude.ToString("F3"));
-			line.Append(';');
+			line.Append(',');
 
 			//surface velocity
 			line.Append(vessel.srf_velocity.magnitude.ToString("F3"));
-			line.Append(';');
+			line.Append(',');
 
 			//vertical speed
 			line.Append(vessel.verticalSpeed.ToString("F3"));
-			line.Append(';');
+			line.Append(',');
 
 			//horizontal speed
 			line.Append(vessel.horizontalSrfSpeed.ToString("F3"));
-			line.Append(';');
+			line.Append(',');
 
 			//gee force
 			line.Append(vessel.geeForce.ToString("F3"));
-			line.Append(';');
+			line.Append(',');
 
 			//temperature
 			line.Append(vessel.flightIntegrator.getExternalTemperature().ToString("F2"));
-			line.Append(';');
+			line.Append(',');
 
 			//gravity
 			double r_vessel = vessel.mainBody.Radius + vessel.mainBody.GetAltitude(vessel.findWorldCenterOfMass());
 			double g_vessel = (VOID_Core.Constant_G * vessel.mainBody.Mass) / (r_vessel * r_vessel);
 			line.Append(g_vessel.ToString("F3"));
-			line.Append(';');
+			line.Append(',');
 
 			//atm density
 			line.Append((vessel.atmDensity * 1000).ToString("F3"));
-			line.Append(';');
+			line.Append(',');
 
 			// Downrange Distance
 			line.Append((VOID_Data.downrangeDistance.Value.ToString("G3")));
-			line.Append(';');
 
 			line.Append('\n');
 

--- a/VOID_DataValue.cs
+++ b/VOID_DataValue.cs
@@ -34,6 +34,10 @@
 {
 	public interface IVOID_DataValue
 	{
+		string Label { get; }
+		string Units { get; }
+		object Value { get; }
+
 		void Refresh();
 		string ValueUnitString();
 		void DoGUIHorizontal();
@@ -64,6 +68,14 @@
 		 * */
 		public string Label { get; protected set; }
 		public string Units { get; protected set; }
+
+		object IVOID_DataValue.Value
+		{
+			get
+			{
+				return (object)this.Value;
+			}
+		}
 
 		public T Value
 		{
@@ -90,6 +102,8 @@
 			this.Units = Units;
 			this.ValueFunc = ValueFunc;
 			this.lastUpdate = 0;
+
+			VOID_Data.DataValues[this.GetHashCode()] = this;
 		}
 
 		public void Refresh()
@@ -115,6 +129,21 @@
 			GUILayout.FlexibleSpace ();
 			GUILayout.Label (this.ValueUnitString(), GUILayout.ExpandWidth (false));
 			GUILayout.EndHorizontal ();
+		}
+
+		public override int GetHashCode()
+		{
+			int hash;
+			unchecked
+			{
+				hash = 79999;
+
+				hash = hash * 104399 + this.Label.GetHashCode();
+				hash = hash * 104399 + this.ValueFunc.GetHashCode();
+				hash = hash * 104399 + this.Units.GetHashCode();
+			}
+
+			return hash;
 		}
 
 		public override string ToString()

--- a/VOID_HUD.cs
+++ b/VOID_HUD.cs
@@ -118,7 +118,7 @@
 
 			leftHUD = new StringBuilder();
 
-			this.core.LabelStyles["hud"].alignment = TextAnchor.UpperRight;
+			VOID_Styles.labelHud.alignment = TextAnchor.UpperRight;
 
 			if (this.core.powerAvailable)
 			{
@@ -145,11 +145,11 @@
 			}
 			else
 			{
-				this.core.LabelStyles["hud"].normal.textColor = Color.red;
+				VOID_Styles.labelHud.normal.textColor = Color.red;
 				leftHUD.Append(string.Intern("-- POWER LOST --"));
 			}
 
-			GUILayout.Label(leftHUD.ToString(), this.core.LabelStyles["hud"], GUILayout.ExpandWidth(true));
+			GUILayout.Label(leftHUD.ToString(), VOID_Styles.labelHud, GUILayout.ExpandWidth(true));
 
 			if (!this.positionsLocked)
 			{
@@ -165,7 +165,7 @@
 
 			rightHUD = new StringBuilder();
 
-			this.core.LabelStyles["hud"].alignment = TextAnchor.UpperLeft;
+			VOID_Styles.labelHud.alignment = TextAnchor.UpperLeft;
 
 			if (this.core.powerAvailable)
 			{
@@ -191,7 +191,7 @@
 				);
 
 				if (
-					this.core.vessel.mainBody == this.core.Kerbin &&
+					this.core.vessel.mainBody == this.core.HomeBody &&
 					(
 						this.core.vessel.situation == Vessel.Situations.FLYING ||
 						this.core.vessel.situation == Vessel.Situations.SUB_ORBITAL ||
@@ -205,12 +205,12 @@
 			}
 			else
 			{
-				this.core.LabelStyles["hud"].normal.textColor = Color.red;
+				VOID_Styles.labelHud.normal.textColor = Color.red;
 				rightHUD.Append(string.Intern("-- POWER LOST --"));
 			}
 
 
-			GUILayout.Label(rightHUD.ToString(), this.core.LabelStyles["hud"], GUILayout.ExpandWidth(true));
+			GUILayout.Label(rightHUD.ToString(), VOID_Styles.labelHud, GUILayout.ExpandWidth(true));
 
 			if (!this.positionsLocked)
 			{
@@ -222,12 +222,7 @@
 
 		public override void DrawGUI()
 		{
-			if (!this.core.LabelStyles.ContainsKey("hud"))
-			{
-				this.core.LabelStyles["hud"] = new GUIStyle(GUI.skin.label);
-			}
-
-			this.core.LabelStyles["hud"].normal.textColor = textColors [ColorIndex];
+			VOID_Styles.labelHud.normal.textColor = textColors [ColorIndex];
 
 			GUI.skin = this.core.Skin;
 

--- a/VOID_HUDAdvanced.cs
+++ b/VOID_HUDAdvanced.cs
@@ -105,7 +105,7 @@
 
 			leftHUD = new StringBuilder();
 
-			this.core.LabelStyles["hud"].alignment = TextAnchor.UpperRight;
+			VOID_Styles.labelHud.alignment = TextAnchor.UpperRight;
 
 			if (this.core.powerAvailable)
 			{
@@ -144,11 +144,11 @@
 			}
 			else
 			{
-				this.core.LabelStyles["hud"].normal.textColor = Color.red;
+				VOID_Styles.labelHud.normal.textColor = Color.red;
 				leftHUD.Append(string.Intern("-- POWER LOST --"));
 			}
 
-			GUILayout.Label(leftHUD.ToString(), this.core.LabelStyles["hud"], GUILayout.ExpandWidth(true));
+			GUILayout.Label(leftHUD.ToString(), VOID_Styles.labelHud, GUILayout.ExpandWidth(true));
 
 			if (!this.positionsLocked)
 			{
@@ -164,7 +164,7 @@
 
 			rightHUD = new StringBuilder();
 
-			this.core.LabelStyles["hud"].alignment = TextAnchor.UpperLeft;
+			VOID_Styles.labelHud.alignment = TextAnchor.UpperLeft;
 
 			if (this.core.powerAvailable)
 			{
@@ -203,11 +203,11 @@
 			}
 			else
 			{
-				this.core.LabelStyles["hud"].normal.textColor = Color.red;
+				VOID_Styles.labelHud.normal.textColor = Color.red;
 				rightHUD.Append(string.Intern("-- POWER LOST --"));
 			}
 
-			GUILayout.Label(rightHUD.ToString(), this.core.LabelStyles["hud"], GUILayout.ExpandWidth(true));
+			GUILayout.Label(rightHUD.ToString(), VOID_Styles.labelHud, GUILayout.ExpandWidth(true));
 
 			if (!this.positionsLocked)
 			{

--- a/VOID_StageInfo.cs
+++ b/VOID_StageInfo.cs
@@ -20,6 +20,7 @@
 		private Table.Column<int> stageNumberCol;
 		private Table.Column<double> stageDeltaVCol;
 		private Table.Column<double> stageTotalDVCol;
+		private Table.Column<double> stageInvertDVCol;
 		private Table.Column<double> stageMassCol;
 		private Table.Column<double> stageTotalMassCol;
 		private Table.Column<double> stageThrustCol;
@@ -51,27 +52,31 @@
 			this.stageNumberCol = new Table.Column<int>("Stage", 40f);
 			this.stageTable.Add(this.stageNumberCol);
 
-			this.stageDeltaVCol = new Table.Column<double>("DeltaV [m/s]", 80f);
+			this.stageDeltaVCol = new Table.Column<double>("DeltaV [m/s]", 60f);
 			this.stageDeltaVCol.Format = "S2";
 			this.stageTable.Add(this.stageDeltaVCol);
 
-			this.stageTotalDVCol = new Table.Column<double>("Total ΔV [m/s]", 80f);
+			this.stageTotalDVCol = new Table.Column<double>("Total ΔV [m/s]", 60f);
 			this.stageTotalDVCol.Format = "S2";
 			this.stageTable.Add(this.stageTotalDVCol);
 
-			this.stageMassCol = new Table.Column<double>("Mass [Mg]", 80f);
+			this.stageInvertDVCol = new Table.Column<double>("Invert ΔV [m/s]", 60f);
+			this.stageInvertDVCol.Format = "S2";
+			this.stageTable.Add(this.stageInvertDVCol);
+
+			this.stageMassCol = new Table.Column<double>("Mass [Mg]", 60f);
 			this.stageMassCol.Format = "#.#";
 			this.stageTable.Add(this.stageMassCol);
 
-			this.stageTotalMassCol = new Table.Column<double>("Total Mass [Mg]", 80f);
+			this.stageTotalMassCol = new Table.Column<double>("Total [Mg]", 60f);
 			this.stageTotalMassCol.Format = "#.#";
 			this.stageTable.Add(this.stageTotalMassCol);
 
-			this.stageThrustCol = new Table.Column<double>("Thrust [N]", 80f);
+			this.stageThrustCol = new Table.Column<double>("Thrust [N]", 60f);
 			this.stageThrustCol.Format = "S2";
 			this.stageTable.Add(this.stageThrustCol);
 
-			this.stageTWRCol = new Table.Column<double>("T/W Ratio", 80f);
+			this.stageTWRCol = new Table.Column<double>("T/W Ratio", 60f);
 			this.stageTWRCol.Format = "#.#";
 			this.stageTable.Add(this.stageTWRCol);
 		}
@@ -127,12 +132,13 @@
 
 				this.stageDeltaVCol.Add(stage.deltaV);
 				this.stageTotalDVCol.Add(stage.totalDeltaV);
+				this.stageInvertDVCol.Add(stage.inverseTotalDeltaV);
 
 				this.stageMassCol.Add(stage.mass);
 				this.stageTotalMassCol.Add(stage.totalMass);      
 
 				this.stageThrustCol.Add(stage.thrust * 1000f);
-				this.stageTWRCol.Add(stage.thrustToWeight / (this.selectedBody ?? core.Kerbin).GeeASL);
+				this.stageTWRCol.Add(stage.thrustToWeight / (this.selectedBody ?? core.HomeBody).GeeASL);
 			}
 
 			this.stageTable.Render();
@@ -146,7 +152,7 @@
 					this.bodyIdx--;
 				}
 
-				this.showBodyList = GUILayout.Toggle(this.showBodyList, (this.selectedBody ?? core.Kerbin).bodyName, GUI.skin.button);
+				this.showBodyList = GUILayout.Toggle(this.showBodyList, (this.selectedBody ?? core.HomeBody).bodyName, GUI.skin.button);
 				Rect bodyButtonPos = GUILayoutUtility.GetLastRect();
 
 				if (Event.current.type == EventType.Repaint)

--- a/VOID_Styles.cs
+++ b/VOID_Styles.cs
@@ -28,14 +28,6 @@
 
 using System;
 using UnityEngine;
-
-#if COMMENT
-this.LabelStyles["link"] = new GUIStyle(GUI.skin.label);
-this.LabelStyles["center"] = new GUIStyle(GUI.skin.label);
-this.LabelStyles["center_bold"] = new GUIStyle(GUI.skin.label);
-this.LabelStyles["right"] = new GUIStyle(GUI.skin.label);
-labelRed = new GUIStyle(GUI.skin.label);
-#endif
 
 namespace VOID
 {
@@ -71,6 +63,12 @@
 			private set;
 		}
 
+		public static GUIStyle labelHud
+		{
+			get;
+			private set;
+		}
+
 		public static GUIStyle labelRight
 		{
 			get;
@@ -100,6 +98,8 @@
 			labelCenterBold.alignment = TextAnchor.UpperCenter;
 			labelCenterBold.fontStyle = FontStyle.Bold;
 
+			labelHud = new GUIStyle(labelDefault);
+
 			labelRight = new GUIStyle(GUI.skin.label);
 			labelRight.normal.textColor = Color.white;
 			labelRight.alignment = TextAnchor.UpperRight;