mirror of
https://github.com/dcs-liberation/dcs_liberation.git
synced 2025-11-10 14:22:26 +00:00
Assign laser codes to players with TGPs.
This doesn't configure the bombs in the mission or anything yet; it only pre-assigns a laser code for the player to use if they choose to.
This commit is contained in:
parent
fc45c3b98c
commit
73ba7933da
@ -294,8 +294,10 @@ class Operation:
|
||||
cls._generate_ground_units()
|
||||
cls._generate_transports()
|
||||
cls._generate_destroyed_units()
|
||||
cls._generate_air_units()
|
||||
# Generate ground conflicts first so the JTACs get the first laser code (1688)
|
||||
# rather than the first player flight with a TGP.
|
||||
cls._generate_ground_conflicts()
|
||||
cls._generate_air_units()
|
||||
cls.assign_channels_to_flights(
|
||||
cls.airgen.flights, cls.airsupportgen.air_support
|
||||
)
|
||||
@ -357,6 +359,7 @@ class Operation:
|
||||
cls.game,
|
||||
cls.radio_registry,
|
||||
cls.tacan_registry,
|
||||
cls.laser_code_registry,
|
||||
cls.unit_map,
|
||||
air_support=cls.airsupportgen.air_support,
|
||||
)
|
||||
|
||||
@ -3,7 +3,7 @@ from __future__ import annotations
|
||||
import itertools
|
||||
import logging
|
||||
import random
|
||||
from dataclasses import dataclass
|
||||
from dataclasses import dataclass, field
|
||||
from datetime import timedelta
|
||||
from functools import cached_property
|
||||
from typing import Dict, List, Optional, TYPE_CHECKING, Type, Union, Iterable, Any
|
||||
@ -65,7 +65,7 @@ from dcs.unitgroup import FlyingGroup, ShipGroup, StaticGroup
|
||||
from dcs.unittype import FlyingType
|
||||
|
||||
from game import db
|
||||
from game.data.weapons import Pylon
|
||||
from game.data.weapons import Pylon, WeaponType as WeaponTypeEnum
|
||||
from game.dcs.aircrafttype import AircraftType
|
||||
from game.factions.faction import Faction
|
||||
from game.settings import Settings
|
||||
@ -90,6 +90,7 @@ from gen.flights.flight import (
|
||||
FlightWaypoint,
|
||||
FlightWaypointType,
|
||||
)
|
||||
from gen.lasercoderegistry import LaserCodeRegistry
|
||||
from gen.radios import RadioFrequency, RadioRegistry
|
||||
from gen.runways import RunwayData
|
||||
from gen.tacan import TacanBand, TacanRegistry
|
||||
@ -138,6 +139,8 @@ class FlightData:
|
||||
|
||||
flight_type: FlightType
|
||||
|
||||
aircraft_type: AircraftType
|
||||
|
||||
#: All units in the flight.
|
||||
units: List[FlyingUnit]
|
||||
|
||||
@ -165,49 +168,24 @@ class FlightData:
|
||||
#: Radio frequency for intra-flight communications.
|
||||
intra_flight_channel: RadioFrequency
|
||||
|
||||
#: Map of radio frequencies to their assigned radio and channel, if any.
|
||||
frequency_to_channel_map: Dict[RadioFrequency, ChannelAssignment]
|
||||
|
||||
#: Bingo fuel value in lbs.
|
||||
bingo_fuel: Optional[int]
|
||||
|
||||
joker_fuel: Optional[int]
|
||||
|
||||
def __init__(
|
||||
self,
|
||||
package: Package,
|
||||
aircraft_type: AircraftType,
|
||||
flight_type: FlightType,
|
||||
units: List[FlyingUnit],
|
||||
size: int,
|
||||
friendly: bool,
|
||||
departure_delay: timedelta,
|
||||
departure: RunwayData,
|
||||
arrival: RunwayData,
|
||||
divert: Optional[RunwayData],
|
||||
waypoints: List[FlightWaypoint],
|
||||
intra_flight_channel: RadioFrequency,
|
||||
bingo_fuel: Optional[int],
|
||||
joker_fuel: Optional[int],
|
||||
custom_name: Optional[str],
|
||||
) -> None:
|
||||
self.package = package
|
||||
self.aircraft_type = aircraft_type
|
||||
self.flight_type = flight_type
|
||||
self.units = units
|
||||
self.size = size
|
||||
self.friendly = friendly
|
||||
self.departure_delay = departure_delay
|
||||
self.departure = departure
|
||||
self.arrival = arrival
|
||||
self.divert = divert
|
||||
self.waypoints = waypoints
|
||||
self.intra_flight_channel = intra_flight_channel
|
||||
self.frequency_to_channel_map = {}
|
||||
self.bingo_fuel = bingo_fuel
|
||||
self.joker_fuel = joker_fuel
|
||||
laser_codes: list[Optional[int]]
|
||||
|
||||
custom_name: Optional[str]
|
||||
|
||||
callsign: str = field(init=False)
|
||||
|
||||
#: Map of radio frequencies to their assigned radio and channel, if any.
|
||||
frequency_to_channel_map: Dict[RadioFrequency, ChannelAssignment] = field(
|
||||
init=False, default_factory=dict
|
||||
)
|
||||
|
||||
def __post_init__(self) -> None:
|
||||
self.callsign = create_group_callsign_from_unit(self.units[0])
|
||||
self.custom_name = custom_name
|
||||
|
||||
@property
|
||||
def client_units(self) -> List[FlyingUnit]:
|
||||
@ -247,6 +225,7 @@ class AircraftConflictGenerator:
|
||||
game: Game,
|
||||
radio_registry: RadioRegistry,
|
||||
tacan_registry: TacanRegistry,
|
||||
laser_code_registry: LaserCodeRegistry,
|
||||
unit_map: UnitMap,
|
||||
air_support: AirSupport,
|
||||
) -> None:
|
||||
@ -255,6 +234,7 @@ class AircraftConflictGenerator:
|
||||
self.settings = settings
|
||||
self.radio_registry = radio_registry
|
||||
self.tacan_registy = tacan_registry
|
||||
self.laser_code_registry = laser_code_registry
|
||||
self.unit_map = unit_map
|
||||
self.flights: List[FlightData] = []
|
||||
self.air_support = air_support
|
||||
@ -361,6 +341,7 @@ class AircraftConflictGenerator:
|
||||
self._setup_payload(flight, group)
|
||||
self._setup_livery(flight, group)
|
||||
|
||||
laser_codes = []
|
||||
for unit, pilot in zip(group.units, flight.roster.pilots):
|
||||
player = pilot is not None and pilot.player
|
||||
self.set_skill(unit, pilot, blue=flight.departure.captured)
|
||||
@ -368,6 +349,11 @@ class AircraftConflictGenerator:
|
||||
if player and group.late_activation:
|
||||
group.late_activation = False
|
||||
|
||||
code: Optional[int] = None
|
||||
if flight.loadout.has_weapon_of_type(WeaponTypeEnum.TGP) and player:
|
||||
code = self.laser_code_registry.get_next_laser_code()
|
||||
laser_codes.append(code)
|
||||
|
||||
# Set up F-14 Client to have pre-stored alignment
|
||||
if unit_type is F_14B:
|
||||
unit.set_property(F_14B.Properties.INSAlignmentStored.id, True)
|
||||
@ -423,6 +409,7 @@ class AircraftConflictGenerator:
|
||||
bingo_fuel=flight.flight_plan.bingo_fuel,
|
||||
joker_fuel=flight.flight_plan.joker_fuel,
|
||||
custom_name=flight.custom_name,
|
||||
laser_codes=laser_codes,
|
||||
)
|
||||
)
|
||||
|
||||
|
||||
@ -31,6 +31,12 @@ class Loadout:
|
||||
def derive_custom(self, name: str) -> Loadout:
|
||||
return Loadout(name, self.pylons, self.date, is_custom=True)
|
||||
|
||||
def has_weapon_of_type(self, weapon_type: WeaponType) -> bool:
|
||||
for weapon in self.pylons.values():
|
||||
if weapon is not None and weapon.weapon_group.type is weapon_type:
|
||||
return True
|
||||
return False
|
||||
|
||||
@staticmethod
|
||||
def _fallback_for(
|
||||
weapon: Weapon,
|
||||
@ -79,9 +85,7 @@ class Loadout:
|
||||
def replace_lgbs_if_no_tgp(
|
||||
self, unit_type: AircraftType, date: datetime.date
|
||||
) -> None:
|
||||
for weapon in self.pylons.values():
|
||||
if weapon is not None and weapon.weapon_group.type is WeaponType.TGP:
|
||||
# Have a TGP. Nothing to do.
|
||||
if self.has_weapon_of_type(WeaponType.TGP):
|
||||
return
|
||||
|
||||
new_pylons = dict(self.pylons)
|
||||
|
||||
@ -354,6 +354,12 @@ class BriefingPage(KneeboardPage):
|
||||
["Bingo", "Joker"],
|
||||
)
|
||||
|
||||
if any(self.flight.laser_codes):
|
||||
codes: list[list[str]] = []
|
||||
for idx, code in enumerate(self.flight.laser_codes, start=1):
|
||||
codes.append([str(idx), "" if code is None else str(code)])
|
||||
writer.table(codes, ["#", "Laser Code"])
|
||||
|
||||
writer.write(path)
|
||||
|
||||
def airfield_info_row(
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user