mirror of
https://github.com/dcs-retribution/dcs-retribution.git
synced 2025-11-10 15:41:24 +00:00
- Fix tgogenerator - Fix UI for ForceGroup and Layouts - Fix ammo depot handling - Split bigger files in smaller meaningful files (TGO, layouts, forces) - Renamed Template to Layout - Renamed GroundGroup to TheaterGroup and GroundUnit to TheaterUnit - Reorganize Layouts and UnitGroups to a ArmedForces class and ForceGroup similar to the AirWing and Squadron - Reworded the UnitClass, GroupRole, GroupTask (adopted to PEP8) and reworked the connection from Role and Task - added comments - added missing unit classes - added temp workaround for missing classes - add repariable property to TheaterUnit - Review and Cleanup Added serialization for loaded templates Loading the templates from the .miz files takes a lot of computation time and in the future there will be more templates added to the system. Therefore a local pickle serialization for the loaded templates was re-added: - The pickle will be created the first time the TemplateLoader will be accessed - Pickle is stored in Liberation SaveDir - Added UI option to (re-)import templates
157 lines
5.0 KiB
Python
157 lines
5.0 KiB
Python
from __future__ import annotations
|
|
|
|
from dataclasses import dataclass, field
|
|
from typing import Any, Type
|
|
|
|
from dcs.unittype import UnitType as DcsUnitType
|
|
|
|
from game import db
|
|
from game.data.groups import GroupRole, GroupTask
|
|
from game.data.units import UnitClass
|
|
|
|
|
|
@dataclass
|
|
class GroupLayoutMapping:
|
|
# The group name used in the template.miz
|
|
name: str
|
|
|
|
# Defines if the group is required for the template or can be skipped
|
|
optional: bool = False
|
|
|
|
# All static units for the group
|
|
statics: list[str] = field(default_factory=list)
|
|
|
|
# Defines to which tgo group the groupTemplate will be added
|
|
# This allows to merge groups back together. Default: Merge all to group 1
|
|
group: int = field(default=1)
|
|
|
|
# How many units should be generated from the grouplayout. If only one value is
|
|
# added this will be an exact amount. If 2 values are used it will be a random
|
|
# amount between these values.
|
|
unit_count: list[int] = field(default_factory=list)
|
|
|
|
# All unit types the template supports.
|
|
unit_types: list[Type[DcsUnitType]] = field(default_factory=list)
|
|
|
|
# All unit classes the template supports.
|
|
unit_classes: list[UnitClass] = field(default_factory=list)
|
|
|
|
# TODO Clarify if this is required. Only used for EWRs to also Use SR when no
|
|
# dedicated EWRs are available to the faction
|
|
alternative_classes: list[UnitClass] = field(default_factory=list)
|
|
|
|
def to_dict(self) -> dict[str, Any]:
|
|
d = self.__dict__
|
|
if not self.optional:
|
|
d.pop("optional")
|
|
if not self.statics:
|
|
d.pop("statics")
|
|
if not self.unit_types:
|
|
d.pop("unit_types")
|
|
if not self.unit_classes:
|
|
d.pop("unit_classes")
|
|
else:
|
|
d["unit_classes"] = [unit_class.value for unit_class in self.unit_classes]
|
|
if not self.alternative_classes:
|
|
d.pop("alternative_classes")
|
|
else:
|
|
d["alternative_classes"] = [
|
|
unit_class.value for unit_class in self.alternative_classes
|
|
]
|
|
if not self.unit_count:
|
|
d.pop("unit_count")
|
|
return d
|
|
|
|
@staticmethod
|
|
def from_dict(d: dict[str, Any]) -> GroupLayoutMapping:
|
|
optional = d["optional"] if "optional" in d else False
|
|
statics = d["statics"] if "statics" in d else []
|
|
unit_count = d["unit_count"] if "unit_count" in d else []
|
|
unit_types = []
|
|
if "unit_types" in d:
|
|
for u in d["unit_types"]:
|
|
unit_type = db.unit_type_from_name(u)
|
|
if unit_type:
|
|
unit_types.append(unit_type)
|
|
group = d["group"] if "group" in d else 1
|
|
unit_classes = (
|
|
[UnitClass(u) for u in d["unit_classes"]] if "unit_classes" in d else []
|
|
)
|
|
alternative_classes = (
|
|
[UnitClass(u) for u in d["alternative_classes"]]
|
|
if "alternative_classes" in d
|
|
else []
|
|
)
|
|
return GroupLayoutMapping(
|
|
d["name"],
|
|
optional,
|
|
statics,
|
|
group,
|
|
unit_count,
|
|
unit_types,
|
|
unit_classes,
|
|
alternative_classes,
|
|
)
|
|
|
|
|
|
@dataclass
|
|
class LayoutMapping:
|
|
# The name of the Template
|
|
name: str
|
|
|
|
# An optional description to give more information about the template
|
|
description: str
|
|
|
|
# Optional field to define if the template can be used to create generic groups
|
|
generic: bool
|
|
|
|
# The role the template can be used for
|
|
role: GroupRole
|
|
|
|
# All taskings the template can be used for
|
|
tasks: list[GroupTask]
|
|
|
|
# All Groups the template has
|
|
groups: list[GroupLayoutMapping]
|
|
|
|
# Define the miz file for the template. Optional. If empty use the mapping name
|
|
layout_file: str
|
|
|
|
def to_dict(self) -> dict[str, Any]:
|
|
d = {
|
|
"name": self.name,
|
|
"description": self.description,
|
|
"generic": self.generic,
|
|
"role": self.role.value,
|
|
"tasks": [task.description for task in self.tasks],
|
|
"groups": [group.to_dict() for group in self.groups],
|
|
"layout_file": self.layout_file,
|
|
}
|
|
if not self.description:
|
|
d.pop("description")
|
|
if not self.generic:
|
|
# Only save if true
|
|
d.pop("generic")
|
|
if not self.layout_file:
|
|
d.pop("layout_file")
|
|
return d
|
|
|
|
@staticmethod
|
|
def from_dict(d: dict[str, Any], file_name: str) -> LayoutMapping:
|
|
groups = [GroupLayoutMapping.from_dict(group) for group in d["groups"]]
|
|
description = d["description"] if "description" in d else ""
|
|
generic = d["generic"] if "generic" in d else False
|
|
layout_file = (
|
|
d["layout_file"] if "layout_file" in d else file_name.replace("yaml", "miz")
|
|
)
|
|
tasks = [GroupTask.by_description(task) for task in d["tasks"]]
|
|
return LayoutMapping(
|
|
d["name"],
|
|
description,
|
|
generic,
|
|
GroupRole(d["role"]),
|
|
tasks,
|
|
groups,
|
|
layout_file,
|
|
)
|