Esempio n. 1
0
        /// <summary>
        /// Refuel the aircraft unit in air.
        /// </summary>
        /// <param name="refuelingAircraft">The aircraft unit to refuel from.</param>
        /// <returns></returns>
        public bool RefuelInAir(AircraftUnit refuelingAircraft)
        {
            // Check if refueling aircraft is within distance
            var distanceToTargetM = MapHelper.CalculateDistanceM(Position.Coordinate, refuelingAircraft.Position.Coordinate);

            if (distanceToTargetM < GameConstants.DISTANCE_TO_TARGET_IS_HIT_M)
            {
                // Make sure we're in the queue
                if (!refuelingAircraft.IsInFuelQueue(this) && !refuelingAircraft.AddToFuelQueue(this, FuelDistanceCoveredSinceRefuelM))
                {
                    return(false);
                }
                return(refuelingAircraft.GiveFuel(this));
            }

            // Take bingo fuel factor into account
            distanceToTargetM *= GameConstants.BINGO_FUEL_FACTOR;
            if (distanceToTargetM < FuelDistanceRemainingM)
            {
                // Check if refueling aircraft has enough fuel to give us. Make sure to remove from queue before adding
                refuelingAircraft.RemoveFromFuelQueue(this);
                if (refuelingAircraft.AddToFuelQueue(this, FuelDistanceCoveredSinceRefuelM + distanceToTargetM))
                {
                    MissionType             = GameConstants.MissionType.Ferry;
                    MissionTargetType       = GameConstants.MissionTargetType.Undefined;
                    TargetDetectedUnit      = null;
                    IsOrderedToReturnToBase = true;
                    ActualSpeedKph          = GetSpeedInKphFromSpeedType(GameConstants.UnitSpeedType.Cruise);
                    SetActualSpeed(ActualSpeedKph); //force afterburners off immediately
                    UserDefinedSpeed = GameConstants.UnitSpeedType.Cruise;
                    SetDirty(GameConstants.DirtyStatus.UnitChanged);

                    // Change speed on refueling aircraft as well
                    refuelingAircraft.ActualSpeedKph = refuelingAircraft.GetSpeedInKphFromSpeedType(GameConstants.UnitSpeedType.Slow);
                    refuelingAircraft.SetActualSpeed(refuelingAircraft.ActualSpeedKph);
                    refuelingAircraft.UserDefinedSpeed = GameConstants.UnitSpeedType.Slow;
                    refuelingAircraft.SetDirty(GameConstants.DirtyStatus.UnitChanged);

                    // Create waypoint to the refueling aircraft and add refuel order
                    if (MovementOrder is MovementFormationOrder)
                    {
                        MovementOrder = new MovementOrder();
                    }
                    var wp = new Waypoint(refuelingAircraft);
                    wp.DesiredDistanceToTargetM = GameConstants.DISTANCE_TO_TARGET_IS_HIT_M; // TODO: set proper distance
                    wp.IsNotRecurring           = true;
                    wp.Orders.Add(new BaseOrder()
                    {
                        OrderType = GameConstants.OrderType.RefuelInAir, SecondId = refuelingAircraft.Id
                    });

                    MovementOrder.AddWaypointToTop(wp);
                    ReCalculateEta();
                    return(true);
                }
            }
            return(false);
        }
Esempio n. 2
0
        /// <summary>
        /// Transfer fuel to another aircraft unit.
        /// </summary>
        /// <param name="unit">The aircraft unit to transfer fuel to.</param>
        /// <param name="fuelDistanceM">The amount of fuel to transfer.</param>
        /// <returns>True if any fuel was transferred.</returns>
        private bool GiveFuel(AircraftUnit unit)
        {
            // Make sure unit is in queue
            if (!IsInFuelQueue(unit))
            {
                return(false);
            }

            // Get amount to give
            var fuelDistanceM = _aircraftsToRefuel.Where(pair => pair.Key != null && pair.Key.Id == unit.Id).Sum(pair => pair.Value);

            // Make sure we don't give too much fuel
            fuelDistanceM = fuelDistanceM.Clamp(0.0, GetMaxFuelDistanceToGiveM());
            if (fuelDistanceM > unit.FuelDistanceCoveredSinceRefuelM)
            {
                fuelDistanceM = unit.FuelDistanceCoveredSinceRefuelM;
            }

            // Give fuel to unit
            unit.IsOrderedToReturnToBase          = false;
            unit.FuelDistanceCoveredSinceRefuelM -= fuelDistanceM;

            // Remove fuel from ourself
            FuelDistanceCoveredSinceRefuelM += fuelDistanceM;

            // Remove unit from fueling list
            RemoveFromFuelQueue(unit);

            // Also remove units that's marked for deletion
            _aircraftsToRefuel.RemoveAll(
                pair => pair.Key == null || pair.Key.IsMarkedForDeletion);

            // Go back to cruise speed if no more units to refuel
            // TODO: go back to the user defined speed instead
            if (!_aircraftsToRefuel.Any())
            {
                ActualSpeedKph = GetSpeedInKphFromSpeedType(GameConstants.UnitSpeedType.Cruise);
                SetActualSpeed(ActualSpeedKph);
                UserDefinedSpeed = GameConstants.UnitSpeedType.Cruise;
            }

            SetDirty(GameConstants.DirtyStatus.UnitChanged);
            unit.SetDirty(GameConstants.DirtyStatus.UnitChanged);

            // The unit should check for bingo fuel after refueling as it might be too far away from base.
            //CheckForBingoFuel(); //removed to avoid stack exhausted
            //unit.CheckForBingoFuel();

            return(fuelDistanceM > 0.0);
        }