internal override void Update() { if (!isReady) { return; } if (masterStatus == null) { masterStatus = new Dictionary <Guid, MasterStatusItem>(); } currentUTC = Planetarium.GetUniversalTime(); // ensure out vessel list is up to date CacheVessels(); if (currentUTC >= lastMasterStatusUpdate + tfScenario.userSettings.masterStatusUpdateFrequency) { lastMasterStatusUpdate = currentUTC; VerifyMasterStatus(); } // process vessels foreach (var entry in knownVessels) { Vessel vessel = FlightGlobals.Vessels.Find(v => v.id == entry.Key); if (vessel.loaded) { foreach (Part part in vessel.parts) { ITestFlightCore core = TestFlightUtil.GetCore(part); if (core != null) { // Poll for flight data and part status if (currentUTC >= lastDataPoll + tfScenario.userSettings.masterStatusUpdateFrequency) { TestFlightData currentFlightData = new TestFlightData(); currentFlightData.scope = core.GetScope(); currentFlightData.flightData = core.GetFlightData(); currentFlightData.flightTime = core.GetFlightTime(); PartStatus partStatus = new PartStatus(); partStatus.flightCore = core; partStatus.partName = TestFlightUtil.GetPartTitle(part); partStatus.partID = part.flightID; partStatus.flightData = currentFlightData.flightData; partStatus.flightTime = currentFlightData.flightTime; partStatus.partStatus = core.GetPartStatus(); partStatus.timeToRepair = core.GetRepairTime(); double failureRate = core.GetBaseFailureRate(); MomentaryFailureRate momentaryFailureRate = core.GetWorstMomentaryFailureRate(); if (momentaryFailureRate.valid && momentaryFailureRate.failureRate > failureRate) { failureRate = momentaryFailureRate.failureRate; } partStatus.momentaryFailureRate = failureRate; partStatus.repairRequirements = core.GetRequirementsTooltip(); partStatus.acknowledged = core.IsFailureAcknowledged(); partStatus.activeFailure = core.GetFailureModule(); partStatus.mtbfString = core.FailureRateToMTBFString(failureRate, TestFlightUtil.MTBFUnits.SECONDS, 999); // Update or Add part status in Master Status if (masterStatus.ContainsKey(vessel.id)) { // Vessel is already in the Master Status, so check if part is in there as well int numItems = masterStatus[vessel.id].allPartsStatus.Count(p => p.partID == part.flightID); int existingPartIndex; if (numItems == 1) { existingPartIndex = masterStatus[vessel.id].allPartsStatus.FindIndex(p => p.partID == part.flightID); masterStatus[vessel.id].allPartsStatus[existingPartIndex] = partStatus; } else if (numItems == 0) { masterStatus[vessel.id].allPartsStatus.Add(partStatus); } else { existingPartIndex = masterStatus[vessel.id].allPartsStatus.FindIndex(p => p.partID == part.flightID); masterStatus[vessel.id].allPartsStatus[existingPartIndex] = partStatus; Log("[ERROR] TestFlightManager: Found " + numItems + " matching parts in Master Status Display!"); } } else { // Vessel is not in the Master Status so create a new entry for it and add this part MasterStatusItem masterStatusItem = new MasterStatusItem(); masterStatusItem.vesselID = vessel.id; masterStatusItem.vesselName = vessel.GetName(); masterStatusItem.allPartsStatus = new List <PartStatus>(); masterStatusItem.allPartsStatus.Add(partStatus); masterStatus.Add(vessel.id, masterStatusItem); } PartFlightData data = tfScenario.GetFlightDataForPartName(TestFlightUtil.GetFullPartName(part)); if (data != null) { data.AddFlightData(part.name, currentFlightData); } else { data = new PartFlightData(); data.AddFlightData(TestFlightUtil.GetFullPartName(part), currentFlightData); tfScenario.SetFlightDataForPartName(TestFlightUtil.GetFullPartName(part), data); } } } } } if (currentUTC >= lastDataPoll + tfScenario.userSettings.minTimeBetweenDataPoll) { lastDataPoll = currentUTC; } if (currentUTC >= lastFailurePoll + tfScenario.userSettings.minTimeBetweenFailurePoll) { lastFailurePoll = currentUTC; } } }