/// <summary> /// Called by Unity once to initialize the class. /// </summary> public void Awake( ) { _logger = new Logger( this ); _logger.Trace( "Awake" ); if( _addonInitialized == true ) { // For some reason the addon can be instantiated several times by the KSP addon loader (generally when going to/from the VAB), // even though we set onlyOnce to true in the KSPAddon attribute. return; } }
/// <summary> /// Called by Unity once to initialize the class. /// </summary> public void Awake() { if (_addonInitialized == true) { // For some reason the addon can be instantiated several times by the KSP addon loader (generally when going to/from the VAB), // even though we set onlyOnce to true in the KSPAddon attribute. return; } Config.Load(); _addonInitialized = true; _active = false; _logger = new Logger(this); _logger.Trace("Awake"); _window = new ScienceWindow(); _window.Settings.UseBlizzysToolbarChanged += Settings_UseBlizzysToolbarChanged; _window.OnCloseEvent += OnWindowClosed; _nextSituationUpdate = DateTime.Now; GameEvents.onGUIApplicationLauncherReady.Add(Load); GameEvents.onGUIApplicationLauncherDestroyed.Add(Unload); GameEvents.onVesselWasModified.Add( new EventData<Vessel>.OnEvent( this.VesselWasModified ) ); GameEvents.onVesselChange.Add( new EventData<Vessel>.OnEvent( this.VesselChange ) ); GameEvents.onEditorShipModified.Add( new EventData<ShipConstruct>.OnEvent( this.EditorShipModified ) ); GameEvents.onGameStateSave.Add( new EventData<ConfigNode>.OnEvent( this.GameStateSave ) ); GameEvents.OnPartPurchased.Add( new EventData<AvailablePart>.OnEvent( this.PartPurchased ) ); GameEvents.OnTechnologyResearched.Add( new EventData<GameEvents.HostTargetAction<RDTech, RDTech.OperationResult>>.OnEvent( this.TechnologyResearched ) ); GameEvents.OnScienceChanged.Add( new EventData<float, TransactionReasons>.OnEvent( this.ScienceChanged ) ); GameEvents.OnScienceRecieved.Add( new EventData<float, ScienceSubject, ProtoVessel, bool>.OnEvent( this.ScienceRecieved ) ); GameEvents.onVesselRename.Add( new EventData<GameEvents.HostedFromToAction<Vessel, string>>.OnEvent( this.VesselRename ) ); GameEvents.OnKSCFacilityUpgraded.Add( new EventData<Upgradeables.UpgradeableFacility, int>.OnEvent( this.FacilityUpgrade ) ); // GameEvents.OnKSCFacilityUpgrading.Add(); // GameEvents.OnUpgradeableObjLevelChange.Add(); }
/// <summary> /// Gets all available onboard science. /// </summary> /// <returns>A list containing all of the onboard science on all of the vessels.</returns> public static Dictionary<string, List<ScienceData>> GetOnboardScience( bool CheckDebris ) { // Init var _logger = new Logger( "GameHelper" ); var Start = DateTime.Now; TimeSpan Elapsed; var onboardScience = new List<ScienceData>( ); var vesselIds = new List<string>( ); // Handle loaded craft, remember the Ids so we can filter the unloaded ones var LoadedVessels = FlightGlobals.Vessels.Where (x => x.loaded ); foreach( var v in LoadedVessels ) { if( CheckDebris || v.vesselType != VesselType.Debris ) { onboardScience.AddRange(v .FindPartModulesImplementing<IScienceDataContainer>( ) .SelectMany( y => y.GetData( ) ?? new ScienceData[ 0 ] ) ); vesselIds.Add( v.id.ToString( ).ToLower( ).Replace( "-", "" ) ); } } // Look for science in unloaded vessels. // Don't do debris or already loaded vessels(from routine above) // I was having execptions because something was NULL. // Only happend on a brand-new game, not a load. // This seemed to fix it if( HighLogic.CurrentGame != null && HighLogic.CurrentGame.flightState != null ) { // Dump all the vessels to a save. var node = new ConfigNode( ); HighLogic.CurrentGame.flightState.Save( node ); if( node == null ) _logger.Trace( "flightState save is null" ); else { // Grab the unloaded vessels ConfigNode[] vessels = node.GetNodes( "VESSEL" ); onboardScience.AddRange ( vessels.Where( x => CheckDebris || x.GetValue( "type" ) != "Debris" ) .Where( x => !vesselIds.Contains( x.GetValue( "pid" ) ) ) // Not the active ones, we have them already .SelectMany( x => x.GetNodes("PART") .SelectMany(y => y.GetNodes("MODULE") .SelectMany(z => z.GetNodes("ScienceData")).Select(z => new ScienceData(z)) ) ) ); } } // Turn all the science into a dictionary Dictionary<string, List<ScienceData>> onboardScienceDict = new Dictionary<string, List<ScienceData>>( ); foreach( var i in onboardScience ) { if( !onboardScienceDict.ContainsKey( i.subjectID ) ) onboardScienceDict.Add( i.subjectID, new List<ScienceData>( ) ); onboardScienceDict[ i.subjectID ].Add( i ); } // Return the dictionary Elapsed = DateTime.Now - Start; // _logger.Trace( "GetOnboardScience took " + Elapsed.ToString( ) + "ms and found " + onboardScience.Count( ) + " ScienceData" ); return onboardScienceDict; }
// Called by Unity once to initialize the class, just before Update is called. public void Start( ) { _logger.Trace("Start"); if (_addonInitialized == true) { // For some reason the addon can be instantiated several times by the KSP addon loader (generally when going to/from the VAB), // even though we set onlyOnce to true in the KSPAddon attribute. HammerMusicMute( ); // Ensure we enforce music volume anyway return; } _addonInitialized = true; _active = false; // Config Config = new Config( ); Config.Load( ); // Music Muting if (Config.MusicStartsMuted) { Muted = true; ScreenMessages.PostScreenMessage("[x] Science! - Music Mute"); } GameEvents.onGameSceneSwitchRequested.Add(this.onGameSceneSwitchRequested); GameEvents.onLevelWasLoaded.Add(this.onLevelWasLoaded); // _logger.Trace( "Making DMagic Factory" ); DMagic = new DMagicFactory( ); // _logger.Trace( "Made DMagic Factory" ); // _logger.Trace( "Making ScienceContext" ); Science = new ScienceContext(this); // _logger.Trace( "Made ScienceContext" ); // Start event handlers ScienceEventHandler = new xScienceEventHandler(this); // Settings window _settingsWindow = new SettingsWindow(this); Config.UseBlizzysToolbarChanged += Settings_UseBlizzysToolbarChanged; Config.RighClickMutesMusicChanged += Settings_RighClickMutesMusicChanged; // Help window _helpWindow = new HelpWindow(this); // Status window _alertNoise = gameObject.AddComponent <Noise>( ); _statusWindow = new StatusWindow(this); _statusWindow.NoiseEvent += OnPlayNoise; _statusWindow.WindowClosed += OnStatusWindowClosed; _statusWindow.OnCloseEvent += OnStatusWindowClosed; _statusWindow.OnOpenEvent += OnStatusWindowOpened; // Checklist window _checklistWindow = new ScienceWindow(this, _settingsWindow, _helpWindow); _checklistWindow.OnCloseEvent += OnChecklistWindowClosed; _checklistWindow.OnOpenEvent += OnChecklistWindowOpened; // ShipState Window _shipStateWindow = new ShipStateWindow(this); // Save and load checklist window config when the game scene is changed // We are only visible in some scenes GameEvents.onGameSceneSwitchRequested.Add(new EventData <GameEvents.FromToAction <GameScenes, GameScenes> > .OnEvent(this.OnGameSceneSwitch)); // Callbacks for buttons - we init when the "Launcher" toolbar is ready GameEvents.onGUIApplicationLauncherReady.Add(Load); GameEvents.onGUIApplicationLauncherDestroyed.Add(Unload); // Callbacks for F2 GameEvents.onHideUI.Add(OnHideUI); GameEvents.onShowUI.Add(OnShowUI); DontDestroyOnLoad(this); _logger.Trace("Done Start"); }
// Called by Unity once to initialize the class. public void Awake( ) { _logger = new Logger(this); _logger.Trace("Awake"); }
// Gets all available onboard science. private void UpdateOnboardScience( ) { // Init // var Start = DateTime.Now; // TimeSpan Elapsed; var onboardScience = new List <ScienceData>( ); var vesselIds = new List <string>( ); _currentVesselScience = new List <ScienceData>( ); // Handle loaded craft, remember the Ids so we can filter the unloaded ones var LoadedVessels = FlightGlobals.Vessels.Where(x => x.loaded); List <ScienceData> D = new List <ScienceData>( ); foreach (var v in LoadedVessels) { if (_parent.Config.CheckDebris || v.vesselType != VesselType.Debris) { D = v.FindPartModulesImplementing <IScienceDataContainer>( ) .SelectMany(y => y.GetData( ) ?? new ScienceData[0]).ToList( ); vesselIds.Add(v.id.ToString( ).ToLower( ).Replace("-", "")); onboardScience.AddRange(D); } if (FlightGlobals.ActiveVessel) { if (FlightGlobals.ActiveVessel == v) { _currentVesselScience = D; } } } // Look for science in unloaded vessels. // Don't do debris or already loaded vessels(from routine above) // I was having execptions because something was NULL. // Only happend on a brand-new game, not a load. // This seemed to fix it if (HighLogic.CurrentGame != null && HighLogic.CurrentGame.flightState != null) { // Dump all the vessels to a save. var node = new ConfigNode( ); HighLogic.CurrentGame.flightState.Save(node); if (node == null) { _logger.Trace("flightState save is null"); } else { // Grab the unloaded vessels ConfigNode[] vessels = node.GetNodes("VESSEL"); onboardScience.AddRange ( vessels.Where(x => _parent.Config.CheckDebris || x.GetValue("type") != "Debris") .Where(x => !vesselIds.Contains(x.GetValue("pid"))) // Not the active ones, we have them already .SelectMany(x => x.GetNodes("PART") .SelectMany(y => y.GetNodes("MODULE") .SelectMany(z => z.GetNodes("ScienceData")).Select(z => new ScienceData(z)) ) ) ); } } // Turn all the science into a dictionary Dictionary <string, List <ScienceData> > onboardScienceDict = new Dictionary <string, List <ScienceData> >( ); for (var x = 0; x < onboardScience.Count; x++) { if (!onboardScienceDict.ContainsKey(onboardScience[x].subjectID)) { onboardScienceDict.Add(onboardScience[x].subjectID, new List <ScienceData>( )); } onboardScienceDict[onboardScience[x].subjectID].Add(onboardScience[x]); } // Update the dictionary // Elapsed = DateTime.Now - Start; //_logger.Trace( "GetOnboardScience took " + Elapsed.ToString( ) + "ms and found " + onboardScience.Count( ) + " ScienceData" ); _onboardScience = onboardScienceDict; }
/// <summary> /// Draws the controls inside the window. /// </summary> /// <param name="windowId"></param> private void DrawControls(int windowId) { DrawTitleBarButtons(_rect); GUILayout.BeginHorizontal( ); GUILayout.BeginVertical(GUILayout.Width(480), GUILayout.ExpandHeight(true)); ProgressBar( new Rect(10, 27, 480, 13), _filter.TotalCount == 0 ? 1 : _filter.CompleteCount, _filter.TotalCount == 0 ? 1 : _filter.TotalCount, 0, false, false); GUILayout.Space(20); GUILayout.BeginHorizontal( ); GUILayout.Label ( new GUIContent( string.Format("{0}/{1} complete.", _filter.CompleteCount, _filter.TotalCount), string.Format("{0} remaining\n{1:0.#} mits", _filter.TotalCount - _filter.CompleteCount, _filter.TotalScience - _filter.CompletedScience) ), _experimentProgressLabelStyle, GUILayout.Width(150) ); GUILayout.FlexibleSpace(); GUILayout.Label(new GUIContent(_searchTexture)); _filter.Text = GUILayout.TextField(_filter.Text, GUILayout.Width(150)); if (GUILayout.Button(new GUIContent(_clearSearchTexture, "Clear search"), GUILayout.Width(25), GUILayout.Height(23))) { _filter.Text = string.Empty; } GUILayout.EndHorizontal(); _scrollPos = GUILayout.BeginScrollView(_scrollPos, _skin.scrollView); var i = 0; if (_filter.DisplayScienceInstances == null) { _logger.Trace("DisplayExperiments is null"); } else { for ( ; i < _filter.DisplayScienceInstances.Count; i++) { var rect = new Rect(5, 20 * i, _filter.DisplayScienceInstances.Count > 13 ? 490 : 500, 20); if (rect.yMax < _scrollPos.y || rect.yMin > _scrollPos.y + 400) { continue; } var experiment = _filter.DisplayScienceInstances[i]; DrawExperiment(experiment, rect, false, _labelStyle); } } GUILayout.Space(20 * i); GUILayout.EndScrollView(); GUILayout.BeginHorizontal(); var TextWidth = 290; var NumButtons = 3; GUIContent[] FilterButtons = { new GUIContent(_currentSituationTexture, "Show experiments available right now"), new GUIContent(_currentVesselTexture, "Show experiments available on this vessel"), new GUIContent(_unlockedTexture, "Show all unlocked experiments") }; if (_parent.Config.AllFilter) { Array.Resize(ref FilterButtons, 4); FilterButtons[3] = new GUIContent(_allTexture, "Show all experiments"); TextWidth = 260; NumButtons = 4; } else { if (_filter.DisplayMode == DisplayMode.All) { _filter.DisplayMode = DisplayMode.Unlocked; _filter.UpdateFilter( ); } } _filter.DisplayMode = (DisplayMode)GUILayout.SelectionGrid((int)_filter.DisplayMode, FilterButtons, NumButtons); GUILayout.FlexibleSpace(); if (_filter.CurrentSituation != null) { var desc = _filter.CurrentSituation.Description; GUILayout.Box(char.ToUpper(desc[0]) + desc.Substring(1), _situationStyle, GUILayout.Width(TextWidth)); } GUILayout.FlexibleSpace( ); GUILayout.EndHorizontal(); GUILayout.EndVertical(); GUILayout.EndHorizontal(); GUI.DragWindow(); if (Event.current.type == EventType.Repaint && GUI.tooltip != _lastTooltip) { _lastTooltip = GUI.tooltip; } // If this window gets focus, it pushes the tooltip behind the window, which looks weird. // Just hide the tooltip while mouse buttons are held down to avoid this. if (Input.GetMouseButton(0) || Input.GetMouseButton(1) || Input.GetMouseButton(2)) { _lastTooltip = string.Empty; } }
protected override void DrawWindowContents(int windowID) { GUILayout.BeginVertical( ); if (_filter.CurrentSituation != null && _parent.Science.CurrentVesselScience != null) { var desc = _filter.CurrentSituation.Description; GUILayout.Box ( new GUIContent ( char.ToUpper(desc[0]) + desc.Substring(1), MakeSituationToolTip( ) ), _situationStyle, GUILayout.Width(wScale(250)) ); } int Top = wScale(65); if (_filter.DisplayScienceInstances != null) { for (var i = 0; i < _filter.DisplayScienceInstances.Count; i++) { var rect = new Rect(wScale(5), Top, wScale(250), wScale(30)); var experiment = _filter.DisplayScienceInstances[i]; DrawExperiment(experiment, rect); Top += wScale(35); } } else { _logger.Trace("DisplayExperiments is null"); } if (_filter.DisplayScienceInstances.Count > 0) { GUILayout.Space(wScale(_filter.DisplayScienceInstances.Count * 35)); // Leave space for experiments, as drawn above } GUILayout.Space(wScale(10)); GUILayout.BeginHorizontal( ); GUIContent Content = null; if (_parent.Config.StopTimeWarp) { Content = new GUIContent(_GfxTimeWarp, Localizer.Format("#autoLOC_[x]_Science!_131") /*Time warp will be stopped*/); } else { Content = new GUIContent(_GfxTimeWarpOff, Localizer.Format("#autoLOC_[x]_Science!_132") /*Time warp will not be stopped*/); } if (GUILayout.Button(Content, GUILayout.Width(wScale(36)), GUILayout.Height(wScale(32)))) { _parent.Config.StopTimeWarp = !_parent.Config.StopTimeWarp; _parent.Config.Save( ); } if (_parent.Config.PlayNoise) { Content = new GUIContent(_GfxAudioAlert, Localizer.Format("#autoLOC_[x]_Science!_133") /*Audio alert will sound*/); } else { Content = new GUIContent(_GfxAudioAlertOff, Localizer.Format("#autoLOC_[x]_Science!_134") /*No audio alert*/); } if (GUILayout.Button(Content, GUILayout.Width(wScale(36)), GUILayout.Height(wScale(32)))) { _parent.Config.PlayNoise = !_parent.Config.PlayNoise; _parent.Config.Save( ); } if (_parent.Config.ShowResultsWindow) { Content = new GUIContent(_GfxResultsWindow, Localizer.Format("#autoLOC_[x]_Science!_135") /*Show results window*/); } else { Content = new GUIContent(_GfxResultsWindowOff, Localizer.Format("#autoLOC_[x]_Science!_136") /*Supress results window*/); } if (GUILayout.Button(Content, GUILayout.Width(wScale(36)), GUILayout.Height(wScale(32)))) { _parent.Config.ShowResultsWindow = !_parent.Config.ShowResultsWindow; _parent.Config.Save( ); } GUILayout.EndHorizontal( ); GUILayout.EndVertical( ); GUILayout.Space(wScale(2)); }