コード例 #1
0
        public void Disable()
        {
            balanceStatus                = BalanceStatus.Deactivated;
            _tanks                       = null;
            Status                       = "Deactivated";
            Events["Disable"].active     = false;
            Events["BalanceFuel"].active = true;
            Events["Maintain"].active    = true;

            // Clear the list of tanks. They will have to be rebuilt next time balancing is enabled
        }
コード例 #2
0
        public void Maintain()
        {
            // If we were previously Deactivated then we need to build a list of tanks and set up to start balancing
            if (balanceStatus == BalanceStatus.Deactivated || balanceStatus == BalanceStatus.Balance_not_possible)
            {
                BuildTanksList();

                _iNextSourceTank      = 0;
                _iNextDestinationTank = 0;
                ResetfNextAmountMoved();
                _fMostMovedThisRound = 0;
                DeactivateOtherPWBModules();
            }

            Events["Disable"].active     = true;
            Events["BalanceFuel"].active = false;
            Events["Maintain"].active    = false;
            balanceStatus = BalanceStatus.Maintaining;
            Status        = "Maintaining";
        }
コード例 #3
0
        public BalanceStatus Balance(string cardNumber)
        {
            var card = cardRepository.GetByNumber(cardNumber);

            if (card == null)
            {
                return(null);
            }

            TrackOperation(card, OperationTypes.BalanceCheck);
            Save();

            var balance = new BalanceStatus
            {
                Date       = DateTime.Now,
                Amount     = card.Account.Balance,
                CardNumber = cardNumber
            };

            return(balance);
        }
コード例 #4
0
        // Transfer fuel to move the center of mass from current position towards target.
        // Returns the new distance the CoM was moved towards its target
        public float MoveFuel()
        {
            float   fCoMStartingError = CalculateCoMFromTargetCoM(vessel.CoM);
            float   mass           = vessel.GetTotalMass(); // Get total mass.
            Vector3 oldWorldCoM    = vessel.CoM;
            float   fOldCoMError   = fCoMStartingError;
            bool    moveMade       = false;
            int     iNumberofTanks = _tanks.Count;

            Log.Info("MoveFuel, mass: " + mass.ToString("F1") + ", iNumberOfTanks: " + iNumberofTanks);

            //Log.Info("Number of tanks " + iNumberofTanks);

            // Now go through the list of parts and resources and consider making transfers
            while (_iNextSourceTank < iNumberofTanks && false == moveMade)
            {
                //Log.Info("Considering moving fuel from tank" + this.iNextSourceTank);
                PartResource resource1 = ((PartAndResource)_tanks[_iNextSourceTank]).Resource;
                Part         part1     = ((PartAndResource)_tanks[_iNextSourceTank]).Part;

                // Only process nonempty tanks, and tanks that are not locked.
                if (resource1.amount > 0 && resource1.flowState &&
                    resource1.resourceName != "Ore" &&
                    resource1.resourceName != "Ablator" &&
                    resource1.resourceName != "SolidFuel")
                {
                    // Only move resources that have mass (don't move electricity!)
                    if (resource1.info.density > 0)
                    {
                        // If the two tanks are the same move on.
                        if (_iNextDestinationTank == _iNextSourceTank)
                        {
                            _iNextDestinationTank++;
                        }

                        while (_iNextDestinationTank < iNumberofTanks && false == moveMade)
                        {
                            Log.Info("Considering moving fuel from tank: " + _iNextSourceTank + " to tank: " + this._iNextDestinationTank);

                            PartResource resource2 = ((PartAndResource)_tanks[_iNextDestinationTank]).Resource;
                            Part         part2     = ((PartAndResource)_tanks[_iNextDestinationTank]).Part;

                            // Check that the resources are of the same type  and the tank is not locked
                            if (resource2.resourceName == resource1.resourceName && resource2.flowState)
                            {
                                // Clamp resource quantity by the amount available in the two tanks.
                                //Log.Info("MoveFuel: _iNextSourceTank: " + _iNextSourceTank + ", _fNextAmountMoved: " + ((PartAndResource)_tanks[_iNextDestinationTank])._fNextAmountMoved + ", resource1.amount: " + resource1.amount);

                                float moveAmount = (float)Math.Min(((PartAndResource)_tanks[_iNextDestinationTank]).fNextAmountMoved, resource1.amount);
                                moveAmount = (float)Math.Max(moveAmount, -(resource1.maxAmount - resource1.amount));
                                moveAmount = (float)Math.Max(moveAmount, -resource2.amount);
                                moveAmount = (float)Math.Min(moveAmount, resource2.maxAmount - resource2.amount);

                                Log.Info("Considering moving " + moveAmount.ToString("F2"));
                                if (moveAmount > 0)
                                {
                                    // Calculate the new CoM to see if it helped:
                                    float fVesselMass = vessel.GetTotalMass();

                                    //Log.Info("part1.transform.position : " + part1.transform.position.ToString());
                                    //Log.Info("part2.transform.position : " + part2.transform.position.ToString());

                                    Vector3 newCenterOfMass = ((oldWorldCoM * fVesselMass) - (part1.transform.position * (moveAmount * resource1.info.density)) + (part2.transform.position * (moveAmount * resource2.info.density))) * (1 / fVesselMass);

                                    // Recompute the distance between CoM and the TargetCoM
                                    float fNewError = CalculateCoMFromTargetCoM(newCenterOfMass);

                                    //Log.Info("Old world CoM: " + OldWorldCoM.ToString());
                                    //Log.Info("New suggested CoM: " + NewCenterOfMass.ToString());
                                    //Log.Info("new error is: " + fNewError.ToString() + " compared to " + fOldCoMError.ToString());
                                    if (fNewError < fOldCoMError)
                                    {
                                        //Log.Info("CoM moved in correct direction");
                                        // This is moving us in the right direction
                                        fOldCoMError = fNewError;

                                        // Actually move the fuel
                                        resource1.amount -= moveAmount;
                                        resource2.amount += moveAmount;

                                        // set the new CoM for the next iteration
                                        oldWorldCoM = newCenterOfMass;
                                        moveMade    = true;
                                        if (moveAmount > _fMostMovedThisRound)
                                        {
                                            _fMostMovedThisRound = moveAmount;
                                        }
                                        // Finally, move on to another source tank, so that the flow out of each source tank appears a bit smoother.
                                        _iNextSourceTank++;
                                    }
                                }
                            }

                            // Move on the the next destination tank
                            _iNextDestinationTank++;
                            if (_iNextDestinationTank == _iNextSourceTank)
                            {
                                _iNextDestinationTank++;
                            }
                        }

                        // If we have reached the end of the list of destination tanks then we need to reset tank list for next time
                        if (_iNextDestinationTank < iNumberofTanks)
                        {
                            continue;
                        }
                        _iNextDestinationTank = 0;
                        _iNextSourceTank++;
                    }
                    else
                    {
                        //Log.Info("Tank" + this.iNextSourceTank + " contains a zero density resource, moving on to the next source tank");
                        _iNextSourceTank++;
                    }
                }
                else
                {
                    //Log.Info("Tank" + this.iNextSourceTank + " was empty, moving on to the next source tank");
                    _iNextSourceTank++;
                }
            }

            // If we have reached the end of the source tanks then we need to reset the list for next time
            if (_iNextSourceTank >= iNumberofTanks)
            {
                _iNextSourceTank = 0;
                // Since we are now starting a new round, the next thing to consider is whether we moved anything this round. If not then we need to consider moving smaller amounts
                if (_fMostMovedThisRound == 0)
                {
                    ((PartAndResource)_tanks[_iNextDestinationTank]).fNextAmountMoved /= 2f;


                    //Log.Info("changing the amount to move to be " + fNextAmountMoved);

                    // Finally has the amount move become so small that we need to call it a day?
                    if (((PartAndResource)_tanks[_iNextDestinationTank]).fNextAmountMoved < 0.0005)
                    {
                        // Since perfect balance is not possible, we need to move into an appropriate state.If we are trying to maintain blanace then we will keep trying trying again with larger amounts. If we were trying for a single balance then move to a state that shows it is not possible.
                        if (balanceStatus == BalanceStatus.Maintaining)
                        {
                            ResetfNextAmountMoved();
                            Events["Disable"].active = true;
                        }
                        else
                        {
                            balanceStatus                = BalanceStatus.Balance_not_possible;
                            Status                       = "Balance not possible";
                            Events["Disable"].active     = true;
                            Events["BalanceFuel"].active = true;
                            Events["Maintain"].active    = true;
                            // throw away the tanks list
                            _tanks = null;
                        }
                    }
                }
                _fMostMovedThisRound = 0;
            }

            // Update the member variable that remembers what the error is to display it
            FComError = fOldCoMError;

            // Return the amount that the CoM has been corrected
            return(fCoMStartingError - fOldCoMError);
        }
コード例 #5
0
        /// <summary>
        /// Per-physx-frame update
        /// </summary>
        private void FixedUpdate()
        {
            Log.Info("FixedUpdate, ActualCoMMarker: " + (ActualCoMMarker != null) + ", ActualCoMMarkerVisible: " + ActualCoMMarkerVisible);

            if (ActualCoMMarker != null)
            {
                ActualCoMMarker.SetActive(!MapView.MapIsEnabled && ActualCoMMarkerVisible && !HideUI);
            }
            if (ActualCoLMarker != null)
            {
                ActualCoLMarker.SetActive(!MapView.MapIsEnabled && ActualCoLMarkerVisible && vessel.srf_velocity.magnitude > 0.1f && !HideUI);
            }
            if (!_started || !HighLogic.LoadedSceneIsFlight || balanceStatus < BalanceStatus.Maintaining)
            {
                return;
            }

            if (SavedCoMMarker != null)
            {
                SavedCoMMarker.SetActive(!MapView.MapIsEnabled && SavedCoMMarkerVisible && !HideUI);
            }

            // Update the ComError (hopefully this will not kill our performance)
            FComError = CalculateCoMFromTargetCoM(part.vessel.CoM);

            if (balanceStatus == BalanceStatus.Deactivated || balanceStatus == BalanceStatus.Balance_not_possible)
            {
                return;
            }
            if (FComError < 0.002)
            {
                // The error is so small we need not worry anymore
                if (balanceStatus == BalanceStatus.Balancing)
                {
                    DeactivateModule(this);

                    // Clear the list of tanks. They will have to be rebuilt next time balancing is enabled
                    _tanks = null;
                }
                else if (balanceStatus == BalanceStatus.Maintaining)
                {
                    // Move from a maintaining state to a standby one. If the error increases we con mvoe back to a maintining state
                    balanceStatus = BalanceStatus.Standby;
                    Status        = "Standby";

                    _iNextSourceTank      = 0;
                    _iNextDestinationTank = 0;
                    ResetfNextAmountMoved();

                    _fMostMovedThisRound = 0;
                }
            }
            else
            {
                // There is an error
                if (balanceStatus == BalanceStatus.Standby)
                {
                    // is the error large enough to get us back into a maintaining mode?
                    if (FComError > 0.002 * 2)
                    {
                        balanceStatus = BalanceStatus.Maintaining;
                        Status        = "Maintaining";
                    }
                }
                MoveFuel();
            }
        }