Ejemplo n.º 1
0
        public void FixedUpdate()
        {
            if (HighLogic.LoadedSceneIsFlight)
            {
                ElectricEngineControllerFX.getAllPropellants().ForEach(prop => part.Effect(prop.ParticleFXName, 0)); // set all FX to zero

                if (_current_propellant != null && _attached_engine != null)
                {
                    updateISP();
                    int    engine_count      = Math.Max(vessel.FindPartModulesImplementing <ElectricEngineControllerFX>().Count(ee => ee.IsOperational), 1); // max of operational electric engines and 1
                    double total_max_thrust  = evaluateMaxThrust();
                    double thrust_per_engine = total_max_thrust / (double)engine_count;
                    double power_per_engine  = Math.Min(0.5 * _attached_engine.currentThrottle * thrust_per_engine * _current_propellant.IspMultiplier * baseISP / 1000.0 * 9.81, maxPower * _current_propellant.Efficiency);
                    double power_received    = consumeFNResource(power_per_engine * TimeWarp.fixedDeltaTime / _current_propellant.Efficiency, FNResourceManager.FNRESOURCE_MEGAJOULES) / TimeWarp.fixedDeltaTime;
                    double heat_to_produce   = power_received * (1.0 - _current_propellant.Efficiency);
                    double heat_production   = supplyFNResource(heat_to_produce * TimeWarp.fixedDeltaTime, FNResourceManager.FNRESOURCE_WASTEHEAT) / TimeWarp.fixedDeltaTime;
                    // update GUI Values
                    _electrical_consumption_f = (float)power_received;
                    _heat_production_f        = (float)heat_production;
                    // thrust values
                    double thrust_ratio      = power_per_engine > 0 ? Math.Min(power_received / power_per_engine, 1.0) : 1;
                    double actual_max_thrust = _current_propellant.Efficiency * 2000.0f * power_received / (_current_propellant.IspMultiplier * baseISP * 9.81f * _attached_engine.currentThrottle);

                    if (_attached_engine.currentThrottle > 0)
                    {
                        if (!double.IsNaN(actual_max_thrust) && !double.IsInfinity(actual_max_thrust))
                        {
                            _attached_engine.maxThrust = Mathf.Max((float)actual_max_thrust, 0.00001f);
                        }
                        else
                        {
                            _attached_engine.maxThrust = 0.00001f;
                        }
                        float fx_ratio = Mathf.Min(_electrical_consumption_f / maxPower, _attached_engine.finalThrust / _attached_engine.maxThrust);
                        part.Effect(_current_propellant.ParticleFXName, fx_ratio);
                    }

                    if (isupgraded)
                    {
                        List <PartResource> vacuum_resources = part.GetConnectedResources(InterstellarResourcesConfiguration.Instance.VacuumPlasma).ToList();
                        double vacuum_plasma_needed          = vacuum_resources.Sum(vc => vc.maxAmount - vc.amount);
                        double vacuum_plasma_current         = vacuum_resources.Sum(vc => vc.amount);

                        if (vessel.IsInAtmosphere())
                        {
                            part.RequestResource(InterstellarResourcesConfiguration.Instance.VacuumPlasma, vacuum_plasma_current);
                        }
                        else
                        {
                            part.RequestResource(InterstellarResourcesConfiguration.Instance.VacuumPlasma, -vacuum_plasma_needed);
                        }
                    }
                }
            }
        }
        public void FixedUpdate()
        {
            if (HighLogic.LoadedSceneIsFlight)
            {
                ElectricEngineControllerFX.getAllPropellants().ForEach(prop => part.Effect(prop.ParticleFXName, 0)); // set all FX to zero

                if (current_propellant != null && attachedEngine != null)
                {
                    updateISP();
                    List <ElectricEngineControllerFX> electric_engine_list = vessel.FindPartModulesImplementing <ElectricEngineControllerFX>();
                    int    engine_count      = electric_engine_list.Count;
                    double total_max_thrust  = evaluateMaxThrust();
                    double thrust_per_engine = total_max_thrust / (double)engine_count;
                    double power_per_engine  = Math.Min(0.5 * attachedEngine.currentThrottle * thrust_per_engine * current_propellant.IspMultiplier * baseISP / 1000.0 * 9.81, maxPower * current_propellant.Efficiency);
                    double power_received    = consumeFNResource(power_per_engine * TimeWarp.fixedDeltaTime / current_propellant.Efficiency, FNResourceManager.FNRESOURCE_MEGAJOULES) / TimeWarp.fixedDeltaTime;
                    double heat_to_produce   = power_received * (1.0 - current_propellant.Efficiency);
                    double heat_production   = supplyFNResource(heat_to_produce * TimeWarp.fixedDeltaTime, FNResourceManager.FNRESOURCE_WASTEHEAT) / TimeWarp.fixedDeltaTime;
                    // update GUI Values
                    electrical_consumption_f = (float)power_received;
                    heat_production_f        = (float)heat_production;
                    // thrust values
                    double thrust_ratio      = power_per_engine > 0 ? Math.Min(power_received / power_per_engine, 1.0) : 1;
                    double actual_max_thrust = current_propellant.Efficiency * 2000.0f * power_received / (current_propellant.IspMultiplier * baseISP * 9.81f * attachedEngine.currentThrottle);

                    if (attachedEngine.currentThrottle > 0)
                    {
                        if (!double.IsNaN(actual_max_thrust) && !double.IsInfinity(actual_max_thrust))
                        {
                            attachedEngine.maxThrust = Mathf.Max((float)actual_max_thrust, 0.00001f);
                        }
                        else
                        {
                            attachedEngine.maxThrust = 0.00001f;
                        }
                        float fx_ratio = Mathf.Min(electrical_consumption_f / maxPower, attachedEngine.finalThrust / attachedEngine.maxThrust);
                        part.Effect(current_propellant.ParticleFXName, fx_ratio);
                    }

                    if (isupgraded)
                    {
                        List <PartResource> vacuum_resources = part.GetConnectedResources("VacuumPlasma").ToList();
                        double vacuum_plasma_needed          = vacuum_resources.Sum(vc => vc.maxAmount - vc.amount);
                        double vacuum_plasma_current         = vacuum_resources.Sum(vc => vc.amount);
                        if (vessel.altitude < PluginHelper.getMaxAtmosphericAltitude(vessel.mainBody))
                        {
                            part.RequestResource("VacuumPlasma", vacuum_plasma_current);
                        }
                        else
                        {
                            part.RequestResource("VacuumPlasma", -vacuum_plasma_needed);
                        }
                    }
                }
            }
        }
        public void FixedUpdate()
        {
            if (initializationCountdown > 0)
            {
                initializationCountdown--;
            }

            if (!HighLogic.LoadedSceneIsFlight)
            {
                return;
            }

            if (_attached_engine == null)
            {
                return;
            }

            if (_attached_engine is ModuleEnginesFX)
            {
                ElectricEngineControllerFX.getAllPropellants().ForEach(prop => part.Effect(prop.ParticleFXName, 0, -1)); // set all FX to zero
            }
            if (Current_propellant == null)
            {
                return;
            }

            if (!this.vessel.packed && !warpToReal)
            {
                storedThrotle = vessel.ctrlState.mainThrottle;
            }

            // retrieve power
            maxEffectivePower = MaxEffectivePower;
            var sumOfAllEffectivePower = vessel.FindPartModulesImplementing <ElectricEngineControllerFX>().Where(ee => ee.IsOperational).Sum(ee => ee.MaxEffectivePower);

            _electrical_share_f = sumOfAllEffectivePower > 0 ? maxEffectivePower / sumOfAllEffectivePower : 1;

            maxThrottlePower = maxEffectivePower * ModifiedThrotte;
            var currentPropellantEfficiency = CurrentPropellantEfficiency;

            if (CheatOptions.InfiniteElectricity)
            {
                power_request = maxThrottlePower;
            }
            else
            {
                var availablePower     = Math.Max(getStableResourceSupply(ResourceManager.FNRESOURCE_MEGAJOULES) - getCurrentHighPriorityResourceDemand(ResourceManager.FNRESOURCE_MEGAJOULES), 0);
                var megaJoulesBarRatio = getResourceBarRatio(ResourceManager.FNRESOURCE_MEGAJOULES);

                var effectiveResourceThrotling = megaJoulesBarRatio > oneThird ? 1 : megaJoulesBarRatio * 3;

                var power_per_engine = effectiveResourceThrotling * ModifiedThrotte * EvaluateMaxThrust(availablePower * _electrical_share_f) * CurrentIspMultiplier * _modifiedEngineBaseISP / GetPowerThrustModifier() * _g0;
                power_request = currentPropellantEfficiency <= 0 ? 0 : Math.Min(power_per_engine / currentPropellantEfficiency, maxThrottlePower);
            }

            var power_received = CheatOptions.InfiniteElectricity
                ? power_request
                : consumeFNResource(power_request * TimeWarp.fixedDeltaTime, ResourceManager.FNRESOURCE_MEGAJOULES) / TimeWarp.fixedDeltaTime;

            // produce waste heat
            var heat_to_produce = power_received * (1 - currentPropellantEfficiency) * Current_propellant.WasteHeatMultiplier;

            var heat_production = CheatOptions.IgnoreMaxTemperature
                ? heat_to_produce
                : supplyFNResourceFixed(heat_to_produce * TimeWarp.fixedDeltaTime, ResourceManager.FNRESOURCE_WASTEHEAT) / TimeWarp.fixedDeltaTime;

            // update GUI Values
            _electrical_consumption_f = power_received;
            _heat_production_f        = heat_production;

            var effectiveIsp = _modifiedCurrentPropellantIspMultiplier * _modifiedEngineBaseISP * ThrottleModifiedIsp();

            var max_thrust_in_space = currentPropellantEfficiency * CurrentPropellantThrustMultiplier * ModifiedThrotte * GetPowerThrustModifier() * power_received / (effectiveIsp * _g0);

            _maxISP             = _modifiedEngineBaseISP * _modifiedCurrentPropellantIspMultiplier * CurrentPropellantThrustMultiplier * ThrottleModifiedIsp();
            _max_fuel_flow_rate = _maxISP <= 0 ? 0 : max_thrust_in_space / _maxISP / PluginHelper.GravityConstant;

            var max_thrust_with_current_throttle = max_thrust_in_space * ModifiedThrotte;

            throtle_max_thrust = Current_propellant.SupportedEngines == 8
                ? max_thrust_with_current_throttle
                : Math.Max(max_thrust_with_current_throttle - (exitArea * FlightGlobals.getStaticPressure(vessel.transform.position)), 0);

            float throttle = _attached_engine.currentThrottle > 0 ? Mathf.Max(_attached_engine.currentThrottle, 0.01f) : 0;

            //if (ModifiedThrotte > 0)
            if (throttle > 0 && !this.vessel.packed)
            {
                if (IsValidPositiveNumber(throtle_max_thrust) && IsValidPositiveNumber(max_thrust_with_current_throttle))
                {
                    updateISP(throtle_max_thrust / max_thrust_with_current_throttle);
                    _attached_engine.maxFuelFlow = (float)Math.Max(_max_fuel_flow_rate * (ModifiedThrotte / _attached_engine.currentThrottle), 0.0000000001);
                }
                else
                {
                    updateISP(0.000001);
                    _attached_engine.maxFuelFlow = 0.0000000001f;
                }

                if (_attached_engine is ModuleEnginesFX)
                {
                    this.part.Effect(Current_propellant.ParticleFXName, Mathf.Min((float)Math.Pow(_electrical_consumption_f / maxEffectivePower, 0.5), _attached_engine.finalThrust / _attached_engine.maxThrust), -1);
                }
            }
            else if (this.vessel.packed && _attached_engine.enabled && FlightGlobals.ActiveVessel == vessel && throttle > 0 && initializationCountdown == 0)
            {
                warpToReal = true; // Set to true for transition to realtime

                PersistantThrust(TimeWarp.fixedDeltaTime, Planetarium.GetUniversalTime(), this.part.transform.up, this.vessel.GetTotalMass());
            }
            else
            {
                throtle_max_thrust = 0;
                var projected_max_thrust = Math.Max(max_thrust_in_space - (exitArea * FlightGlobals.getStaticPressure(vessel.transform.position)), 0);

                if (IsValidPositiveNumber(projected_max_thrust) && IsValidPositiveNumber(max_thrust_in_space))
                {
                    updateISP(projected_max_thrust / max_thrust_in_space);
                    _attached_engine.maxFuelFlow = (float)Math.Max(_max_fuel_flow_rate, 0.0000000001);
                }
                else
                {
                    updateISP(1);
                    _attached_engine.maxFuelFlow = 0.0000000001f;
                }

                if (_attached_engine is ModuleEnginesFX)
                {
                    this.part.Effect(Current_propellant.ParticleFXName, 0, -1);
                }
            }

            if (isupgraded && vacuumPlasmaResource != null)
            {
                //vacuumPlasmaResource.maxAmount = maxPower * 0.00001 * TimeWarp.fixedDeltaTime;
                this.part.RequestResource(InterstellarResourcesConfiguration.Instance.VacuumPlasma, -vacuumPlasmaResource.maxAmount);
            }
        }
Ejemplo n.º 4
0
        public void FixedUpdate()
        {
            if (!HighLogic.LoadedSceneIsFlight)
            {
                return;
            }

            if (_attached_engine is ModuleEnginesFX)
            {
                ElectricEngineControllerFX.getAllPropellants().ForEach(prop => part.Effect(prop.ParticleFXName, 0)); // set all FX to zero
            }
            if (Current_propellant == null || _attached_engine == null)
            {
                return;
            }

            // retrieve power
            _electrical_share_f = maxPower / Math.Max(vessel.FindPartModulesImplementing <ElectricEngineControllerFX>().Where(ee => ee.IsOperational).Sum(ee => ee.maxPower), maxPower);
            double powerAvailableForEngine = Math.Max(getStableResourceSupply(FNResourceManager.FNRESOURCE_MEGAJOULES) - getCurrentHighPriorityResourceDemand(FNResourceManager.FNRESOURCE_MEGAJOULES), 0) * _electrical_share_f;
            double power_per_engine        = Math.Min(GetModifiedThrotte() * EvaluateMaxThrust(powerAvailableForEngine) * _current_propellant.IspMultiplier * _modifiedEngineBaseISP / GetPowerThrustModifier() * _g0, maxPower * CurrentPropellantEfficiency);

            double power_received = consumeFNResource(power_per_engine * TimeWarp.fixedDeltaTime / CurrentPropellantEfficiency, FNResourceManager.FNRESOURCE_MEGAJOULES) / TimeWarp.fixedDeltaTime;

            // produce waste heat
            double heat_to_produce = power_received * (1.0 - CurrentPropellantEfficiency) * Current_propellant.WasteHeatMultiplier;
            double heat_production = supplyFNResource(heat_to_produce * TimeWarp.fixedDeltaTime, FNResourceManager.FNRESOURCE_WASTEHEAT) / TimeWarp.fixedDeltaTime;

            // update GUI Values
            _electrical_consumption_f = (float)power_received;
            _heat_production_f        = (float)heat_production;

            // produce thrust
            double thrust_ratio = power_per_engine > 0 ? Math.Min(power_received / power_per_engine, 1.0) : 1;

            double max_thrust_in_space = CurrentPropellantEfficiency * CurrentPropellantThrustMultiplier * GetPowerThrustModifier() * power_received / (_modifiedCurrentPropellantIspMultiplier * _modifiedEngineBaseISP * ThrottleModifiedIsp() * _g0 * GetModifiedThrotte());

            _maxISP             = (float)(_modifiedEngineBaseISP * _modifiedCurrentPropellantIspMultiplier * CurrentPropellantThrustMultiplier) * ThrottleModifiedIsp();
            _max_fuel_flow_rate = _maxISP <= 0 ? 0 :  max_thrust_in_space / _maxISP / PluginHelper.GravityConstant;

            if (GetModifiedThrotte() > 0)
            {
                if (part.Resources.Contains("LqdWater"))
                {
                    var lqdWaterResourse  = part.Resources["LqdWater"];
                    var lqdWaterShortage  = lqdWaterResourse.maxAmount - lqdWaterResourse.amount;
                    var collectFlowGlobal = ORSHelper.fixedRequestResource(this.part, "Water", lqdWaterShortage);
                    lqdWaterResourse.amount += collectFlowGlobal;
                }

                double max_thrust_with_current_throttle = max_thrust_in_space * GetModifiedThrotte();
                double actual_max_thrust = Current_propellant.SupportedEngines == 8 ? max_thrust_with_current_throttle
                    : Math.Max(max_thrust_with_current_throttle - (exitArea * FlightGlobals.getStaticPressure(vessel.transform.position)), 0.0);

                if (actual_max_thrust > 0 && !double.IsNaN(actual_max_thrust) && max_thrust_with_current_throttle > 0 && !double.IsNaN(max_thrust_with_current_throttle))
                {
                    updateISP(actual_max_thrust / max_thrust_with_current_throttle);
                    _attached_engine.maxFuelFlow = (float)_max_fuel_flow_rate * (GetModifiedThrotte() / _attached_engine.currentThrottle);
                }
                else
                {
                    updateISP(0.000001);
                    _attached_engine.maxFuelFlow = 0;
                }

                if (_attached_engine is ModuleEnginesFX)
                {
                    part.Effect(Current_propellant.ParticleFXName, Mathf.Min((float)Math.Pow(_electrical_consumption_f / maxPower, 0.5), _attached_engine.finalThrust / _attached_engine.maxThrust));
                }
            }
            else
            {
                double actual_max_thrust = Math.Max(max_thrust_in_space - (exitArea * FlightGlobals.getStaticPressure(vessel.transform.position)), 0.0);

                if (!double.IsNaN(actual_max_thrust) && !double.IsInfinity(actual_max_thrust) && actual_max_thrust > 0 && max_thrust_in_space > 0)
                {
                    updateISP(actual_max_thrust / max_thrust_in_space);
                    _attached_engine.maxFuelFlow = (float)_max_fuel_flow_rate;
                }
                else
                {
                    updateISP(1);
                    _attached_engine.maxFuelFlow = 0;
                }

                //_attached_engine.maxThrust = _avrageragedLastActualMaxThrustWithTrottle > 1 ? _avrageragedLastActualMaxThrustWithTrottle : 1;
                if (_attached_engine is ModuleEnginesFX)
                {
                    part.Effect(Current_propellant.ParticleFXName, 0);
                }
            }

            if (isupgraded)
            {
                List <PartResource> vacuum_resources = part.GetConnectedResources(InterstellarResourcesConfiguration.Instance.VacuumPlasma).ToList();
                double vacuum_plasma_needed          = vacuum_resources.Sum(vc => vc.maxAmount - vc.amount);
                double vacuum_plasma_current         = vacuum_resources.Sum(vc => vc.amount);

                //if (vessel.IsInAtmosphere())
                //    part.RequestResource(InterstellarResourcesConfiguration.Instance.VacuumPlasma, vacuum_plasma_current);
                //else
                part.RequestResource(InterstellarResourcesConfiguration.Instance.VacuumPlasma, -vacuum_plasma_needed);
            }
        }
        public void FixedUpdate()
        {
            if (!HighLogic.LoadedSceneIsFlight)
            {
                return;
            }

            ElectricEngineControllerFX.getAllPropellants().ForEach(prop => part.Effect(prop.ParticleFXName, 0)); // set all FX to zero

            if (Current_propellant == null || _attached_engine == null)
            {
                return;
            }

            //updateISP();

            double power_received;
            double power_per_engine;

            // retrieve power for engine
            if (PluginHelper.MatchDemandWithSupply)
            {
                _electrical_share_f = maxPower / Math.Max(vessel.FindPartModulesImplementing <ElectricEngineControllerFX>().Where(ee => ee.IsOperational).Sum(ee => ee.maxPower), maxPower);
                double availablePower = getResourceSupply(FNResourceManager.FNRESOURCE_MEGAJOULES) - getCurrentHighPriorityResourceDemand(FNResourceManager.FNRESOURCE_MEGAJOULES);
                power_per_engine = Math.Min(availablePower * _electrical_share_f, maxPower * _propellantIspMultiplierPowerLimitModifier);
                power_received   = consumeFNResource(_attached_engine.currentThrottle * power_per_engine * TimeWarp.fixedDeltaTime, FNResourceManager.FNRESOURCE_MEGAJOULES) / TimeWarp.fixedDeltaTime;
            }
            else
            {
                int engine_count = Math.Max(vessel.FindPartModulesImplementing <ElectricEngineControllerFX>().Count(ee => ee.IsOperational), 1); // max of operational electric engines and 1
                _electrical_share_f = 1.0f / engine_count;
                double powerTrustModifier = GetPowerTrustModifier();
                double total_max_thrust   = evaluateMaxThrust();
                double thrust_per_engine  = total_max_thrust / (double)engine_count;
                power_per_engine = Math.Min(_attached_engine.currentThrottle * thrust_per_engine * _current_propellant.IspMultiplier * modifiedEngineBaseISP / powerTrustModifier * g0, maxPower * _current_propellant.Efficiency);
                power_received   = consumeFNResource(power_per_engine * TimeWarp.fixedDeltaTime / _current_propellant.Efficiency, FNResourceManager.FNRESOURCE_MEGAJOULES) / TimeWarp.fixedDeltaTime;
            }

            // produce waste heat
            double heat_to_produce = power_received * (1.0 - Current_propellant.Efficiency);
            double heat_production = supplyFNResource(heat_to_produce * TimeWarp.fixedDeltaTime, FNResourceManager.FNRESOURCE_WASTEHEAT) / TimeWarp.fixedDeltaTime;

            // update GUI Values
            _electrical_consumption_f = (float)power_received;
            _heat_production_f        = (float)heat_production;
            // thrust values

            // produce trust
            double thrust_ratio        = power_per_engine > 0 ? Math.Min(power_received / power_per_engine, 1.0) : 1;
            double max_thrust_in_space = Current_propellant.Efficiency * GetPowerTrustModifier() * power_received / (_modifiedCurrentPropellantIspMultiplier * modifiedEngineBaseISP * g0 * _attached_engine.currentThrottle);
            double actual_max_thrust   = Math.Max(max_thrust_in_space - (exitArea * GameConstants.EarthAthmospherePresureAtSeaLevel * part.vessel.atmDensity), 0.0);

            // update engine ISP
            updateISP(actual_max_thrust / Math.Max(max_thrust_in_space, 0.00001f));

            if (_attached_engine.currentThrottle > 0)
            {
                if (!double.IsNaN(actual_max_thrust) && !double.IsInfinity(actual_max_thrust))
                {
                    _attached_engine.maxThrust = Mathf.Max((float)actual_max_thrust, 0.00001f);
                }
                else
                {
                    _attached_engine.maxThrust = 0.00001f;
                }

                float fx_ratio = Mathf.Min(_electrical_consumption_f / maxPower, _attached_engine.finalThrust / _attached_engine.maxThrust);
                part.Effect(Current_propellant.ParticleFXName, fx_ratio);
            }

            if (isupgraded)
            {
                List <PartResource> vacuum_resources = part.GetConnectedResources(InterstellarResourcesConfiguration.Instance.VacuumPlasma).ToList();
                double vacuum_plasma_needed          = vacuum_resources.Sum(vc => vc.maxAmount - vc.amount);
                double vacuum_plasma_current         = vacuum_resources.Sum(vc => vc.amount);

                if (vessel.IsInAtmosphere())
                {
                    part.RequestResource(InterstellarResourcesConfiguration.Instance.VacuumPlasma, vacuum_plasma_current);
                }
                else
                {
                    part.RequestResource(InterstellarResourcesConfiguration.Instance.VacuumPlasma, -vacuum_plasma_needed);
                }
            }
        }