Include layouts & groups from Saved Games folder

Partial #244
This commit is contained in:
Raffson 2024-10-06 22:29:29 +02:00
parent 69c6f8f2f2
commit 4aacc68f4a
No known key found for this signature in database
GPG Key ID: B0402B2C9B764D99
3 changed files with 54 additions and 11 deletions

View File

@ -9,6 +9,7 @@ from typing import Any, ClassVar, Iterator, Optional, TYPE_CHECKING, Type
import yaml
from dcs.unittype import ShipType, StaticType, UnitType as DcsUnitType, VehicleType
from game import persistency
from game.data.groups import GroupTask
from game.dcs.groundunittype import GroundUnitType
from game.dcs.helpers import static_type_from_name
@ -317,7 +318,18 @@ class ForceGroup:
@classmethod
def _load_all(cls) -> None:
for file in Path("resources/groups").glob("*.yaml"):
locations = [
Path("resources/groups"),
persistency.groups_dir(),
]
for path in locations:
cls._process_path(path)
cls._loaded = True
@classmethod
def _process_path(cls, path: Path) -> None:
for file in path.glob("*.yaml"):
if not file.is_file():
raise RuntimeError(f"{file.name} is not a valid ForceGroup")
@ -365,5 +377,3 @@ class ForceGroup:
)
cls._by_name[force_group.name] = force_group
cls._loaded = True

View File

@ -5,6 +5,7 @@ import logging
import pickle
from collections import defaultdict
from concurrent.futures import ThreadPoolExecutor
from copy import deepcopy
from pathlib import Path
from typing import Iterator
@ -41,6 +42,8 @@ LAYOUT_TYPES = {
GroupRole.DEFENSES: DefensesLayout,
}
LOCATIONS_TO_CHECK: list[Path] = []
class LayoutLoader:
# Map of all available layouts indexed by name
@ -51,9 +54,19 @@ class LayoutLoader:
def initialize(self) -> None:
if not self._layouts:
self.initialize_locations_to_check()
with logged_duration("Loading layouts"):
self.load_templates()
@staticmethod
def initialize_locations_to_check() -> None:
global LOCATIONS_TO_CHECK
if not LOCATIONS_TO_CHECK:
LOCATIONS_TO_CHECK = [
Path(LAYOUT_DIR),
persistency.layouts_dir(),
]
@property
def layouts(self) -> Iterator[TgoLayout]:
self.initialize()
@ -83,14 +96,9 @@ class LayoutLoader:
self._layouts = {}
mappings: dict[str, list[LayoutMapping]] = defaultdict(list)
with logged_duration("Parsing mapping yamls"):
for file in Path(LAYOUT_DIR).rglob("*.yaml"):
if not file.is_file():
raise RuntimeError(f"{file.name} is not a file")
with file.open("r", encoding="utf-8") as f:
mapping_dict = yaml.safe_load(f)
template_map = LayoutMapping.from_dict(mapping_dict, f.name)
mappings[template_map.layout_file].append(template_map)
for path_to_check in LOCATIONS_TO_CHECK:
for file in path_to_check.rglob("*.yaml"):
self._process_yaml(file, mappings)
with logged_duration(f"Parsing all layout miz multithreaded"):
with ThreadPoolExecutor() as exe:
@ -105,6 +113,15 @@ class LayoutLoader:
logging.info(f"Imported {len(self._layouts)} layouts")
self._dump_templates()
@staticmethod
def _process_yaml(file: Path, mappings: dict[str, list[LayoutMapping]]) -> None:
if not file.is_file():
raise RuntimeError(f"{file.name} is not a file")
with file.open("r", encoding="utf-8") as f:
mapping_dict = yaml.safe_load(f)
template_map = LayoutMapping.from_dict(mapping_dict, f.name)
mappings[template_map.layout_file].append(template_map)
def _dump_templates(self) -> None:
file = persistency.base_path() / LAYOUT_DUMP
dump = (VERSION, self._layouts)
@ -112,6 +129,14 @@ class LayoutLoader:
pickle.dump(dump, fdata)
def _load_from_miz(self, miz: str, mappings: list[LayoutMapping]) -> None:
path = Path(miz)
locations_to_check = deepcopy(LOCATIONS_TO_CHECK)
while not path.exists() and locations_to_check:
path = locations_to_check.pop() / miz
miz = path.absolute().as_posix()
if not path.exists():
logging.warning(f"Layout miz file not found: '{miz}'")
return
template_position: dict[str, Point] = {}
temp_mis = dcs.Mission()
with logged_duration(f"Parsing {miz}"):

View File

@ -125,6 +125,14 @@ def debug_dir() -> Path:
return base_path() / "Retribution" / "Debug"
def groups_dir() -> Path:
return base_path() / "Retribution" / "Groups"
def layouts_dir() -> Path:
return base_path() / "Retribution" / "Layouts"
def waypoint_debug_directory() -> Path:
return debug_dir() / "Waypoints"