From c329c806dfadb4a7fd21fd5b3f8dbc1d3c556a7b Mon Sep 17 00:00:00 2001 From: Vasyl Horbachenko Date: Tue, 26 Jun 2018 03:31:29 +0300 Subject: [PATCH] take off silencing WIP; fixes for blufor; fixed SAMs commision on samless campaigns --- __init__.py | 10 +++++++++- game/db.py | 9 +++++++++ game/event/capture.py | 7 +++++-- game/event/event.py | 6 +++--- game/game.py | 7 ++++++- game/settings.py | 1 + gen/aircraft.py | 28 +++++++++++++++++----------- gen/settingsgen.py | 12 ++++++++++-- ui/basemenu.py | 10 +++++----- ui/newgamemenu.py | 6 ++++++ ui/overviewcanvas.py | 16 +++++++++++++--- 11 files changed, 84 insertions(+), 28 deletions(-) diff --git a/__init__.py b/__init__.py index 2bd319b9..a308eaaf 100755 --- a/__init__.py +++ b/__init__.py @@ -27,7 +27,7 @@ game = persistency.restore_game() if not game: new_game_menu = None # type: NewGameMenu - def start_new_game(player_name: str, enemy_name: str, terrain: str, sams: bool, multiplier: float): + def start_new_game(player_name: str, enemy_name: str, terrain: str, sams: bool, midgame: bool, multiplier: float): if terrain == "persiangulf": conflicttheater = theater.persiangulf.PersianGulfTheater() elif terrain == "nevada": @@ -35,12 +35,20 @@ if not game: else: conflicttheater = theater.caucasus.CaucasusTheater() + if midgame: + for i in range(0, int(len(conflicttheater.controlpoints) / 2)): + conflicttheater.controlpoints[i].captured = True + start_generator.generate_initial(conflicttheater, enemy_name, sams, multiplier) game = Game(player_name=player_name, enemy_name=enemy_name, theater=conflicttheater) game.budget = int(game.budget * multiplier) game.settings.multiplier = multiplier + game.settings.sams = sams + + if midgame: + game.budget = game.budget * 8 proceed_to_main_menu(game) diff --git a/game/db.py b/game/db.py index 734662e2..f7dce96b 100644 --- a/game/db.py +++ b/game/db.py @@ -160,6 +160,10 @@ TAKEOFF_BAN = [ AV8BNA, ] +CARRIER_TAKEOFF_BAN = [ + Su_33, +] + EXTRA_AA = { "Russia": AirDefence.SAM_SA_9_Strela_1_9P31, "USA": AirDefence.SAM_Patriot_EPP_III, @@ -252,6 +256,11 @@ PLANE_PAYLOAD_OVERRIDES = { "*": "AIM-9M*6, AIM-7M*2, FUEL*3", }, + Su_33: { + "*": "R-73*4,R-27R*2,R-27ER*6", + "_carrier": "R-73*4", + }, + AV8BNA: { CAS: "AS 2", }, diff --git a/game/event/capture.py b/game/event/capture.py index d111a595..d7ff5f37 100644 --- a/game/event/capture.py +++ b/game/event/capture.py @@ -12,12 +12,15 @@ from .event import Event class CaptureEvent(Event): silent = True - BONUS_BASE = 7 + BONUS_BASE = 10 STRENGTH_RECOVERY = 0.35 def __str__(self): return "Attack from {} to {}".format(self.from_cp, self.to_cp) + def bonus(self): + return + @property def threat_description(self): descr = "{} aircraft + CAS, {} vehicles".format( @@ -33,7 +36,7 @@ class CaptureEvent(Event): def is_successfull(self, debriefing: Debriefing): alive_attackers = sum([v for k, v in debriefing.alive_units[self.attacker_name].items() if db.unit_task(k) == PinpointStrike]) alive_defenders = sum([v for k, v in debriefing.alive_units[self.defender_name].items() if db.unit_task(k) == PinpointStrike]) - attackers_success = alive_attackers > alive_defenders + attackers_success = alive_attackers >= alive_defenders if self.from_cp.captured: return attackers_success else: diff --git a/game/event/event.py b/game/event/event.py index 8186d1f8..15bbc58b 100644 --- a/game/event/event.py +++ b/game/event/event.py @@ -5,7 +5,7 @@ from theater import * from userdata.debriefing import Debriefing -DIFFICULTY_LOG_BASE = 1.5 +DIFFICULTY_LOG_BASE = 1.1 class Event: @@ -15,7 +15,7 @@ class Event: operation = None # type: Operation difficulty = 1 # type: int game = None # type: Game - BONUS_BASE = 0 + BONUS_BASE = 3 def __init__(self, attacker_name: str, defender_name: str, from_cp: ControlPoint, to_cp: ControlPoint, game): self.attacker_name = attacker_name @@ -40,7 +40,7 @@ class Event: return "" def bonus(self) -> int: - return math.ceil(math.log(self.difficulty, DIFFICULTY_LOG_BASE) * self.BONUS_BASE) + return int(math.log(self.to_cp.importance + 1, DIFFICULTY_LOG_BASE) * self.BONUS_BASE) def is_successfull(self, debriefing: Debriefing) -> bool: return self.operation.is_successfull(debriefing) diff --git a/game/game.py b/game/game.py index e7b50dd9..7a05d0fe 100644 --- a/game/game.py +++ b/game/game.py @@ -130,7 +130,12 @@ class Game: points_to_spend = cp.base.append_commision_points(for_task, awarded_points) if points_to_spend > 0: importance_factor = (cp.importance - IMPORTANCE_LOW) / (IMPORTANCE_HIGH - IMPORTANCE_LOW) - unittypes = db.choose_units(for_task, importance_factor, COMMISION_UNIT_VARIETY, self.enemy) + + if for_task == AirDefence and not self.settings.sams: + unittypes = [x for x in db.find_unittype(AirDefence, self.enemy) if x not in db.SAM_BAN] + else: + unittypes = db.choose_units(for_task, importance_factor, COMMISION_UNIT_VARIETY, self.enemy) + d = {random.choice(unittypes): points_to_spend} print("Commision {}: {}".format(cp, d)) cp.base.commision_units(d) diff --git a/game/settings.py b/game/settings.py index 412e6e88..69db52b2 100644 --- a/game/settings.py +++ b/game/settings.py @@ -5,3 +5,4 @@ class Settings: only_player_takeoff = False night_disabled = False multiplier = 1 + sams = True diff --git a/gen/aircraft.py b/gen/aircraft.py index 9a3e5fd8..23744eac 100644 --- a/gen/aircraft.py +++ b/gen/aircraft.py @@ -57,7 +57,7 @@ class AircraftConflictGenerator: count -= group_size client_count -= client_size - def _setup_group(self, group: FlyingGroup, for_task: Task, clients: db.PlaneDict): + def _setup_group(self, group: FlyingGroup, for_task: Task, at: db.StartingPosition, client_count: int): did_load_loadout = False unit_type = group.units[0].unit_type if unit_type in db.PLANE_PAYLOAD_OVERRIDES: @@ -66,6 +66,9 @@ class AircraftConflictGenerator: if for_task in db.PLANE_PAYLOAD_OVERRIDES[unit_type]: group.load_loadout(db.PLANE_PAYLOAD_OVERRIDES[unit_type][for_task]) did_load_loadout = True + elif "_carrier" in db.PLANE_PAYLOAD_OVERRIDES[unit_type] and isinstance(at, ShipGroup): + group.load_loadout(db.PLANE_PAYLOAD_OVERRIDES[unit_type]["_carrier"]) + did_load_loadout = True elif "*" in db.PLANE_PAYLOAD_OVERRIDES[unit_type]: group.load_loadout(db.PLANE_PAYLOAD_OVERRIDES[unit_type]["*"]) did_load_loadout = True @@ -80,9 +83,8 @@ class AircraftConflictGenerator: for unit_instance in group.units: unit_instance.livery_id = db.PLANE_LIVERY_OVERRIDES[unit_type] - single_client = sum(clients.values()) == 1 - client_count = clients.get(unit_type, 0) - for idx in range(min(client_count, len(group.units))): + single_client = client_count == 1 + for idx in range(0, min(len(group.units), client_count)): if single_client: group.units[idx].set_player() else: @@ -135,7 +137,11 @@ class AircraftConflictGenerator: if isinstance(at, Point): return self._generate_inflight(name, side, unit_type, count, client_count, at) elif isinstance(at, ShipGroup): - return self._generate_at_carrier(name, side, unit_type, count, client_count, at) + takeoff_ban = unit_type in db.CARRIER_TAKEOFF_BAN + if not takeoff_ban: + return self._generate_at_carrier(name, side, unit_type, count, client_count, at) + else: + return self._generate_inflight(name, side, unit_type, count, client_count, at.position) elif issubclass(at, Airport): takeoff_ban = unit_type in db.TAKEOFF_BAN ai_ban = client_count == 0 and self.settings.only_player_takeoff @@ -176,7 +182,7 @@ class AircraftConflictGenerator: position = group.position # type: Point wayp = group.add_waypoint(position.point_from_heading(heading, WORKAROUND_WAYP_DIST), CAS_ALTITUDE, WARM_START_AIRSPEED) - self._setup_group(group, CAP, clients) + self._setup_group(group, CAP, at, client_count) for group in self.escort_targets: wayp.tasks.append(EscortTaskAction(group.id, engagement_max_dist=ESCORT_MAX_DIST)) @@ -199,7 +205,7 @@ class AircraftConflictGenerator: group.add_waypoint(self.conflict.position, CAS_ALTITUDE, WARM_START_AIRSPEED) group.task = CAS.name - self._setup_group(group, CAS, clients) + self._setup_group(group, CAS, at, client_count) group.add_waypoint(self.conflict.from_cp.position, RTB_ALTITUDE) @@ -221,7 +227,7 @@ class AircraftConflictGenerator: wayp.tasks.append(AttackGroup(target_group.id)) group.task = AntishipStrike.name - self._setup_group(group, AntishipStrike, clients) + self._setup_group(group, AntishipStrike, at, client_count) group.add_waypoint(self.conflict.from_cp.position, RTB_ALTITUDE) @@ -255,7 +261,7 @@ class AircraftConflictGenerator: wayp = group.add_waypoint(self.conflict.position, CAS_ALTITUDE, WARM_START_AIRSPEED) wayp.tasks.append(dcs.task.EngageTargets(max_distance=INTERCEPT_MAX_DISTANCE)) wayp.tasks.append(dcs.task.OrbitAction()) - self._setup_group(group, CAP, clients) + self._setup_group(group, CAP, at, client_count) group.add_waypoint(self.conflict.to_cp.position, RTB_ALTITUDE) @@ -295,7 +301,7 @@ class AircraftConflictGenerator: wayp = group.add_waypoint(self.conflict.position, 0) wayp.tasks.append(EngageTargets(max_distance=INTERCEPT_MAX_DISTANCE)) - self._setup_group(group, CAP, clients) + self._setup_group(group, CAP, at, client_count) group.add_waypoint(self.conflict.from_cp.position, RTB_ALTITUDE) @@ -315,4 +321,4 @@ class AircraftConflictGenerator: altitude=HELI_ALT, ) - self._setup_group(group, Transport, clients) + self._setup_group(group, Transport, at, client_count) diff --git a/gen/settingsgen.py b/gen/settingsgen.py index 65a70593..6cbbba19 100644 --- a/gen/settingsgen.py +++ b/gen/settingsgen.py @@ -38,6 +38,10 @@ RANDOM_WEATHER = { } +class Silence(Option): + Key = 7 + + class SettingsGenerator: def __init__(self, mission: Mission, conflict: Conflict, game): self.mission = mission @@ -84,7 +88,7 @@ class SettingsGenerator: for coalition_name, coalition in self.mission.coalition.items(): for country in coalition.countries.values(): if coalition_name == enemy_coalition: - for plane_group in country.plane_group: + for plane_group in country.plane_group + country.helicopter_group: plane_group.late_activation = True activate_by_trigger.append(plane_group) @@ -108,9 +112,10 @@ class SettingsGenerator: for coalition_name, coalition in self.mission.coalition.items(): for country in coalition.countries.values(): if coalition_name == player_coalition: - for plane_group in country.plane_group: + for plane_group in country.plane_group + country.helicopter_group: if plane_group.task == AWACS.name: continue + regroup_heading = self.conflict.to_cp.position.heading_between_point(self.conflict.from_cp.position) pos1 = plane_group.position.point_from_heading(regroup_heading, REGROUP_ZONE_DISTANCE) @@ -124,7 +129,10 @@ class SettingsGenerator: plane_group.points.insert(1, w2) plane_group.points.insert(1, w1) + w1.tasks.append(Silence(True)) w2.tasks.append(SwitchWaypoint(from_waypoint=3, to_waypoint=2)) + plane_group.points[3].tasks.append(Silence(False)) + plane_group.add_trigger_action(SwitchWaypoint(to_waypoint=4)) push_by_trigger.append(plane_group) diff --git a/ui/basemenu.py b/ui/basemenu.py index 636982b4..1a3684fa 100644 --- a/ui/basemenu.py +++ b/ui/basemenu.py @@ -25,8 +25,8 @@ class BaseMenu(Menu): Label(self.frame, text="{}".format(db.unit_type_name(unit_type))).grid(row=row, sticky=W) Label(self.frame, text="({})".format(existing_units)).grid(column=1, row=row) Label(self.frame, text="{}m {}".format(unit_price, scheduled_units and "(bought {})".format(scheduled_units) or "")).grid(column=2, row=row) - Button(self.frame, text="Buy", command=self.buy(unit_type)).grid(column=3, row=row) - Button(self.frame, text="Sell", command=self.sell(unit_type)).grid(column=4, row=row) + Button(self.frame, text="+", command=self.buy(unit_type)).grid(column=3, row=row) + Button(self.frame, text="-", command=self.sell(unit_type)).grid(column=4, row=row) row += 1 units = { @@ -38,7 +38,7 @@ class BaseMenu(Menu): } Label(self.frame, text="Budget: {}m".format(self.game.budget)).grid(row=row, sticky=W) - Button(self.frame, text="Back", command=self.dismiss).grid(column=2, row=row) + Button(self.frame, text="Back", command=self.dismiss).grid(column=4, row=row) row += 1 for task_type, units in units.items(): @@ -62,7 +62,7 @@ class BaseMenu(Menu): self.event.deliver({unit_type: 1}) self.game.budget -= price - self.display() + #self.display() return action @@ -76,6 +76,6 @@ class BaseMenu(Menu): price = db.PRICES[unit_type] self.game.budget += price self.base.commit_losses({unit_type: 1}) - self.display() + #self.display() return action \ No newline at end of file diff --git a/ui/newgamemenu.py b/ui/newgamemenu.py index 1a90f3e2..23bcfec6 100644 --- a/ui/newgamemenu.py +++ b/ui/newgamemenu.py @@ -8,6 +8,7 @@ class NewGameMenu(Menu): selected_country = None # type: IntVar selected_terrain = None # type: IntVar sams = None + midgame = None multiplier = None def __init__(self, window: Window, callback: typing.Callable): @@ -27,6 +28,9 @@ class NewGameMenu(Menu): self.multiplier = StringVar() self.multiplier.set("1") + self.midgame = BooleanVar() + self.midgame.set(0) + @property def player_country_name(self): if self.selected_country.get() == 0: @@ -64,6 +68,7 @@ class NewGameMenu(Menu): Label(self.frame, text="Options").grid(row=1, column=2) Checkbutton(self.frame, text="SAMs", variable=self.sams).grid(row=1, column=2) + Checkbutton(self.frame, text="Mid game", variable=self.midgame).grid(row=2, column=2) Label(self.frame, text="Multiplier").grid(row=0, column=3) Entry(self.frame, textvariable=self.multiplier).grid(row=1, column=3) @@ -75,4 +80,5 @@ class NewGameMenu(Menu): self.enemy_country_name, self.terrain_name, bool(self.sams.get()), + bool(self.midgame.get()), float(self.multiplier.get())) diff --git a/ui/overviewcanvas.py b/ui/overviewcanvas.py index 685a7dca..7e0bd205 100644 --- a/ui/overviewcanvas.py +++ b/ui/overviewcanvas.py @@ -51,6 +51,12 @@ class OverviewCanvas: id = self.canvas.create_text(coords[0], coords[1], text=title, font=font) self.canvas.tag_bind(id, "", self.display(cp)) + def _player_color(self): + return self.game.player == "USA" and "blue" or "red" + + def _enemy_color(self): + return self.game.player == "USA" and "red" or "blue" + def update(self): self.canvas.delete(ALL) self.canvas.create_image((self.image.width()/2, self.image.height()/2), image=self.image) @@ -60,9 +66,9 @@ class OverviewCanvas: for connected_cp in cp.connected_points: connected_coords = self.transform_point(connected_cp.position) if connected_cp.captured != cp.captured: - color = "red" + color = self._enemy_color() elif connected_cp.captured and cp.captured: - color = "blue" + color = self._player_color() else: color = "black" @@ -73,7 +79,11 @@ class OverviewCanvas: arc_size = 22 * math.pow(cp.importance, 1) extent = max(cp.base.strength * 180, 10) start = (180 - extent) / 2 - color = cp.captured and 'blue' or 'red' + + if cp.captured: + color = self._player_color() + else: + color = self._enemy_color() cp_id = self.canvas.create_arc((coords[0] - arc_size/2, coords[1] - arc_size/2), (coords[0]+arc_size/2, coords[1]+arc_size/2),