General cleanup of SimManager start-up and calling.
[VOID.git] / VOIDCore_Generic.cs
blob:a/VOIDCore_Generic.cs -> blob:b/VOIDCore_Generic.cs
// VOID // VOID
// //
// VOIDCore_Generic.cs // VOIDCore_Generic.cs
// //
// Copyright © 2014, toadicus // Copyright © 2014, toadicus
// All rights reserved. // All rights reserved.
// //
// Redistribution and use in source and binary forms, with or without modification, // Redistribution and use in source and binary forms, with or without modification,
// are permitted provided that the following conditions are met: // are permitted provided that the following conditions are met:
// //
// 1. Redistributions of source code must retain the above copyright notice, // 1. Redistributions of source code must retain the above copyright notice,
// this list of conditions and the following disclaimer. // this list of conditions and the following disclaimer.
// //
// 2. Redistributions in binary form must reproduce the above copyright notice, // 2. Redistributions in binary form must reproduce the above copyright notice,
// this list of conditions and the following disclaimer in the documentation and/or other // this list of conditions and the following disclaimer in the documentation and/or other
// materials provided with the distribution. // materials provided with the distribution.
// //
// 3. Neither the name of the copyright holder nor the names of its contributors may be used // 3. Neither the name of the copyright holder nor the names of its contributors may be used
// to endorse or promote products derived from this software without specific prior written permission. // to endorse or promote products derived from this software without specific prior written permission.
// //
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES,
// INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE // INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
// DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, // DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR // SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
// SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, // SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
// WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE // WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. // OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
   
using KerbalEngineer.Editor; using KerbalEngineer.Editor;
using KerbalEngineer.Helpers; using KerbalEngineer.Helpers;
using KerbalEngineer.VesselSimulator; using KerbalEngineer.VesselSimulator;
using KSP; using KSP;
using System; using System;
using System.Collections.Generic; using System.Collections.Generic;
using System.Linq; using System.Linq;
using System.Text; using System.Text;
using ToadicusTools; using ToadicusTools;
using UnityEngine; using UnityEngine;
   
namespace VOID namespace VOID
{ {
public abstract class VOIDCore_Generic<T> : VOID_SingletonCore<T>, IVOID_Module, IDisposable public abstract class VOIDCore_Generic<T> : VOID_SingletonCore<T>, IVOID_Module, IDisposable
where T : VOID_Module, new() where T : VOID_Module, new()
{ {
/* /*
* Fields * Fields
* */ * */
protected string VoidName = "VOID"; protected string VoidName = "VOID";
protected string VoidVersion; protected string VoidVersion;
   
[AVOID_SaveValue("configValue")] [AVOID_SaveValue("configValue")]
protected VOID_SaveValue<int> configVersion = (VOID_SaveValue<int>)VOIDCore.CONFIG_VERSION; protected VOID_SaveValue<int> configVersion = (VOID_SaveValue<int>)VOIDCore.CONFIG_VERSION;
   
protected List<IVOID_Module> modules = new List<IVOID_Module>(); protected List<IVOID_Module> modules = new List<IVOID_Module>();
protected bool modulesLoaded = false; protected bool modulesLoaded = false;
   
protected Texture2D VOIDIconTexture; protected Texture2D VOIDIconTexture;
protected string VOIDIconOnActivePath; protected string VOIDIconOnActivePath;
protected string VOIDIconOnInactivePath; protected string VOIDIconOnInactivePath;
protected string VOIDIconOffActivePath; protected string VOIDIconOffActivePath;
protected string VOIDIconOffInactivePath; protected string VOIDIconOffInactivePath;
   
private bool _useToolbarManager; [AVOID_SaveValue("useToolbarManager")]
  protected VOID_SaveValue<bool> useToolbarManager;
   
protected GUIStyle iconStyle; protected GUIStyle iconStyle;
   
protected int windowBaseID = -96518722; protected int windowBaseID = -96518722;
protected int windowID = 0; protected int windowID = 0;
   
protected bool GUIStylesLoaded = false; protected bool GUIStylesLoaded = false;
   
protected CelestialBody homeBody; protected CelestialBody homeBody;
   
[AVOID_SaveValue("togglePower")] [AVOID_SaveValue("togglePower")]
public VOID_SaveValue<bool> togglePower = (VOID_SaveValue<bool>)true; public VOID_SaveValue<bool> togglePower = (VOID_SaveValue<bool>)true;
   
public override bool powerAvailable { get; protected set; } public override bool powerAvailable { get; protected set; }
   
[AVOID_SaveValue("consumeResource")] [AVOID_SaveValue("consumeResource")]
protected VOID_SaveValue<bool> consumeResource = (VOID_SaveValue<bool>)false; protected VOID_SaveValue<bool> consumeResource = (VOID_SaveValue<bool>)false;
   
[AVOID_SaveValue("resourceName")] [AVOID_SaveValue("resourceName")]
protected VOID_SaveValue<string> resourceName = (VOID_SaveValue<string>)"ElectricCharge"; protected VOID_SaveValue<string> resourceName = (VOID_SaveValue<string>)"ElectricCharge";
   
[AVOID_SaveValue("resourceRate")] [AVOID_SaveValue("resourceRate")]
protected VOID_SaveValue<float> resourceRate = (VOID_SaveValue<float>)0.2f; protected VOID_SaveValue<float> resourceRate = (VOID_SaveValue<float>)0.2f;
   
[AVOID_SaveValue("updatePeriod")] [AVOID_SaveValue("updatePeriod")]
protected VOID_SaveValue<double> updatePeriod = (VOID_SaveValue<double>)(1001f / 15000f); protected VOID_SaveValue<double> updatePeriod = (VOID_SaveValue<double>)(1001f / 15000f);
protected string stringFrequency; protected string stringFrequency;
   
[AVOID_SaveValue("vesselSimActive")] [AVOID_SaveValue("vesselSimActive")]
protected VOID_SaveValue<bool> vesselSimActive; protected VOID_SaveValue<bool> vesselSimActive;
   
[AVOID_SaveValue("timeScaleFlags")] [AVOID_SaveValue("timeScaleFlags")]
protected VOID_SaveValue<UInt32> timeScaleFlags; protected VOID_SaveValue<UInt32> timeScaleFlags;
   
// Load-up housekeeping // Load-up housekeeping
protected bool vesselTypesLoaded = false; protected bool vesselTypesLoaded = false;
protected bool simManagerLoaded = false; protected bool simManagerLoaded = false;
   
protected string defaultSkin = "KSP window 2"; protected string defaultSkin = "KSP window 2";
   
[AVOID_SaveValue("defaultSkin")] [AVOID_SaveValue("defaultSkin")]
protected VOID_SaveValue<string> skinName; protected VOID_SaveValue<string> skinName;
protected int skinIdx; protected int skinIdx;
   
protected Dictionary<string, GUISkin> validSkins; protected Dictionary<string, GUISkin> validSkins;
protected string[] skinNames; protected string[] skinNames;
protected string[] forbiddenSkins = protected string[] forbiddenSkins =
{ {
"PlaqueDialogSkin", "PlaqueDialogSkin",
"FlagBrowserSkin", "FlagBrowserSkin",
"SSUITextAreaDefault", "SSUITextAreaDefault",
"ExperimentsDialogSkin", "ExperimentsDialogSkin",
"ExpRecoveryDialogSkin", "ExpRecoveryDialogSkin",
"KSP window 1", "KSP window 1",
"KSP window 3", "KSP window 3",
"KSP window 5", "KSP window 5",
"KSP window 6", "KSP window 6",
"PartTooltipSkin", "PartTooltipSkin",
"KSCContextMenuSkin" "KSCContextMenuSkin"
}; };
protected bool skinsLoaded = false; protected bool skinsLoaded = false;
   
public override bool configDirty { get; set; } public override bool configDirty { get; set; }
   
protected IButton ToolbarButton; protected IButton ToolbarButton;
protected ApplicationLauncherButton AppLauncherButton; protected ApplicationLauncherButton AppLauncherButton;
protected IconState iconState; protected IconState iconState;
   
/* /*
* Properties * Properties
* */ * */
public override bool Active public override bool Active
{ {
get get
{ {
return base.Active; return base.Active;
} }
set set
{ {
if (value != base.Active) if (value != base.Active)
{ {
this.SetIconTexture(this.powerState | this.activeState); this.SetIconTexture(this.powerState | this.activeState);
} }
   
base.Active = value; base.Active = value;
} }
} }
public override IList<CelestialBody> AllBodies public override IList<CelestialBody> AllBodies
{ {
get get
{ {
return FlightGlobals.Bodies.AsReadOnly(); return FlightGlobals.Bodies.AsReadOnly();
} }
} }
   
public override VesselType[] AllVesselTypes public override VesselType[] AllVesselTypes
{ {
get; get;
protected set; protected set;
} }
   
public override int ConfigVersion public override int ConfigVersion
{ {
get get
{ {
return this.configVersion; return this.configVersion;
} }
} }
   
public bool FactoryReset public bool FactoryReset
{ {
get; get;
protected set; protected set;
} }
   
public override CelestialBody HomeBody public override CelestialBody HomeBody
{ {
get get
{ {
if (this.homeBody == null) if (this.homeBody == null)
{ {
if (Planetarium.fetch != null) if (Planetarium.fetch != null)
{ {
this.homeBody = Planetarium.fetch.Home; this.homeBody = Planetarium.fetch.Home;
} }
} }
   
return this.homeBody; return this.homeBody;
} }
} }
   
public override IList<IVOID_Module> Modules public override IList<IVOID_Module> Modules
{ {
get get
{ {
return this.modules.AsReadOnly(); return this.modules.AsReadOnly();
} }
} }
   
public override GUISkin Skin public override GUISkin Skin
{ {
get get
{ {
if (this.skinsLoaded) if (this.skinsLoaded)
{ {
try try
{ {
return this.validSkins[this.skinName]; return this.validSkins[this.skinName];
} }
catch catch
{ {
} }
} }
   
return AssetBase.GetGUISkin(this.defaultSkin); return AssetBase.GetGUISkin(this.defaultSkin);
} }
} }
   
public override List<CelestialBody> SortedBodyList public override List<CelestialBody> SortedBodyList
{ {
get; get;
protected set; protected set;
} }
   
public override double UpdatePeriod public override double UpdatePeriod
{ {
get get
{ {
return this.updatePeriod; return this.updatePeriod;
} }
} }
   
public override float UpdateTimer public override float UpdateTimer
{ {
get; get;
protected set; protected set;
} }
   
public override int WindowID public override int WindowID
{ {
get get
{ {
if (this.windowID == 0) if (this.windowID == 0)
{ {
this.windowID = this.windowBaseID; this.windowID = this.windowBaseID;
} }
return this.windowID++; return this.windowID++;
} }
} }
   
public override Stage[] Stages public override Stage[] Stages
{ {
get; get;
protected set; protected set;
} }
   
public override Stage LastStage public override Stage LastStage
{ {
get; get;
protected set; protected set;
} }
   
public override VOID_TimeScale TimeScale public override VOID_TimeScale TimeScale
{ {
get get
{ {
return (VOID_TimeScale)this.timeScaleFlags.value; return (VOID_TimeScale)this.timeScaleFlags.value;
} }
protected set protected set
{ {
this.timeScaleFlags.value = (UInt32)value; this.timeScaleFlags.value = (UInt32)value;
} }
} }
   
protected IconState activeState protected IconState activeState
{ {
get get
{ {
if (this.Active) if (this.Active)
{ {
return IconState.Inactive; return IconState.Inactive;
} }
else else
{ {
return IconState.Active; return IconState.Active;
} }
   
} }
} }
   
protected IconState powerState protected IconState powerState
{ {
get get
{ {
if (this.togglePower && this.powerAvailable) if (this.togglePower && this.powerAvailable)
{ {
return IconState.PowerOn; return IconState.PowerOn;
} }
else else
{ {
return IconState.PowerOff; return IconState.PowerOff;
} }
   
} }
} }
   
protected virtual ApplicationLauncher.AppScenes appIconVisibleScenes protected virtual ApplicationLauncher.AppScenes appIconVisibleScenes
{ {
get get
{ {
return HighLogic.LoadedScene.ToAppScenes(); return HighLogic.LoadedScene.ToAppScenes();
} }
} }
   
protected bool useToolbarManager  
{  
get  
{  
return _useToolbarManager & ToolbarManager.ToolbarAvailable;  
}  
set  
{  
if (_useToolbarManager == value)  
{  
return;  
}  
   
if (value == false && this.ToolbarButton != null)  
{  
this.ToolbarButton.Destroy();  
this.ToolbarButton = null;  
}  
if (value == true)  
{  
if (this.AppLauncherButton != null)  
{  
ApplicationLauncher.Instance.RemoveModApplication(this.AppLauncherButton);  
this.AppLauncherButton = null;  
}  
   
this.InitializeToolbarButton();  
}  
   
_useToolbarManager = value;  
}  
}  
   
/* /*
* Events * Events
* */ * */
  // public
public override event VOIDEventHandler onApplicationQuit; public override event VOIDEventHandler onApplicationQuit;
public override event VOIDEventHandler onSkinChanged; public override event VOIDEventHandler onSkinChanged;
  public override event VOIDEventHandler onUpdate;
   
/* /*
* Methods * Methods
* */ * */
public override void DrawGUI() public override void DrawGUI()
{ {
this.windowID = this.windowBaseID; this.windowID = this.windowBaseID;
   
if (!this.modulesLoaded) if (!this.modulesLoaded)
{ {
this.LoadModulesOfType<IVOID_Module>(); this.LoadModulesOfType<IVOID_Module>();
} }
   
if (!this.skinsLoaded) if (!this.skinsLoaded)
{ {
this.LoadSkins(); this.LoadSkins();
} }
   
GUI.skin = this.Skin; GUI.skin = this.Skin;
   
if (!this.GUIStylesLoaded) if (!this.GUIStylesLoaded)
{ {
this.LoadGUIStyles(); this.LoadGUIStyles();
   
Tools.PostDebugMessage( Tools.PostDebugMessage(
this, this,
"ToolbarAvailable: {0}, UseToobarManager: {1}", "ToolbarAvailable: {0}, UseToobarManager: {1}",
ToolbarManager.ToolbarAvailable, ToolbarManager.ToolbarAvailable,
this.useToolbarManager); this.useToolbarManager);
} }
   
if (!this.useToolbarManager) if (
{ this.iconState != (this.powerState | this.activeState) ||
if (this.AppLauncherButton == null) (this.VOIDIconTexture == null && this.AppLauncherButton != null)
{ )
Tools.PostDebugMessage(this, {
"UseToolbarManager = false (ToolbarAvailable = {0}) and " + this.iconState = this.powerState | this.activeState;
"AppLauncherButton is null, making AppLauncher button.",  
ToolbarManager.ToolbarAvailable this.SetIconTexture(this.iconState);
); }
this.InitializeAppLauncherButton();  
}  
}  
else if (this.ToolbarButton == null)  
{  
Tools.PostDebugMessage(this,  
"UseToolbarManager = true (ToolbarAvailable = {0}) and " +  
"ToolbarButton is null, making Toolbar button.",  
ToolbarManager.ToolbarAvailable  
);  
this.InitializeToolbarButton();  
}  
   
this.SetIconTexture();  
   
if (this.Active) if (this.Active)
{ {
base.DrawGUI(); base.DrawGUI();
} }
} }
   
public virtual void Update() public virtual void Update()
{ {
this.LoadBeforeUpdate(); this.LoadBeforeUpdate();
   
if ( if (
this.vesselSimActive && this.vesselSimActive &&
( (
this.Vessel != null || this.Vessel != null ||
( (
HighLogic.LoadedSceneIsEditor && HighLogic.LoadedSceneIsEditor &&
EditorLogic.RootPart != null && EditorLogic.RootPart != null &&
EditorLogic.SortedShipList.Count > 0 EditorLogic.SortedShipList.Count > 0
) )
) )
) )
{ {
Tools.PostDebugMessage(this, "Updating SimManager."); Tools.PostDebugMessage(this, "Updating SimManager.");
this.UpdateSimManager(); this.UpdateSimManager();
} }
   
if (!this.GUIRunning) if (!this.GUIRunning)
{ {
this.StartGUI(); this.StartGUI();
} }
   
foreach (IVOID_Module module in this.modules) IVOID_Module module;
{ for (int idx = 0; idx < this.modules.Count; idx++)
  {
  module = this.modules[idx];
   
if ( if (
!module.GUIRunning && !module.GUIRunning &&
module.Active && module.Active &&
module.InValidScene && module.InValidScene &&
( (
!HighLogic.LoadedSceneIsEditor || !HighLogic.LoadedSceneIsEditor ||
(EditorLogic.RootPart != null && EditorLogic.SortedShipList.Count > 0) (EditorLogic.RootPart != null && EditorLogic.SortedShipList.Count > 0)
) )
) )
{ {
module.StartGUI(); module.StartGUI();
} }
if ( if (
module.GUIRunning && module.GUIRunning &&
( (
!module.Active || !module.Active ||
!this.togglePower || !this.togglePower ||
!module.InValidScene || !module.InValidScene ||
this.FactoryReset || this.FactoryReset ||
( (
HighLogic.LoadedSceneIsEditor && HighLogic.LoadedSceneIsEditor &&
(EditorLogic.RootPart == null || EditorLogic.SortedShipList.Count == 0) (EditorLogic.RootPart == null || EditorLogic.SortedShipList.Count == 0)
) )
) )
) )
{ {
module.StopGUI(); module.StopGUI();
} }
   
if (module is IVOID_BehaviorModule) if (module is IVOID_BehaviorModule)
{ {
((IVOID_BehaviorModule)module).Update(); ((IVOID_BehaviorModule)module).Update();
} }
} }
   
this.CheckAndSave(); if (this.useToolbarManager)
  {
  if (this.AppLauncherButton != null)
  {
  ApplicationLauncher.Instance.RemoveModApplication(this.AppLauncherButton);
  this.AppLauncherButton = null;
  }
   
  if (this.ToolbarButton == null)
  {
  this.InitializeToolbarButton();
  }
  }
  else
  {
  if (this.ToolbarButton != null)
  {
  this.ToolbarButton.Destroy();
  this.ToolbarButton = null;
  }
   
  if (this.AppLauncherButton == null)
  {
  this.InitializeAppLauncherButton();
  }
   
  }
   
  this.saveTimer += Time.deltaTime;
   
  if (this.saveTimer > 2f)
  {
  if (this.configDirty)
  {
   
  Tools.PostDebugMessage(string.Format(
  "{0}: Time to save, checking if configDirty: {1}",
  this.GetType().Name,
  this.configDirty
  ));
   
  this.SaveConfig();
  this.saveTimer = 0;
  }
  }
   
this.UpdateTimer += Time.deltaTime; this.UpdateTimer += Time.deltaTime;
   
  if (this.onUpdate != null)
  {
  this.onUpdate(this);
  }
} }
   
public virtual void FixedUpdate() public virtual void FixedUpdate()
{ {
bool newPowerState = this.powerAvailable; bool newPowerState = this.powerAvailable;
   
if (this.togglePower && this.consumeResource && if (this.togglePower && this.consumeResource &&
this.Vessel.vesselType != VesselType.EVA && this.Vessel.vesselType != VesselType.EVA &&
TimeWarp.deltaTime != 0) TimeWarp.deltaTime != 0)
{ {
float powerReceived = this.Vessel.rootPart.RequestResource( float powerReceived = this.Vessel.rootPart.RequestResource(
this.resourceName, this.resourceName,
this.resourceRate * TimeWarp.fixedDeltaTime this.resourceRate * TimeWarp.fixedDeltaTime
); );
   
if (powerReceived > 0) if (powerReceived > 0)
{ {
newPowerState = true; newPowerState = true;
} }
else else
{ {
newPowerState = false; newPowerState = false;
} }
   
if (this.powerAvailable != newPowerState) if (this.powerAvailable != newPowerState)
{ {
this.powerAvailable = newPowerState; this.powerAvailable = newPowerState;
} }
} }
   
foreach (IVOID_Module module in this.modules) IVOID_Module module;
{ for (int idx = 0; idx < this.modules.Count; idx++)
  {
  module = this.modules[idx];
   
if (module is IVOID_BehaviorModule) if (module is IVOID_BehaviorModule)
{ {
((IVOID_BehaviorModule)module).FixedUpdate(); ((IVOID_BehaviorModule)module).FixedUpdate();
} }
} }
} }
   
public void OnDestroy() public void OnDestroy()
{ {
foreach (IVOID_Module module in this.modules) IVOID_Module module;
{ for (int idx = 0; idx < this.modules.Count; idx++)
  {
  module = this.modules[idx];
   
if (module is IVOID_BehaviorModule) if (module is IVOID_BehaviorModule)
{ {
((IVOID_BehaviorModule)module).OnDestroy(); ((IVOID_BehaviorModule)module).OnDestroy();
} }
} }
   
this.Dispose(); this.Dispose();
} }
   
public virtual void OnApplicationQuit() public virtual void OnApplicationQuit()
{ {
if (this.onApplicationQuit != null) if (this.onApplicationQuit != null)
{ {
this.onApplicationQuit(this); this.onApplicationQuit(this);
} }
   
this.OnDestroy(); this.OnDestroy();
} }
   
public override void StartGUI() public override void StartGUI()
{ {
if (!this.GUIRunning) if (!this.GUIRunning)
{ {
RenderingManager.AddToPostDrawQueue(3, this.DrawGUI); RenderingManager.AddToPostDrawQueue(3, this.DrawGUI);
} }
} }
   
public void ResetGUI() public void ResetGUI()
{ {
this.StopGUI(); this.StopGUI();
   
foreach (IVOID_Module module in this.modules) IVOID_Module module;
{ for (int idx = 0; idx < this.modules.Count; idx++)
  {
  module = this.modules[idx];
   
module.StopGUI(); module.StopGUI();
module.StartGUI(); module.StartGUI();
} }
   
this.StartGUI(); this.StartGUI();
} }
   
public override void ModuleWindow(int id) public override void ModuleWindow(int id)
{ {
GUILayout.BeginVertical(); GUILayout.BeginVertical();
   
if (this.powerAvailable || !HighLogic.LoadedSceneIsFlight) if (this.powerAvailable || !HighLogic.LoadedSceneIsFlight)
{ {
if (!HighLogic.LoadedSceneIsEditor) if (!HighLogic.LoadedSceneIsEditor)
{ {
string str = string.Intern("ON"); string str = string.Intern("ON");
if (togglePower) if (togglePower)
str = string.Intern("OFF"); str = string.Intern("OFF");
if (GUILayout.Button("Power " + str)) if (GUILayout.Button("Power " + str))
{ {
togglePower.value = !togglePower; togglePower.value = !togglePower;
} }
} }
   
if (togglePower || !HighLogic.LoadedSceneIsFlight) if (togglePower || !HighLogic.LoadedSceneIsFlight)
{ {
foreach (IVOID_Module module in this.modules) IVOID_Module module;
  for (int idx = 0; idx < this.modules.Count; idx++)
{ {
  module = this.modules[idx];
   
if (module is VOID_ConfigWindow) if (module is VOID_ConfigWindow)
{ {
continue; continue;
} }
   
module.Active = GUITools.Toggle(module.Active, module.Name); module.Active = GUITools.Toggle(module.Active, module.Name);
} }
} }
} }
else else
{ {
GUILayout.Label("-- POWER LOST --", VOID_Styles.labelRed); GUILayout.Label("-- POWER LOST --", VOID_Styles.labelRed);
} }
   
VOID_ConfigWindow.Instance.Active = GUITools.Toggle( VOID_ConfigWindow.Instance.Active = GUITools.Toggle(
VOID_ConfigWindow.Instance.Active, VOID_ConfigWindow.Instance.Active,
"Configuration" "Configuration"
); );
   
GUILayout.EndVertical(); GUILayout.EndVertical();
   
base.ModuleWindow(id); base.ModuleWindow(id);
} }
   
public override void DrawConfigurables() public override void DrawConfigurables()
{ {
GUIContent _content; GUIContent _content;
   
this.useToolbarManager = GUITools.Toggle(this.useToolbarManager, "Use Blizzy's Toolbar If Available"); this.useToolbarManager.value = GUITools.Toggle(this.useToolbarManager, "Use Blizzy's Toolbar If Available");
   
this.vesselSimActive.value = GUITools.Toggle(this.vesselSimActive.value, this.vesselSimActive.value = GUITools.Toggle(this.vesselSimActive.value,
"Enable Engineering Calculations"); "Enable Engineering Calculations");
   
bool useEarthTime = (this.TimeScale & VOID_TimeScale.KERBIN_TIME) == 0u; bool useEarthTime = (this.TimeScale & VOID_TimeScale.KERBIN_TIME) == 0u;
bool useSiderealTime = (this.TimeScale & VOID_TimeScale.SOLAR_DAY) == 0u; bool useSiderealTime = (this.TimeScale & VOID_TimeScale.SOLAR_DAY) == 0u;
bool useRoundedScale = (this.TimeScale & VOID_TimeScale.ROUNDED_SCALE) != 0u; bool useRoundedScale = (this.TimeScale & VOID_TimeScale.ROUNDED_SCALE) != 0u;
   
useEarthTime = GUITools.Toggle(useEarthTime, "Use Earth Time (changes KSP option)"); useEarthTime = GUITools.Toggle(useEarthTime, "Use Earth Time (changes KSP option)");
   
GameSettings.KERBIN_TIME = !useEarthTime; GameSettings.KERBIN_TIME = !useEarthTime;
   
useSiderealTime = GUITools.Toggle( useSiderealTime = GUITools.Toggle(
useSiderealTime, useSiderealTime,
string.Format( string.Format(
"Time Scale: {0}", "Time Scale: {0}",
useSiderealTime ? "Sidereal" : "Solar" useSiderealTime ? "Sidereal" : "Solar"
) )
); );
   
useRoundedScale = GUITools.Toggle( useRoundedScale = GUITools.Toggle(
useRoundedScale, useRoundedScale,
string.Format( string.Format(
"Time Scale: {0}", "Time Scale: {0}",
useRoundedScale ? "Rounded" : "True" useRoundedScale ? "Rounded" : "True"
) )
); );
   
if (useEarthTime) if (useEarthTime)
{ {
this.TimeScale &= ~VOID_TimeScale.KERBIN_TIME; this.TimeScale &= ~VOID_TimeScale.KERBIN_TIME;
} }
else else
{ {
this.TimeScale |= VOID_TimeScale.KERBIN_TIME; this.TimeScale |= VOID_TimeScale.KERBIN_TIME;
} }
   
if (useSiderealTime) if (useSiderealTime)
{ {
this.TimeScale &= ~VOID_TimeScale.SOLAR_DAY; this.TimeScale &= ~VOID_TimeScale.SOLAR_DAY;
} }
else else
{ {
this.TimeScale |= VOID_TimeScale.SOLAR_DAY; this.TimeScale |= VOID_TimeScale.SOLAR_DAY;
} }
   
if (useRoundedScale) if (useRoundedScale)
{ {
this.TimeScale |= VOID_TimeScale.ROUNDED_SCALE; this.TimeScale |= VOID_TimeScale.ROUNDED_SCALE;
} }
else else
{ {
this.TimeScale &= ~VOID_TimeScale.ROUNDED_SCALE; this.TimeScale &= ~VOID_TimeScale.ROUNDED_SCALE;
} }
   
GUILayout.BeginHorizontal(GUILayout.ExpandWidth(true)); GUILayout.BeginHorizontal(GUILayout.ExpandWidth(true));
   
GUILayout.Label("Skin:", GUILayout.ExpandWidth(false)); GUILayout.Label("Skin:", GUILayout.ExpandWidth(false));
   
_content = new GUIContent(); _content = new GUIContent();
   
_content.text = "◄"; _content.text = "◄";
_content.tooltip = "Select previous skin"; _content.tooltip = "Select previous skin";
if (GUILayout.Button(_content, GUILayout.ExpandWidth(true))) if (GUILayout.Button(_content, GUILayout.ExpandWidth(true)))
{ {
this.skinIdx--; this.skinIdx--;
Tools.PostDebugMessage(string.Format( Tools.PostDebugMessage(string.Format(
"{0}: new this.skinIdx = {1} :: skin_list.Count = {2}", "{0}: new this.skinIdx = {1} :: skin_list.Count = {2}",
this.GetType().Name, this.GetType().Name,
this.skinName, this.skinName,
this.validSkins.Count this.validSkins.Count
)); ));
} }
   
_content.text = this.Skin.name; _content.text = this.Skin.name;
_content.tooltip = "Current skin"; _content.tooltip = "Current skin";
GUILayout.Label(_content, VOID_Styles.labelCenter, GUILayout.ExpandWidth(true)); GUILayout.Label(_content, VOID_Styles.labelCenter, GUILayout.ExpandWidth(true));
   
_content.text = "►"; _content.text = "►";
_content.tooltip = "Select next skin"; _content.tooltip = "Select next skin";
if (GUILayout.Button(_content, GUILayout.ExpandWidth(true))) if (GUILayout.Button(_content, GUILayout.ExpandWidth(true)))
{ {
this.skinIdx++; this.skinIdx++;
Tools.PostDebugMessage(string.Format( Tools.PostDebugMessage(string.Format(
"{0}: new this.skinIdx = {1} :: skin_list.Count = {2}", "{0}: new this.skinIdx = {1} :: skin_list.Count = {2}",
this.GetType().Name, this.GetType().Name,
this.skinName, this.skinName,
this.validSkins.Count this.validSkins.Count
)); ));
} }
   
this.skinIdx %= this.skinNames.Length; this.skinIdx %= this.skinNames.Length;
if (this.skinIdx < 0) if (this.skinIdx < 0)
{ {
this.skinIdx += this.skinNames.Length; this.skinIdx += this.skinNames.Length;
} }
   
if (this.skinName != skinNames[this.skinIdx]) if (this.skinName != skinNames[this.skinIdx])
{ {
this.skinName.value = skinNames[this.skinIdx]; this.skinName.value = skinNames[this.skinIdx];
this.GUIStylesLoaded = false; this.GUIStylesLoaded = false;
} }
   
GUILayout.EndHorizontal(); GUILayout.EndHorizontal();
   
GUILayout.BeginHorizontal(); GUILayout.BeginHorizontal();
GUILayout.Label("Update Rate (Hz):"); GUILayout.Label("Update Rate (Hz):");
if (this.stringFrequency == null) if (this.stringFrequency == null)
{ {
this.stringFrequency = (1f / this.UpdatePeriod).ToString(); this.stringFrequency = (1f / this.UpdatePeriod).ToString();
} }
this.stringFrequency = GUILayout.TextField(this.stringFrequency.ToString(), 5, GUILayout.ExpandWidth(true)); this.stringFrequency = GUILayout.TextField(this.stringFrequency.ToString(), 5, GUILayout.ExpandWidth(true));
   
if (GUILayout.Button("Apply")) if (GUILayout.Button("Apply"))
{ {
double updateFreq = 1f / this.UpdatePeriod; double updateFreq = 1f / this.UpdatePeriod;
double.TryParse(stringFrequency, out updateFreq); double.TryParse(stringFrequency, out updateFreq);
this.updatePeriod.value = 1 / updateFreq; this.updatePeriod.value = 1 / updateFreq;
} }
GUILayout.EndHorizontal(); GUILayout.EndHorizontal();
   
foreach (IVOID_Module mod in this.modules) IVOID_Module module;
{ for (int idx = 0; idx < this.modules.Count; idx++)
mod.DrawConfigurables(); {
  module = this.modules[idx];
   
  module.DrawConfigurables();
} }
   
this.FactoryReset = GUITools.Toggle(this.FactoryReset, "Factory Reset"); this.FactoryReset = GUITools.Toggle(this.FactoryReset, "Factory Reset");
} }
   
protected void UpdateSimManager() protected void UpdateSimManager()
{ {
if (HighLogic.LoadedSceneIsFlight) if (HighLogic.LoadedSceneIsFlight)
{ {
double radius = this.Vessel.Radius(); double radius = this.Vessel.Radius();
SimManager.Gravity = this.Vessel.mainBody.gravParameter / (radius * radius); SimManager.Gravity = this.Vessel.mainBody.gravParameter / (radius * radius);
SimManager.Atmosphere = this.Vessel.staticPressurekPa * PhysicsGlobals.KpaToAtmospheres; SimManager.Atmosphere = this.Vessel.staticPressurekPa * PhysicsGlobals.KpaToAtmospheres;
SimManager.Mach = this.Vessel.mach; SimManager.Mach = this.Vessel.mach;
BuildAdvanced.Altitude = this.Vessel.altitude; BuildAdvanced.Altitude = this.Vessel.altitude;
CelestialBodies.SelectedBody = this.Vessel.mainBody; CelestialBodies.SelectedBody = this.Vessel.mainBody;
} }
   
#if DEBUG #if DEBUG
SimManager.logOutput = true; SimManager.logOutput = true;
#endif #endif
   
SimManager.TryStartSimulation(); SimManager.TryStartSimulation();
   
Tools.PostDebugMessage(this, "Started Engineer simulation with Atmosphere={0} atm and Gravity={1} m/s²", Tools.PostDebugMessage(this, "Started Engineer simulation with Atmosphere={0} atm and Gravity={1} m/s²",
SimManager.Atmosphere, SimManager.Atmosphere,
SimManager.Gravity SimManager.Gravity
); );
} }
   
protected void GetSimManagerResults() protected void GetSimManagerResults()
{ {
Tools.PostDebugMessage(this, "VesselSimulator results ready, setting Stages."); Tools.PostDebugMessage(this, "VesselSimulator results ready, setting Stages.");
   
this.Stages = SimManager.Stages; this.Stages = SimManager.Stages;
   
if (this.Stages != null) if (this.Stages != null)
{ {
this.LastStage = this.Stages.Last(); this.LastStage = this.Stages.Last();
} }
} }
   
protected void LoadModulesOfType<U>() protected void LoadModulesOfType<U>()
{ {
Tools.DebugLogger sb = Tools.DebugLogger.New(this); Tools.DebugLogger sb = Tools.DebugLogger.New(this);
sb.AppendLine("Loading modules..."); sb.AppendLine("Loading modules...");
   
foreach (AssemblyLoader.LoadedAssembly assy in AssemblyLoader.loadedAssemblies) AssemblyLoader.LoadedAssembly assy;
{ for (int aIdx = 0; aIdx < AssemblyLoader.loadedAssemblies.Count; aIdx++)
foreach (Type loadedType in assy.assembly.GetExportedTypes()) {
{ assy = AssemblyLoader.loadedAssemblies[aIdx];
   
  Type[] loadedTypes = assy.assembly.GetExportedTypes();
  Type loadedType;
  for (int tIdx = 0; tIdx < loadedTypes.Length; tIdx++)
  {
  loadedType = loadedTypes[tIdx];
   
if ( if (
loadedType.IsInterface || loadedType.IsInterface ||
loadedType.IsAbstract || loadedType.IsAbstract ||
!typeof(U).IsAssignableFrom(loadedType) || !typeof(U).IsAssignableFrom(loadedType) ||
typeof(VOIDCore).IsAssignableFrom(loadedType) typeof(VOIDCore).IsAssignableFrom(loadedType)
) )
{ {
continue; continue;
} }
   
sb.AppendFormat("Checking IVOID_Module type {0}...", loadedType.Name); sb.AppendFormat("Checking IVOID_Module type {0}...", loadedType.Name);
   
try try
{ {
this.LoadModule(loadedType); this.LoadModule(loadedType);
sb.AppendLine("Success."); sb.AppendLine("Success.");
} }
catch (Exception ex) catch (Exception ex)
{ {
sb.AppendFormat("Failed, caught {0}\n", ex.GetType().Name); sb.AppendFormat("Failed, caught {0}\n", ex.GetType().Name);
   
#if DEBUG #if DEBUG
Debug.LogException(ex); Debug.LogException(ex);
#endif #endif
} }
} }
} }
   
this.modulesLoaded = true; this.modulesLoaded = true;
   
sb.AppendFormat("Loaded {0} modules.\n", this.Modules.Count); sb.AppendFormat("Loaded {0} modules.\n", this.Modules.Count);
   
sb.Print(); sb.Print();
} }
   
protected void LoadModule(Type T) protected void LoadModule(Type T)
{ {
var existingModules = this.modules.Where(mod => mod.GetType().Name == T.Name); var existingModules = this.modules.Where(mod => mod.GetType().Name == T.Name);
if (existingModules.Any()) if (existingModules.Any())
{ {
Tools.PostDebugMessage(string.Format( Tools.PostDebugMessage(string.Format(
"{0}: refusing to load {1}: already loaded", "{0}: refusing to load {1}: already loaded",
this.GetType().Name, this.GetType().Name,
T.Name T.Name
)); ));
return; return;
} }
   
var InstanceProperty = T.GetProperty( var InstanceProperty = T.GetProperty(
"Instance", "Instance",
System.Reflection.BindingFlags.Static | System.Reflection.BindingFlags.Static |
System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.Public |
System.Reflection.BindingFlags.FlattenHierarchy System.Reflection.BindingFlags.FlattenHierarchy
); );
   
object modInstance = null; object modInstance = null;
IVOID_Module module; IVOID_Module module;
   
if (InstanceProperty != null) if (InstanceProperty != null)
{ {
modInstance = InstanceProperty.GetValue(null, null); modInstance = InstanceProperty.GetValue(null, null);
} }
   
if (modInstance != null) if (modInstance != null)
{ {
module = modInstance as IVOID_Module; module = modInstance as IVOID_Module;
} }
else else
{ {
module = Activator.CreateInstance(T) as IVOID_Module; module = Activator.CreateInstance(T) as IVOID_Module;
} }
   
if (module.InValidGame && module.InValidScene) if (module.InValidGame && module.InValidScene)
{ {
module.LoadConfig(); module.LoadConfig();
this.modules.Add(module); this.modules.Add(module);
   
Tools.PostDebugMessage(string.Format( Tools.PostDebugMessage(string.Format(
"{0}: loaded module {1}.", "{0}: loaded module {1}.",
this.GetType().Name, this.GetType().Name,
T.Name T.Name
)); ));
} }
else else
{ {
if (module is IDisposable) if (module is IDisposable)
{ {
(module as IDisposable).Dispose(); (module as IDisposable).Dispose();
} }
} }
} }
   
protected void LoadSkins() protected void LoadSkins()
{ {
Tools.PostDebugMessage("AssetBase has skins: \n" + Tools.PostDebugMessage("AssetBase has skins: \n" +
string.Join("\n\t", string.Join("\n\t",
Resources.FindObjectsOfTypeAll(typeof(GUISkin)) Resources.FindObjectsOfTypeAll(typeof(GUISkin))
.Select(s => s.ToString()) .Select(s => s.ToString())
.ToArray() .ToArray()
) )
); );
   
this.validSkins = Resources.FindObjectsOfTypeAll(typeof(GUISkin)) this.validSkins = Resources.FindObjectsOfTypeAll(typeof(GUISkin))
.Where(s => !this.forbiddenSkins.Contains(s.name)) .Where(s => !this.forbiddenSkins.Contains(s.name))
.Select(s => s as GUISkin) .Select(s => s as GUISkin)
.GroupBy(s => s.name) .GroupBy(s => s.name)
.Select(g => g.First()) .Select(g => g.First())
.ToDictionary(s => s.name); .ToDictionary(s => s.name);
   
Tools.PostDebugMessage(string.Format( Tools.PostDebugMessage(string.Format(
"{0}: loaded {1} GUISkins.", "{0}: loaded {1} GUISkins.",
this.GetType().Name, this.GetType().Name,
this.validSkins.Count this.validSkins.Count
)); ));
   
this.skinNames = this.validSkins.Keys.ToArray(); this.skinNames = this.validSkins.Keys.ToArray();
Array.Sort(this.skinNames); Array.Sort(this.skinNames);
   
int defaultIdx = int.MinValue; int defaultIdx = int.MinValue;
   
for (int i = 0; i < this.skinNames.Length; i++) for (int i = 0; i < this.skinNames.Length; i++)
{ {
if (this.skinNames[i] == this.skinName) if (this.skinNames[i] == this.skinName)
{ {
this.skinIdx = i; this.skinIdx = i;
} }
if (this.skinNames[i] == this.defaultSkin) if (this.skinNames[i] == this.defaultSkin)
{ {
defaultIdx = i; defaultIdx = i;
} }
if (this.skinIdx != int.MinValue && defaultIdx != int.MinValue) if (this.skinIdx != int.MinValue && defaultIdx != int.MinValue)
{ {
break; break;
} }
} }
   
if (this.skinIdx == int.MinValue) if (this.skinIdx == int.MinValue)
{ {
this.skinIdx = defaultIdx; this.skinIdx = defaultIdx;
} }
   
Tools.PostDebugMessage(string.Format( Tools.PostDebugMessage(string.Format(
"{0}: _skinIdx = {1}.", "{0}: _skinIdx = {1}.",
this.GetType().Name, this.GetType().Name,
this.skinName.ToString() this.skinName.ToString()
)); ));
   
this.skinsLoaded = true; this.skinsLoaded = true;
} }
   
protected void LoadGUIStyles() protected void LoadGUIStyles()
{ {
VOID_Styles.OnSkinChanged(); VOID_Styles.OnSkinChanged();
   
if (this.onSkinChanged != null) if (this.onSkinChanged != null)
{ {
this.onSkinChanged(this); this.onSkinChanged(this);
} }
   
this.GUIStylesLoaded = true; this.GUIStylesLoaded = true;
} }
   
protected void LoadVesselTypes()  
{  
this.AllVesselTypes = Enum.GetValues(typeof(VesselType)).OfType<VesselType>().ToArray();  
this.vesselTypesLoaded = true;  
}  
   
protected void LoadBeforeUpdate() protected void LoadBeforeUpdate()
{ {
if (!this.vesselTypesLoaded) if (!this.vesselTypesLoaded)
{ {
this.LoadVesselTypes(); this.AllVesselTypes = Enum.GetValues(typeof(VesselType)).OfType<VesselType>().ToArray();
  this.vesselTypesLoaded = true;
} }
   
if (this.SortedBodyList == null && FlightGlobals.Bodies != null && FlightGlobals.Bodies.Count > 0) if (this.SortedBodyList == null && FlightGlobals.Bodies != null && FlightGlobals.Bodies.Count > 0)
{ {
this.SortedBodyList = new List<CelestialBody>(FlightGlobals.Bodies); this.SortedBodyList = new List<CelestialBody>(FlightGlobals.Bodies);
this.SortedBodyList.Sort(new CBListComparer()); this.SortedBodyList.Sort(new CBListComparer());
this.SortedBodyList.Reverse(); this.SortedBodyList.Reverse();
   
Debug.Log(string.Format("sortedBodyList: {0}", string.Join("\n\t", this.SortedBodyList.Select(b => b.bodyName).ToArray()))); Debug.Log(string.Format("sortedBodyList: {0}", string.Join("\n\t", this.SortedBodyList.Select(b => b.bodyName).ToArray())));
} }
   
// SimManager initialization that we don't necessarily want to repeat every Update. // SimManager initialization that we don't necessarily want to repeat every Update.
if (!this.simManagerLoaded && this.HomeBody != null) if (!this.simManagerLoaded && this.HomeBody != null)
{ {
SimManager.Gravity = VOID_Data.KerbinGee; SimManager.Gravity = VOID_Data.KerbinGee;
SimManager.Atmosphere = 0d; SimManager.Atmosphere = 0d;
SimManager.Mach = 1d; SimManager.Mach = 1d;
CelestialBodies.SelectedBody = this.HomeBody; CelestialBodies.SelectedBody = this.HomeBody;
BuildAdvanced.Altitude = 0d; BuildAdvanced.Altitude = 0d;
SimManager.OnReady += this.GetSimManagerResults; SimManager.OnReady += this.GetSimManagerResults;
   
this.simManagerLoaded = true; this.simManagerLoaded = true;
} }
} }
   
protected void InitializeToolbarButton() protected void InitializeToolbarButton()
{ {
// Do nothing if (the Toolbar is not available. // Do nothing if (the Toolbar is not available.
if (!ToolbarManager.ToolbarAvailable) if (!ToolbarManager.ToolbarAvailable)
{ {
Tools.PostDebugMessage(this, "Refusing to make a ToolbarButton: ToolbarAvailable = false"); Tools.PostDebugMessage(this, "Refusing to make a ToolbarButton: ToolbarAvailable = false");
return; return;
} }
   
this.ToolbarButton = ToolbarManager.Instance.add(this.VoidName, "coreToggle"); this.ToolbarButton = ToolbarManager.Instance.add(this.VoidName, "coreToggle");
this.ToolbarButton.Text = this.VoidName; this.ToolbarButton.Text = this.VoidName;
this.SetIconTexture(this.powerState | this.activeState); this.SetIconTexture(this.powerState | this.activeState);
   
this.ToolbarButton.Visible = true; this.ToolbarButton.Visible = true;
   
this.ToolbarButton.OnClick += this.ToolbarButton.OnClick +=
(e) => (e) =>
{ {
this.ToggleMainWindow(); this.ToggleMainWindow();
}; };
   
Tools.PostDebugMessage(string.Format("{0}: Toolbar Button initialized.", this.GetType().Name)); Tools.PostDebugMessage(string.Format("{0}: Toolbar Button initialized.", this.GetType().Name));
} }
   
protected void InitializeAppLauncherButton() protected void InitializeAppLauncherButton()
{ {
if (ApplicationLauncher.Ready) if (ApplicationLauncher.Ready)
{ {
this.AppLauncherButton = ApplicationLauncher.Instance.AddModApplication( this.AppLauncherButton = ApplicationLauncher.Instance.AddModApplication(
this.ToggleMainWindow, this.ToggleMainWindow, this.ToggleMainWindow, this.ToggleMainWindow,
this.appIconVisibleScenes, this.appIconVisibleScenes,
this.VOIDIconTexture this.VOIDIconTexture
); );
   
Tools.PostDebugMessage( Tools.PostDebugMessage(
this, this,
"AppLauncherButton initialized in {0}", "AppLauncherButton initialized in {0}",
Enum.GetName( Enum.GetName(
typeof(GameScenes), typeof(GameScenes),
HighLogic.LoadedScene HighLogic.LoadedScene
) )
); );
} }
} }
   
protected void ToggleMainWindow() protected void ToggleMainWindow()
{ {
this.Active = !this.Active; this.Active = !this.Active;
}  
   
protected void SetIconTexture()  
{  
if (  
this.iconState != (this.powerState | this.activeState) ||  
(this.VOIDIconTexture == null && this.AppLauncherButton != null)  
)  
{  
this.iconState = this.powerState | this.activeState;  
   
this.SetIconTexture(this.iconState);  
}  
} }
   
protected void SetIconTexture(IconState state) protected void SetIconTexture(IconState state)
{ {
switch (state) switch (state)
{ {
case (IconState.PowerOff | IconState.Inactive): case (IconState.PowerOff | IconState.Inactive):
this.SetIconTexture(this.VOIDIconOffInactivePath); this.SetIconTexture(this.VOIDIconOffInactivePath);
break; break;
case (IconState.PowerOff | IconState.Active): case (IconState.PowerOff | IconState.Active):
this.SetIconTexture(this.VOIDIconOffActivePath); this.SetIconTexture(this.VOIDIconOffActivePath);
break; break;
case (IconState.PowerOn | IconState.Inactive): case (IconState.PowerOn | IconState.Inactive):
this.SetIconTexture(this.VOIDIconOnInactivePath); this.SetIconTexture(this.VOIDIconOnInactivePath);
break; break;
case (IconState.PowerOn | IconState.Active): case (IconState.PowerOn | IconState.Active):
this.SetIconTexture(this.VOIDIconOnActivePath); this.SetIconTexture(this.VOIDIconOnActivePath);
break; break;
default: default:
throw new NotImplementedException(); throw new NotImplementedException();
} }
} }
   
protected void SetIconTexture(string texturePath) protected void SetIconTexture(string texturePath)
{ {
if (texturePath == null) if (texturePath == null)
{ {
return; return;
} }
   
if (this.ToolbarButton != null) if (this.ToolbarButton != null)
{ {
this.ToolbarButton.TexturePath = texturePath; this.ToolbarButton.TexturePath = texturePath;
} }
   
if (this.AppLauncherButton != null) if (this.AppLauncherButton != null)
{ {
this.VOIDIconTexture = GameDatabase.Instance.GetTexture(texturePath.Replace("icon", "appIcon"), false); this.VOIDIconTexture = GameDatabase.Instance.GetTexture(texturePath.Replace("icon", "appIcon"), false);
   
this.AppLauncherButton.SetTexture(VOIDIconTexture); this.AppLauncherButton.SetTexture(VOIDIconTexture);
} }
} }
   
protected virtual void CheckAndSave()  
{  
this.saveTimer += Time.deltaTime;  
   
if (this.saveTimer > 2f)  
{  
if (!this.configDirty)  
{  
return;  
}  
   
Tools.PostDebugMessage(string.Format(  
"{0}: Time to save, checking if configDirty: {1}",  
this.GetType().Name,  
this.configDirty  
));  
   
this.SaveConfig();  
this.saveTimer = 0;  
}  
}  
   
public override void LoadConfig() public override void LoadConfig()
{ {
base.LoadConfig(); base.LoadConfig();
   
foreach (IVOID_Module module in this.modules) IVOID_Module module;
{ for (int idx = 0; idx < this.modules.Count; idx++)
  {
  module = this.modules[idx];
   
module.LoadConfig(); module.LoadConfig();
} }
   
this.TimeScale |= GameSettings.KERBIN_TIME ? VOID_TimeScale.KERBIN_TIME : 0u; this.TimeScale |= GameSettings.KERBIN_TIME ? VOID_TimeScale.KERBIN_TIME : 0u;
} }
   
public override void SaveConfig() public override void SaveConfig()
{ {
if (this.configNeedsUpdate && this is VOIDCore_Flight) if (this.configNeedsUpdate && this is VOIDCore_Flight)
{ {
KSP.IO.File.Delete<T>("config.xml"); KSP.IO.File.Delete<T>("config.xml");
} }
   
var config = KSP.IO.PluginConfiguration.CreateForType<T>(); var config = KSP.IO.PluginConfiguration.CreateForType<T>();
   
config.load(); config.load();
   
this.Save(config); this.Save(config);
   
foreach (IVOID_Module module in this.modules) IVOID_Module module;
{ for (int idx = 0; idx < this.modules.Count; idx++)
  {
  module = this.modules[idx];
   
module.Save(config); module.Save(config);
} }
   
config.save(); config.save();
   
this.configDirty = false; this.configDirty = false;
} }
   
public VOIDCore_Generic() public VOIDCore_Generic()
{ {
System.Version version = this.GetType().Assembly.GetName().Version; System.Version version = this.GetType().Assembly.GetName().Version;
   
this.VoidVersion = string.Format("{0}.{1}.{2}", version.Major, version.Minor, version.MajorRevision); this.VoidVersion = string.Format("{0}.{1}.{2}", version.Major, version.Minor, version.MajorRevision);
   
this.Name = string.Format("VOID {0}", this.VoidVersion.ToString()); this.Name = string.Format("VOID {0}", this.VoidVersion.ToString());
   
this.powerAvailable = true; this.powerAvailable = true;
   
this.Active = true; this.Active = true;
   
this.skinName = (VOID_SaveValue<string>)this.defaultSkin; this.skinName = (VOID_SaveValue<string>)this.defaultSkin;
this.skinIdx = int.MinValue; this.skinIdx = int.MinValue;
   
this.VOIDIconOnActivePath = "VOID/Textures/void_icon_light_glow"; this.VOIDIconOnActivePath = "VOID/Textures/void_icon_light_glow";
this.VOIDIconOnInactivePath = "VOID/Textures/void_icon_dark_glow"; this.VOIDIconOnInactivePath = "VOID/Textures/void_icon_dark_glow";
this.VOIDIconOffActivePath = "VOID/Textures/void_icon_light"; this.VOIDIconOffActivePath = "VOID/Textures/void_icon_light";
this.VOIDIconOffInactivePath = "VOID/Textures/void_icon_dark"; this.VOIDIconOffInactivePath = "VOID/Textures/void_icon_dark";
   
this.saveTimer = 0f; this.saveTimer = 0f;
this.UpdateTimer = 0f; this.UpdateTimer = 0f;
   
this.vesselSimActive = (VOID_SaveValue<bool>)true; this.vesselSimActive = (VOID_SaveValue<bool>)true;
   
this.useToolbarManager = ToolbarManager.ToolbarAvailable; this.useToolbarManager = (VOID_SaveValue<bool>)ToolbarManager.ToolbarAvailable;
   
this.LoadConfig(); this.LoadConfig();
   
this.configVersion = (VOID_SaveValue<int>)VOIDCore.CONFIG_VERSION; this.configVersion = (VOID_SaveValue<int>)VOIDCore.CONFIG_VERSION;
   
this.FactoryReset = false; this.FactoryReset = false;
} }
   
public override void Dispose() public override void Dispose()
{ {
this.StopGUI(); this.StopGUI();
   
this.onSkinChanged(this); this.onSkinChanged(this);
   
if (this.AppLauncherButton != null) if (this.AppLauncherButton != null)
{ {
ApplicationLauncher.Instance.RemoveModApplication(this.AppLauncherButton); ApplicationLauncher.Instance.RemoveModApplication(this.AppLauncherButton);
this.AppLauncherButton = null; this.AppLauncherButton = null;
} }
if (this.ToolbarButton != null) if (this.ToolbarButton != null)
{ {
this.ToolbarButton.Destroy(); this.ToolbarButton.Destroy();
this.ToolbarButton = null; this.ToolbarButton = null;
} }
   
_instance = null; _instance = null;
_initialized = false; _initialized = false;
} }
} }
} }