/// <summary>Removes a ground station from the list by its unique <paramref name="stationid"/>.</summary> /// <param name="stationid">Unique ground station id</param> /// <returns>Returns true for a successful removed station, otherwise false.</returns> public bool RemoveGroundStation(Guid stationid) { RTLog.Notify("Trying to remove ground station {0}", RTLogLevel.LVL1, stationid); for (var i = 0; i < GroundStations.Count; i++) { if (!GroundStations[i].mGuid.Equals(stationid)) { continue; } RTLog.Notify("Removing {0} ", RTLogLevel.LVL1, GroundStations[i].GetName()); GroundStations.RemoveAt(i); Save(); return(true); } RTLog.Notify("Cannot find station {0}", RTLogLevel.LVL1, stationid); return(false); }
public void Unregister(Guid key, IAntenna antenna) { RTLog.Notify("AntennaManager: Unregister({0})", antenna); if (!mLoadedAntennaCache.ContainsKey(key)) { return; } int instance_id = mLoadedAntennaCache[key].FindIndex(x => x == antenna); if (instance_id != -1) { mLoadedAntennaCache[key].RemoveAt(instance_id); if (mLoadedAntennaCache[key].Count == 0) { mLoadedAntennaCache.Remove(key); } OnUnregister(antenna); } }
public static ISignalProcessor GetSignalProcessor(this Vessel v) { RTLog.Notify("GetSignalProcessor({0}): Check", v.vesselName); if (v.loaded) { foreach (PartModule pm in v.Parts.SelectMany(p => p.Modules.Cast <PartModule>()).Where(pm => pm.IsSignalProcessor())) { RTLog.Notify("GetSignalProcessor({0}): Found", v.vesselName); return(pm as ISignalProcessor); } } else { foreach (ProtoPartModuleSnapshot ppms in v.protoVessel.protoPartSnapshots.SelectMany(x => x.modules).Where(ppms => ppms.IsSignalProcessor())) { RTLog.Notify("GetSignalProcessor({0}): Found", v.vesselName); return(new ProtoSignalProcessor(ppms, v)); } } return(null); }
/// <summary> /// Registers a protosatellite compiled from the unloaded vessel data. /// </summary> /// <param name="vessel">The vessel.</param> public void RegisterProto(Vessel vessel) { Guid key = vessel.protoVessel.vesselID; RTLog.Notify("SatelliteManager: RegisterProto({0}, {1})", vessel.vesselName, key); // Return if there are still signal processors loaded. if (mLoadedSpuCache.ContainsKey(vessel.id)) { mLoadedSpuCache.Remove(vessel.id); } ISignalProcessor spu = vessel.GetSignalProcessor(); if (spu != null) { List <ISignalProcessor> protos = new List <ISignalProcessor>(); protos.Add(spu); mSatelliteCache[key] = new VesselSatellite(protos); OnRegister(mSatelliteCache[key]); } }
public static Settings Load() { // Create a new settings object Settings settings = new Settings(); // try to load from the base settings.cfg ConfigNode load = ConfigNode.Load(File); if (load == null) { // write new base file to the rt folder settings.Save(); } else { // old or new format? if (load.HasNode("RemoteTechSettings")) { load = load.GetNode("RemoteTechSettings"); } RTLog.Notify("Load base settings into object with {0}", load); // load basic file ConfigNode.LoadObjectFromConfig(settings, load); } // Prefer to load from GameDatabase, to allow easier user customization UrlDir.UrlConfig[] configList = GameDatabase.Instance.GetConfigs("RemoteTechSettings"); foreach (UrlDir.UrlConfig curSet in configList) { // only third party files if (!curSet.url.Equals("RemoteTech/RemoteTech_Settings/RemoteTechSettings")) { RTLog.Notify("Override RTSettings with configs from {0}", curSet.url); settings.backupFields(); ConfigNode.LoadObjectFromConfig(settings, curSet.config); settings.restoreBackups(); } } return(settings); }
/// <summary> /// Unregisters the specified signal processor. /// </summary> /// <param name="key">The key the signal processor was registered under.</param> /// <param name="spu">The signal processor.</param> public void Unregister(Guid key, ISignalProcessor spu) { RTLog.Notify("SatelliteManager: Unregister({0})", spu); // Return if nothing to unregister. if (!mLoadedSpuCache.ContainsKey(key)) { return; } // Find instance of the signal processor. int instanceID = mLoadedSpuCache[key].FindIndex(x => x == spu); if (instanceID != -1) { // Remove satellite if no signal processors remain. if (mLoadedSpuCache[key].Count == 1) { if (mSatelliteCache.ContainsKey(key)) { VesselSatellite sat = mSatelliteCache[key]; OnUnregister(sat); mSatelliteCache.Remove(key); } mLoadedSpuCache[key].RemoveAt(instanceID); mLoadedSpuCache.Remove(key); // search vessel by id Vessel vessel = RTUtil.GetVesselById(key); if (vessel != null) { // trigger the onRails on more time // to reregister the satellite as a protoSat this.OnVesselOnRails(vessel); } } else { mLoadedSpuCache[key].RemoveAt(instanceID); } } }
/// <summary> /// Adds a new ground station to the list. /// </summary> /// <param name="name">Name of the ground station</param> /// <param name="latitude">Latitude position</param> /// <param name="longitude">Longitude position</param> /// <param name="height">Height above sea level</param> /// <param name="body">Reference body 1=Kerbin etc...</param> /// <returns>A new <see cref="Guid"/> if a new station was successfully added otherwise a Guid.Empty.</returns> public Guid AddGroundStation(string name, double latitude, double longitude, double height, int body) { RTLog.Notify("Trying to add ground station({0})", RTLogLevel.LVL1, name); var newGroundStation = new MissionControlSatellite(); newGroundStation.SetDetails(name, latitude, longitude, height, body); // Already on the list? var foundGroundStation = GroundStations.FirstOrDefault(ms => ms.GetDetails().Equals(newGroundStation.GetDetails())); if (foundGroundStation != null) { RTLog.Notify("Ground station already exists!"); return(Guid.Empty); } GroundStations.Add(newGroundStation); Save(); return(newGroundStation.mGuid); }
public static void AddSanctionedPilot(Guid id, Action <FlightCtrlState> autopilot) { var satellite = RTCore.Instance.Satellites[id]; if (satellite == null) { return; } foreach (var spu in satellite.SignalProcessors) { if (spu.FlightComputer == null) { continue; } if (spu.FlightComputer.SanctionedPilots.Contains(autopilot)) { continue; } RTLog.Verbose("Flight: {0} Adding Sanctioned Pilot", id); spu.FlightComputer.SanctionedPilots.Add(autopilot); } }
public void Register(Guid key, IAntenna antenna) { RTLog.Notify("AntennaManager: Register({0})", antenna); if (!mLoadedAntennaCache.ContainsKey(key)) { mLoadedAntennaCache[key] = new List <IAntenna>(); } IAntenna instance = mLoadedAntennaCache[key].Find(a => a == antenna); if (instance == null) { if (mProtoAntennaCache.ContainsKey(key)) { UnregisterProtos(key); } mLoadedAntennaCache[key].Add(antenna); OnRegister.Invoke(antenna); } }
private void AddTransmitter() { if (mTransmitterConfig == null || !mTransmitterConfig.HasValue("name")) { return; } var transmitters = part.FindModulesImplementing <IScienceDataTransmitter>(); if (transmitters.Count > 0) { RTLog.Notify("ModuleRTAntenna: Find TRANSMITTER success."); mTransmitter = transmitters.First(); } else { var copy = new ConfigNode(); mTransmitterConfig.CopyTo(copy); part.AddModule(copy); AddTransmitter(); RTLog.Notify("ModuleRTAntenna: Add TRANSMITTER success."); } }
private static void SearchAndPreparePresets(Settings settings) { var presetsChanged = false; // Exploit KSP's GameDatabase to find third-party mods' RemoteTechSetting node (from GameData/ExampleMod/RemoteTechSettings.cfg) var cfgs = GameDatabase.Instance.GetConfigs("RemoteTechSettings"); var rtSettingCfGs = cfgs.Select(x => x.url).ToList(); //check for any invalid preset in the settings of a save for (var i = 0; i < settings.PreSets.Count(); i++) { if (rtSettingCfGs.Contains(settings.PreSets[i])) { continue; } RTLog.Notify("Remove an invalid setting preset {0}", settings.PreSets[i]); settings.PreSets.RemoveAt(i); presetsChanged = true; } //find and add new presets to the settings of a save for (var i = 0; i < rtSettingCfGs.Count(); i++) { if (settings.PreSets.Contains(rtSettingCfGs[i])) { continue; } RTLog.Notify("Add a new setting preset {0}", rtSettingCfGs[i]); settings.PreSets.Add(rtSettingCfGs[i]); presetsChanged = true; } if (presetsChanged) // only if new RT settings are found and added to the save-setting's PreSets node { settings.Save(); } }
/// <summary> /// Saves the current RTSettings object to the RemoteTech_Settings.cfg /// </summary> public void Save() { try { // only save the settings if the file name is not empty (i.e. not on loading screen or in training) if (string.IsNullOrEmpty(SaveSettingFile)) { return; } var details = new ConfigNode("RemoteTechSettings"); ConfigNode.CreateConfigFromObject(this, 0, details); var save = new ConfigNode(); save.AddNode(details); save.Save(SaveSettingFile); RTSettings.OnSettingsSaved.Fire(); } catch (Exception e) { RTLog.Notify("An error occurred while attempting to save: {0}", RTLogLevel.LVL1, e.Message); } }
public void Start() { // Destroy the Core instance if != null or if Remotetech is disabled if (Instance != null || !RTSettings.Instance.RemoteTechEnabled) { Destroy(this); return; } Instance = this; ctrlLockAddon = new AddOns.ControlLockAddon(); kacAddon = new AddOns.KerbalAlarmClockAddon(); Satellites = new SatelliteManager(); Antennas = new AntennaManager(); Network = new NetworkManager(); Renderer = NetworkRenderer.CreateAndAttach(); FilterOverlay = new FilterOverlay(); FocusOverlay = new FocusOverlay(); TimeWarpDecorator = new TimeWarpDecorator(); // Handling new F2 GUI Hiding GameEvents.onShowUI.Add(UIOn); GameEvents.onHideUI.Add(UIOff); FlightUIPatcher.Patch(); RTLog.Notify("RTCore {0} loaded successfully.", RTUtil.Version); foreach (var vessel in FlightGlobals.Vessels) { Satellites.RegisterProto(vessel); Antennas.RegisterProtos(vessel); } }
private List <IScalarModule> FindFxModules(int[] indices, bool showUI) { var modules = new List <IScalarModule>(); if (indices == null) { return(modules); } foreach (int i in indices) { var item = base.part.Modules[i] as IScalarModule; if (item != null) { item.SetUIWrite(showUI); item.SetUIRead(showUI); modules.Add(item); } else { RTLog.Notify("ModuleRTAntenna: Part Module {0} doesn't implement IScalarModule", part.Modules[i].name); } } return(modules); }
private IEnumerator Transmit() { var msg = new ScreenMessage(String.Format("[{0}]: Starting Transmission...", part.partInfo.title), 4f, ScreenMessageStyle.UPPER_LEFT); var msg_status = new ScreenMessage(String.Empty, 4.0f, ScreenMessageStyle.UPPER_LEFT); ScreenMessages.PostScreenMessage(msg); mBusy = true; while (mQueue.Any()) { RnDCommsStream commStream = null; var science_data = mQueue[0]; var data_amount = science_data.dataAmount; mQueue.RemoveAt(0); var subject = ResearchAndDevelopment.GetSubjectByID(science_data.subjectID); int packets = Mathf.CeilToInt(science_data.dataAmount / PacketSize); if (ResearchAndDevelopment.Instance != null) { // pre calculate the time interval - fix for x64 systems // workaround for issue #136 float time1 = Time.time; yield return(new WaitForSeconds(PacketInterval)); // get the delta time float x64PacketInterval = (Time.time - time1); RTLog.Notify("Changing RnDCommsStream timeout from {0} to {1}", PacketInterval, x64PacketInterval); commStream = new RnDCommsStream(subject, science_data.dataAmount, x64PacketInterval, science_data.transmitValue, ResearchAndDevelopment.Instance); } //StartCoroutine(SetFXModules_Coroutine(modules_progress, 0.0f)); float power = 0; while (packets > 0) { power += part.RequestResource("ElectricCharge", PacketResourceCost - power); if (power >= PacketResourceCost * 0.95) { float frame = Math.Min(PacketSize, data_amount); power -= PacketResourceCost; GUI_Status = "Uploading Data..."; data_amount -= frame; packets--; float progress = (science_data.dataAmount - data_amount) / science_data.dataAmount; //StartCoroutine(SetFXModules_Coroutine(modules_progress, progress)); msg_status.message = String.Format("[{0}]: Uploading Data... {1}", part.partInfo.title, progress.ToString("P0")); RTLog.Notify("[Transmitter]: Uploading Data... ({0}) - {1} Mits/sec. Packets to go: {2} - Files to Go: {3}", science_data.title, (PacketSize / PacketInterval).ToString("0.00"), packets, mQueue.Count); ScreenMessages.PostScreenMessage(msg_status, true); if (commStream != null) { commStream.StreamData(frame); } } else { msg.message = String.Format("<b><color=orange>[{0}]: Warning! Not Enough {1}!</color></b>", part.partInfo.title, RequiredResource); ScreenMessages.PostScreenMessage(msg, true); GUI_Status = String.Format("{0}/{1} {2}", power, PacketResourceCost, RequiredResource); } yield return(new WaitForSeconds(PacketInterval)); } yield return(new WaitForSeconds(PacketInterval * 2)); } mBusy = false; msg.message = String.Format("[{0}]: Done!", part.partInfo.title); ScreenMessages.PostScreenMessage(msg, true); GUI_Status = "Idle"; yield break; }
private void OnVesselDestroy(Vessel v) { RTLog.Notify("SatelliteManager: OnVesselDestroy({0}, {1})", v.id, v.vesselName); UnregisterProto(v.id); }
public static Settings Load() { // Create a new settings object Settings settings = new Settings(); // Disable RemoteTech on Training missions if (RTUtil.IsGameScenario) { settings.RemoteTechEnabled = false; } // skip loading if we are on the loading screen // and return the default object and also for // scenario games. if (string.IsNullOrEmpty(Settings.File)) { return(settings); } settings.settingsLoaded = true; // try to load from the base settings.cfg ConfigNode load = ConfigNode.Load(Settings.File); if (load == null) { // write new base file to the rt folder settings.Save(); settings.firstStart = true; } else { // old or new format? if (load.HasNode("RemoteTechSettings")) { load = load.GetNode("RemoteTechSettings"); } RTLog.Notify("Load base settings into object with {0}", load); // load basic file ConfigNode.LoadObjectFromConfig(settings, load); } bool presetsLoaded = false; // Prefer to load from GameDatabase, to allow easier user customization UrlDir.UrlConfig[] configList = GameDatabase.Instance.GetConfigs("RemoteTechSettings"); // find the default_settings from remote tech to load as the first settings UrlDir.UrlConfig defConfig = Array.Find(configList, cl => cl.url.Equals("RemoteTech/Default_Settings/RemoteTechSettings") && !settings.PreSets.Contains(cl.url)); if (defConfig != null) { RTLog.Notify("Load default remotetech settings", RTLogLevel.LVL1); settings = Settings.LoadPreset(settings, defConfig); } foreach (UrlDir.UrlConfig curSet in configList) { // only third party files if (!curSet.url.Equals("RemoteTech/RemoteTech_Settings/RemoteTechSettings") && !settings.PreSets.Contains(curSet.url)) { settings = Settings.LoadPreset(settings, curSet); // trigger to save the settings again presetsLoaded = true; } } if (presetsLoaded) { settings.Save(); } RTSettings.OnSettingsLoaded.Fire(); return(settings); }
private void OnVesselCreate(Vessel v) { RTLog.Notify("SatelliteManager: OnVesselCreate({0}, {1})", v.id, v.vesselName); }
private void OnSatelliteRegister(ISatellite s) { RTLog.Notify("NetworkManager: SatelliteRegister({0})", s); Graph[s.Guid] = new List <NetworkLink <ISatellite> >(); }
/// <summary> /// Utilise KSP's GameDatabase to get a list of cfgs, included our Default_Settings.cfg, contained the 'RemoteTechSettings' /// node and process each cfg accordingly /// /// NOTE: Please do not use the static 'Default_Settings.cfg' file directly because we want third-party modders to apply /// ModuleManager patches of their tweaks, like no signal delay, to our default-settings cfg that will be used when a /// player starts a new game. (refer to our online manual for more details) /// </summary> public static Settings Load() { // Create a blank object of settings var settings = new Settings(); var defaultSuccess = false; // Exploit KSP's GameDatabase to find our MM-patched cfg of default settings (from GameData/RemoteTech/Default_Settings.cfg) var cfgs = GameDatabase.Instance.GetConfigs("RemoteTechSettings"); for (var i = 0; i < cfgs.Length; i++) { if (cfgs[i].url.Equals(DefaultSettingCfgURL)) { defaultSuccess = ConfigNode.LoadObjectFromConfig(settings, cfgs[i].config); RTLog.Notify("Load default settings into object with {0}: LOADED {1}", cfgs[i].config, defaultSuccess ? "OK" : "FAIL"); break; } } if (!defaultSuccess) // disable itself and write explanation to KSP's log { RTLog.Notify("RemoteTech is disabled because the default cfg '{0}' is not found", DefaultSettingCfgURL); return(null); // the main impact of returning null is the endless loop of invoking Load() in the KSP's loading screen } settings.SettingsLoaded = true; // Disable RemoteTech on Training missions if (RTUtil.IsGameScenario) { settings.RemoteTechEnabled = false; settings.CommNetEnabled = true; } // stop and return default settings if we are on the KSP loading screen OR in training scenarios if (string.IsNullOrEmpty(SaveSettingFile)) { return(settings); } // try to load from the save-settings.cfg (MM-patches will not touch because it is outside GameData) var load = ConfigNode.Load(SaveSettingFile); if (load == null) { // write the RT settings to the player's save folder settings.Save(); settings.FirstStart = true; } else { // old or new format? if (load.HasNode("RemoteTechSettings")) { load = load.GetNode("RemoteTechSettings"); } // replace the default settings with save-setting file var success = ConfigNode.LoadObjectFromConfig(settings, load); RTLog.Notify("Found and load save settings into object with {0}: LOADED {1}", load, success ? "OK" : "FAIL"); } // find third-party mods' RemoteTech settings SearchAndPreparePresets(settings); RTSettings.OnSettingsLoaded.Fire(); return(settings); }
/// <summary> /// Utilise KSP's GameDatabase to get a list of cfgs, included our Default_Settings.cfg, contained the 'RemoteTechSettings' /// node and process each cfg accordingly /// /// NOTE: Please do not use the static 'Default_Settings.cfg' file directly because we want third-party modders to apply /// ModuleManager patches of their tweaks, like no signal delay, to our default-settings cfg that will be used when a /// player starts a new game. (refer to our online manual for more details) /// </summary> public static Settings Load() { // Create a blank object of settings var settings = new Settings(); var defaultSuccess = false; // Exploit KSP's GameDatabase to find our MM-patched cfg of default settings (from GameData/RemoteTech/Default_Settings.cfg) var cfgs = GameDatabase.Instance.GetConfigs("RemoteTechSettings"); for (var i = 0; i < cfgs.Length; i++) { if (cfgs[i].url.Equals(DefaultSettingCfgURL)) { defaultSuccess = ConfigNode.LoadObjectFromConfig(settings, cfgs[i].config); RTLog.Notify("Load default settings into object with {0}: LOADED {1}", cfgs[i].config, defaultSuccess ? "OK" : "FAIL"); break; } } if (!defaultSuccess) // disable itself and write explanation to KSP's log { RTLog.Notify("RemoteTech is disabled because the default cfg '{0}' is not found", DefaultSettingCfgURL); return(null); // the main impact of returning null is the endless loop of invoking Load() in the KSP's loading screen } settings.SettingsLoaded = true; // Disable RemoteTech on Training missions if (RTUtil.IsGameScenario) { settings.RemoteTechEnabled = false; settings.CommNetEnabled = true; } // stop and return default settings if we are on the KSP loading screen OR in training scenarios if (string.IsNullOrEmpty(SaveSettingFile)) { return(settings); } // try to load from the save-settings.cfg (MM-patches will not touch because it is outside GameData) var load = ConfigNode.Load(SaveSettingFile); if (load == null) { // write the RT settings to the player's save folder settings.Save(); settings.FirstStart = true; } else { // old or new format? if (load.HasNode("RemoteTechSettings")) { load = load.GetNode("RemoteTechSettings"); } // replace the default settings with save-setting file var success = ConfigNode.LoadObjectFromConfig(settings, load); RTLog.Notify("Found and load save settings into object with {0}: LOADED {1}", load, success ? "OK" : "FAIL"); } // find third-party mods' RemoteTech settings SearchAndPreparePresets(settings); // Detect if the celestial body, that Mission Control is on (default body index 1), is Kerbin var KSCMC = settings.GroundStations.Find(x => x.GetName().Equals("Mission Control")); // leave extra ground stations to modders, who need to provide MM patches if (KSCMC != null && !KSCMC.GetBody().name.Equals("Kerbin") && KSCMC.GetBody().flightGlobalsIndex == 1) // Kopernicus or similar map changes the planet { KSCMC.SetBodyIndex(FlightGlobals.GetHomeBodyIndex()); RTLog.Notify("KSC's Mission Control is on the wrong planet (not Kerbin/Earth) (Any Kopernicus/similar map would change). Relocated to the homeworld's body index {0}.", FlightGlobals.GetHomeBodyIndex()); } RTSettings.OnSettingsLoaded.Fire(); return(settings); }