Example #1
0
    def _affordable_aircraft_for_task(
        self,
        task: FlightType,
        airbase: ControlPoint,
        number: int,
        max_price: float,
    ) -> Optional[AircraftType]:
        best_choice: Optional[AircraftType] = None
        for unit in aircraft_for_task(task):
            if unit not in self.faction.aircrafts:
                continue
            if unit.price * number > max_price:
                continue
            if not airbase.can_operate(unit):
                continue

            for squadron in self.air_wing.squadrons_for(unit):
                if task in squadron.auto_assignable_mission_types:
                    break
            else:
                continue

            # Affordable, compatible, and we have a squadron capable of the task. To
            # keep some variety, skip with a 50/50 chance. Might be a good idea to have
            # the chance to skip based on the price compared to the rest of the choices.
            best_choice = unit
            if random.choice([True, False]):
                break
        return best_choice
Example #2
0
 def operates_from(self, control_point: ControlPoint) -> bool:
     if not control_point.can_operate(self.aircraft):
         return False
     if control_point.is_carrier:
         return self.operating_bases.carrier
     elif control_point.is_lha:
         return self.operating_bases.lha
     else:
         return self.operating_bases.shore
Example #3
0
 def _affordable_aircraft_of_types(
         self, types: List[Type[FlyingType]], airbase: ControlPoint,
         number: int, max_price: int) -> Optional[Type[FlyingType]]:
     unit_pool = [u for u in self.faction.aircrafts if u in types]
     affordable_units = [
         u for u in unit_pool
         if db.PRICES[u] * number <= max_price and airbase.can_operate(u)
     ]
     if not affordable_units:
         return None
     return random.choice(affordable_units)
Example #4
0
    def _affordable_aircraft_of_types(
            self, types: List[Type[FlyingType]], airbase: ControlPoint,
            number: int, max_price: float) -> Optional[Type[FlyingType]]:
        best_choice: Optional[Type[FlyingType]] = None
        for unit in [u for u in self.faction.aircrafts if u in types]:
            if db.PRICES[unit] * number > max_price:
                continue
            if not airbase.can_operate(unit):
                continue

            # Affordable and compatible. To keep some variety, skip with a 50/50
            # chance. Might be a good idea to have the chance to skip based on
            # the price compared to the rest of the choices.
            best_choice = unit
            if random.choice([True, False]):
                break
        return best_choice
    def generate_for_task(
            self, task: FlightType,
            control_point: ControlPoint) -> Optional[SquadronDef]:
        aircraft_choice: Optional[AircraftType] = None
        for aircraft in aircraft_for_task(task):
            if aircraft not in self.faction.aircrafts:
                continue
            if not control_point.can_operate(aircraft):
                continue
            aircraft_choice = aircraft
            # 50/50 chance to keep looking for an aircraft that isn't as far up the
            # priority list to maintain some unit variety.
            if random.choice([True, False]):
                break

        if aircraft_choice is None:
            return None
        return self.generate_for_aircraft(aircraft_choice)
Example #6
0
    def plan_relocation(self, destination: ControlPoint,
                        theater: ConflictTheater) -> None:
        if destination == self.location:
            logging.warning(
                f"Attempted to plan relocation of {self} to current location "
                f"{destination}. Ignoring.")
            return
        if destination == self.destination:
            logging.warning(
                f"Attempted to plan relocation of {self} to current destination "
                f"{destination}. Ignoring.")
            return

        if self.expected_size_next_turn > destination.unclaimed_parking():
            raise RuntimeError(
                f"Not enough parking for {self} at {destination}.")
        if not destination.can_operate(self.aircraft):
            raise RuntimeError(f"{self} cannot operate at {destination}.")
        self.destination = destination
        self.replan_ferry_flights(theater)