public void KITFixedUpdate(IResourceManager resMan)
        {
            if (_solarPanel == null)
            {
                return;
            }

            if (_fieldKerbalismNominalRate != null)
            {
                kerbalism_nominalRate = _fieldKerbalismNominalRate.GetValue <double>(_solarPanelFixer);
                kerbalism_panelState  = _fieldKerbalismPanelStatus.GetValue <string>(_solarPanelFixer);

                var kerbalismPanelStateArray = kerbalism_panelState.Split(' ');

                kerbalism_panelOutput = kerbalismPanelStateArray[0];

                double.TryParse(kerbalism_panelOutput, out kerbalism_panelPower);
            }

            if (_outputResource != null && _solarPanel.deployState == ModuleDeployablePart.DeployState.EXTENDED)
            {
                outputResourceRate           = _outputResource.rate;
                outputResourceCurrentRequest = _outputResource.currentRequest;
            }
            else
            {
                outputResourceRate           = 0;
                outputResourceCurrentRequest = 0;
            }

            chargeRate = _solarPanel.chargeRate;

            double age = (Planetarium.GetUniversalTime() - _solarPanel.launchUT) * 1.15740740740741E-05;

            calculatedEfficency = _solarPanel._efficMult > 0 ? _solarPanel._efficMult :
                                  _solarPanel.temperatureEfficCurve.Evaluate((float)part.skinTemperature) *
                                  _solarPanel.timeEfficCurve.Evaluate((float)age) * _solarPanel.efficiencyMult;

            double maxSupply = 0.0, solarRate = 0.0;

            sunAOA = 0;
            CalculateSolarFlowRate(calculatedEfficency / scale, ref maxSupply, ref solarRate);

            if (_outputResource != null)
            {
                var resID = KITResourceSettings.NameToResource(_solarPanel.resourceName);
                if (resID == ResourceName.Unknown)
                {
                    Debug.Log($"[FNSolarPanelWasteHeatModule.KITFixedUpdate] - do not know how to handle Kerbalism resource request of {_solarPanel.resourceName}");
                }
                else
                {
                    if (kerbalism_panelPower > 0)
                    {
                        resMan.Produce(resID, kerbalism_panelPower);
                    }
                    else if (_outputResource != null)
                    {
                        _outputResource.rate = 0;
                    }
                    else
                    {
                        resMan.Produce(resID, solarRate);
                    }
                }
            }

            resMan.Produce(ResourceName.ElectricCharge, solarRate);
            mjSolarSupply = PluginHelper.GetFormattedPowerString(solarRate);
            mjMaxSupply   = PluginHelper.GetFormattedPowerString(maxSupply);
        }
Exemplo n.º 2
0
        private void UpdateFuelFactors()
        {
            if (!String.IsNullOrEmpty(propellant1))
            {
                propellantResourceDefinition1 = PartResourceLibrary.Instance.GetDefinition(propellant1);
                propellantResourceID1         = KITResourceSettings.NameToResource(propellant1);

                if (propellantResourceDefinition1 == null || propellantResourceID1 == ResourceName.Unknown)
                {
                    Debug.Log($"[ModuleEnginesWarp] UpdateFuelFactors propellant1 is not correctly defined -- {(propellantResourceDefinition1 == null ? "definition" : "resource id")}");
                }
            }
            else
            {
                propellantResourceDefinition1 = null;
                propellantResourceID1         = ResourceName.Unknown;
            }

            if (!String.IsNullOrEmpty(propellant2))
            {
                propellantResourceDefinition2 = PartResourceLibrary.Instance.GetDefinition(propellant2);
                propellantResourceID2         = KITResourceSettings.NameToResource(propellant2);

                if (propellantResourceDefinition2 == null || propellantResourceID2 == ResourceName.Unknown)
                {
                    Debug.Log("[ModuleEnginesWarp] UpdateFuelFactors propellant2 is not correctly defined");
                }
            }
            else
            {
                propellantResourceDefinition2 = null;
                propellantResourceID2         = ResourceName.Unknown;
            }

            if (!String.IsNullOrEmpty(propellant3))
            {
                propellantResourceDefinition3 = PartResourceLibrary.Instance.GetDefinition(propellant3);
                propellantResourceID3         = KITResourceSettings.NameToResource(propellant3);

                if (propellantResourceDefinition3 == null || propellantResourceID3 == ResourceName.Unknown)
                {
                    Debug.Log("[ModuleEnginesWarp] UpdateFuelFactors propellant3 is not correctly defined");
                }
            }
            else
            {
                propellantResourceDefinition3 = null;
                propellantResourceID3         = ResourceName.Unknown;
            }

            if (!String.IsNullOrEmpty(propellant4))
            {
                propellantResourceDefinition4 = PartResourceLibrary.Instance.GetDefinition(propellant4);
                propellantResourceID4         = KITResourceSettings.NameToResource(propellant4);

                if (propellantResourceDefinition4 == null || propellantResourceID4 == ResourceName.Unknown)
                {
                    Debug.Log("[ModuleEnginesWarp] UpdateFuelFactors propellant4 is not correctly defined");
                }
            }
            else
            {
                propellantResourceDefinition4 = null;
                propellantResourceID4         = ResourceName.Unknown;
            }

            var ratioSumOverall  = 0.0;
            var ratioSumWithMass = 0.0;
            var densitySum       = 0.0;

            if (propellantResourceDefinition1 != null)
            {
                ratioSumOverall += ratio1;
                if (propellantResourceDefinition1.density > 0)
                {
                    ratioSumWithMass = ratio1;
                    densitySum      += propellantResourceDefinition1.density * ratio1;
                }
            }
            if (propellantResourceDefinition2 != null)
            {
                ratioSumOverall += ratio2;
                if (propellantResourceDefinition2.density > 0)
                {
                    ratioSumWithMass = ratio2;
                    densitySum      += propellantResourceDefinition2.density * ratio2;
                }
            }
            if (propellantResourceDefinition3 != null)
            {
                ratioSumOverall += ratio3;
                if (propellantResourceDefinition3.density > 0)
                {
                    ratioSumWithMass = ratio3;
                    densitySum      += propellantResourceDefinition3.density * ratio3;
                }
            }
            if (propellantResourceDefinition4 != null)
            {
                ratioSumOverall += ratio4;
                if (propellantResourceDefinition4.density > 0)
                {
                    ratioSumWithMass = ratio4;
                    densitySum      += propellantResourceDefinition4.density * ratio4;
                }
            }

            averageDensityInTonPerLiter = densitySum / ratioSumWithMass;
            massPropellantRatio         = ratioSumWithMass / ratioSumOverall;
            ratioSumWithoutMass         = ratioSumOverall - ratioSumWithMass;

            fuelWithMassPercentage1 = propellantResourceDefinition1 != null && propellantResourceDefinition1.density > 0 ? ratio1 / ratioSumWithMass : 0;
            fuelWithMassPercentage2 = propellantResourceDefinition2 != null && propellantResourceDefinition2.density > 0 ? ratio2 / ratioSumWithMass : 0;
            fuelWithMassPercentage3 = propellantResourceDefinition3 != null && propellantResourceDefinition3.density > 0 ? ratio3 / ratioSumWithMass : 0;
            fuelWithMassPercentage4 = propellantResourceDefinition4 != null && propellantResourceDefinition4.density > 0 ? ratio4 / ratioSumWithMass : 0;

            masslessFuelPercentage1 = propellantResourceDefinition1 != null && propellantResourceDefinition1.density <= 0 ? ratio1 / ratioSumWithoutMass : 0;
            masslessFuelPercentage2 = propellantResourceDefinition2 != null && propellantResourceDefinition2.density <= 0 ? ratio2 / ratioSumWithoutMass : 0;
            masslessFuelPercentage3 = propellantResourceDefinition3 != null && propellantResourceDefinition3.density <= 0 ? ratio3 / ratioSumWithoutMass : 0;
            masslessFuelPercentage4 = propellantResourceDefinition4 != null && propellantResourceDefinition4.density <= 0 ? ratio4 / ratioSumWithoutMass : 0;
        }
        private void DecayFuel(IResourceManager resMan)
        {
            if (HighLogic.CurrentGame.Parameters.CustomParams <KITGamePlayParams>().PreventRadioactiveDecay)
            {
                return;
            }

            double halfLife = GameSettings.KERBIN_TIME ? halfLifeInKerbinSeconds : halfLifeInSeconds;
            double originalMassRemaining = massRemaining;

            var currentPartLifetime = Planetarium.GetUniversalTime() - partLifeStarted;

            massRemaining = massInKilograms * Math.Pow(2, (-currentPartLifetime) / halfLife);

            if (_resourceNotDefined)
            {
                return;
            }

            var productsToGenerateInKG = originalMassRemaining - massRemaining;

            if (_decayResource == null || _decayProductResource == null)
            {
                var config = GameDatabase.Instance.GetConfigNodes("KIT_Radioactive_Decay");
                if (config == null || !config.Any())
                {
                    _resourceNotDefined = true;
                    Debug.Log($"[KITRadioisotopeGenerator] can't find KIT_Radioactive_Decay configuration");
                    return;
                }

                var node = config[0].GetNode(radioisotopeFuel);
                if (node == null)
                {
                    _resourceNotDefined = true;
                    Debug.Log($"[KITRadioisotopeGenerator] {radioisotopeFuel} has no decay products defined");
                    return;
                }

                string decayProduct = "";
                if (node.TryGetValue("product", ref decayProduct) == false)
                {
                    _resourceNotDefined = true;
                    Debug.Log($"[KITRadioisotopeGenerator] {radioisotopeFuel} configuration has no product to decay into defined");
                    return;
                }

                _decayResource        = PartResourceLibrary.Instance.GetDefinition(radioisotopeFuel);
                _decayProductResource = PartResourceLibrary.Instance.GetDefinition(decayProduct);

                if (_decayResource == null || _decayProductResource == null)
                {
                    _resourceNotDefined = true;
                    Debug.Log($"[KITRadioisotopeGenerator] could not get definitions for {(_decayResource == null ? radioisotopeFuel + " " : "")}{(_decayProductResource == null ? decayProduct : "")}");
                    return;
                }

                _decayProductId = KITResourceSettings.NameToResource(decayProduct);
                if (_decayProductId == ResourceName.Unknown)
                {
                    _resourceNotDefined = true;
                    Debug.Log($"[KITRadioisotopeGenerator] could not get KIT definition for {decayProduct}");
                    return;
                }
            }

            var densityRatio = _decayResource.density / _decayProductResource.density;

            resMan.Produce(_decayProductId, productsToGenerateInKG * densityRatio);

            // decay products being generated.
        }
        /// <summary>
        /// Called by the IKITModule to consume resources present on a vessel. It automatically converts the wanted amount by the appropriate value to
        /// give you a per-second resource consumption.
        /// </summary>
        /// <param name="data">Resource Data to consume against</param>
        /// <param name="resource">Resource to consume</param>
        /// <param name="wanted">How much you want</param>
        /// <returns>How much you got</returns>
        public double Consume(ResourceData data, ResourceName resource, double wanted)
        {
            KITResourceSettings.ValidateResource(resource);

            PerPartResourceInformation tmpPPRI;

            if (!_inExecuteKITModules || wanted < 0)
            {
                Debug.Log(
                    $"[KITResourceManager.Consume] don't{(_inExecuteKITModules ? " use outside of IKITModules" : "")} {(wanted < 0 ? " consume negative amounts" : "")}");
                return(0);
            }

            tmpPPRI.Amount = tmpPPRI.MaxAmount = 0;

            var lastMod = data.ModsCurrentlyRunning.Last();

            var trackResourceUsage = TrackableResource(resource) && data.ModConsumption != null && data.ModProduction != null && data.ResourceProductionStats != null;

            if (trackResourceUsage)
            {
                data.ResourceProductionStats[(int)ResourceName.ElectricCharge].InternalCurrentlyRequested += wanted;

                if (!data.ModConsumption[resource].ContainsKey(lastMod))
                {
                    data.ModConsumption[resource][lastMod] = new PerPartResourceInformation();
                }
                tmpPPRI            = data.ModConsumption[resource][lastMod];
                tmpPPRI.MaxAmount += wanted;
            }

            if (data.CheatOptions().InfiniteElectricity&& resource == ResourceName.ElectricCharge)
            {
                tmpPPRI.Amount += wanted;
                data.ModConsumption[resource][lastMod] = tmpPPRI;
                return(wanted);
            }

            if (!data.AvailableResources.ContainsKey(resource))
            {
                data.AvailableResources[resource] = 0;
            }

            double obtainedAmount = 0;
            double modifiedAmount = wanted * _fixedDeltaTime;

            var tmp = Math.Min(data.AvailableResources[resource], modifiedAmount);

            obtainedAmount += tmp;
            data.AvailableResources[resource] -= tmp;

            if (trackResourceUsage && tmp > 0)
            {
                data.ResourceProductionStats[(int)resource].InternalCurrentlySupplied += tmp;
            }

            if (obtainedAmount >= modifiedAmount)
            {
                tmpPPRI.Amount += wanted;
                if (trackResourceUsage)
                {
                    data.ModConsumption[resource][lastMod] = tmpPPRI;
                }

                return(wanted);
            }

            double surplusWanted = 0;

            if (resource != ResourceName.ChargedParticle)
            {
                data.MaxResources.TryGetValue(resource, out surplusWanted);
            }

            // Convert to seconds
            obtainedAmount = wanted * (obtainedAmount / modifiedAmount);
            // Debug.Log($"[Consume] calling variable suppliers for {KITResourceSettings.ResourceToName(resource)}, already have {obtainedAmount}, want a total of {wanted}, with a surplus of {surplusWanted}");
            obtainedAmount = CallVariableSuppliers(data, resource, obtainedAmount, wanted, surplusWanted);

            // We do not need to account for InternalCurrentlySupplied here, as the modules called above will call
            // Produce which credits the InternalCurrentlySupplied field here.

            // is it close enough to being fully requested? (accounting for precision issues)
            var result = (obtainedAmount < (wanted * fudgeFactor)) ? wanted * (obtainedAmount / wanted) : wanted;

            // Debug.Log($"[Consume] after calling variable suppliers, obtainedAmount is {obtainedAmount}, fudged value is {wanted * fudgeFactor}, and result is {result}");

            tmpPPRI.Amount += result;
            if (trackResourceUsage)
            {
                data.ModConsumption[resource][lastMod] = tmpPPRI;
            }

            return(result);
        }