diff --git a/changelog.md b/changelog.md index 24a2ec38..77bf4bd8 100644 --- a/changelog.md +++ b/changelog.md @@ -20,6 +20,7 @@ Saves from 4.0.0 are compatible with 4.1.0. * **[Flight Planning]** CAP patrol speeds are now set per-aircraft to be more suitable/sensible. By default the speed will be set based on the aircraft's maximum speed. * **[Mission Generation]** Improvements for better support of the Skynet Plugin and long range SAMs are now acting as EWR * **[Mods]** Support for version v1.5.0-Beta of Gripen mod. In-progress campaigns may need to re-plan Gripen flights to pick up updated loadouts. +* **[Mission Generation]** SAM sites are now headed towards the center of the conflict * **[Plugins]** Increased time JTAC Autolase messages stay visible on the UI. * **[Plugins]** Updated SkynetIADS to 2.2.0 (adds NASAMS support). * **[UI]** Added ability to take notes and have those notes appear as a kneeboard page. diff --git a/gen/sam/airdefensegroupgenerator.py b/gen/sam/airdefensegroupgenerator.py index 36755036..f755cafa 100644 --- a/gen/sam/airdefensegroupgenerator.py +++ b/gen/sam/airdefensegroupgenerator.py @@ -48,6 +48,7 @@ class AirDefenseGroupGenerator(VehicleGroupGenerator[SamGroundObject], ABC): self.vg.name = self.group_name_for_role(self.vg.id, self.primary_group_role()) self.auxiliary_groups: List[VehicleGroup] = [] + self.heading = self.heading_to_conflict() def add_auxiliary_group(self, role: SkynetRole) -> VehicleGroup: gid = self.game.next_group_id() diff --git a/gen/sam/group_generator.py b/gen/sam/group_generator.py index 2fb800f8..03223e00 100644 --- a/gen/sam/group_generator.py +++ b/gen/sam/group_generator.py @@ -2,6 +2,7 @@ from __future__ import annotations import logging import math +import operator import random from collections import Iterable from typing import TYPE_CHECKING, Type, TypeVar, Generic, Any @@ -15,6 +16,7 @@ from dcs.unittype import VehicleType, UnitType, ShipType from game.dcs.groundunittype import GroundUnitType from game.factions.faction import Faction +from game.theater import MissionTarget from game.theater.theatergroundobject import TheaterGroundObject, NavalGroundObject if TYPE_CHECKING: @@ -69,6 +71,27 @@ class GroupGenerator(Generic[GroupT, UnitT, UnitTypeT, TgoT]): ) -> UnitT: raise NotImplementedError + def heading_to_conflict(self) -> int: + # Heading for a Group to the enemy. + # Should be the point between the nearest and the most distant conflict + conflicts: dict[MissionTarget, float] = {} + + for conflict in self.game.theater.conflicts(): + conflicts[conflict] = conflict.distance_to(self.go) + + if len(conflicts) == 0: + return self.heading + + closest_conflict = min(conflicts.items(), key=operator.itemgetter(1))[0] + most_distant_conflict = max(conflicts.items(), key=operator.itemgetter(1))[0] + + conflict_center = Point( + (closest_conflict.position.x + most_distant_conflict.position.x) / 2, + (closest_conflict.position.y + most_distant_conflict.position.y) / 2, + ) + + return int(self.go.position.heading_between_point(conflict_center)) + class VehicleGroupGenerator( Generic[TgoT], GroupGenerator[VehicleGroup, Vehicle, Type[VehicleType], TgoT]