Initial commit: Plants turn-based battle game
This commit is contained in:
@@ -0,0 +1,120 @@
|
||||
from __future__ import annotations
|
||||
|
||||
import random
|
||||
from dataclasses import dataclass, field
|
||||
from typing import List
|
||||
|
||||
# Target kinds
|
||||
TARGET_ENEMY = "enemy"
|
||||
TARGET_ALL_ENEMIES = "all_enemies"
|
||||
TARGET_TWO_ENEMIES = "two_enemies"
|
||||
TARGET_ALLY = "ally"
|
||||
TARGET_ALL_ALLIES = "all_allies"
|
||||
TARGET_SELF = "self"
|
||||
TARGET_ANY = "any"
|
||||
|
||||
# Effect kinds
|
||||
EFF_SHIELD = "shield"
|
||||
EFF_WILT = "wilt" # value = % of the skill's damage dealt, over 3 turns
|
||||
EFF_DOT = "dot" # value = damage per turn, duration = turns
|
||||
EFF_HOT = "hot" # value = heal per turn, duration = turns
|
||||
EFF_STATUS = "status" # applies status[key] with value/duration
|
||||
EFF_HEAL = "heal" # immediate heal
|
||||
|
||||
|
||||
@dataclass
|
||||
class Effect:
|
||||
kind: str
|
||||
value: int = 0
|
||||
duration: int = 0
|
||||
key: str = ""
|
||||
|
||||
|
||||
@dataclass
|
||||
class Skill:
|
||||
name: str
|
||||
power: int = 0
|
||||
cooldown: int = 0
|
||||
target: str = TARGET_ENEMY
|
||||
kind: str = "damage" # damage | heal | shield | utility
|
||||
hits: int = 1
|
||||
effects: List[Effect] = field(default_factory=list)
|
||||
description: str = ""
|
||||
priority: int = 100 # lower = "best" (preselected / AI preference)
|
||||
mechanic: str = "" # special behaviour id handled by the engine
|
||||
extra_action: bool = False
|
||||
requires_form: str = "" # hydrangea: "acidic" | "alkaline"
|
||||
power_alt: int = 0 # conditional power (e.g. [50/75])
|
||||
cooldown_left: int = field(init=False, default=0)
|
||||
|
||||
|
||||
def roll_crit(chance: float) -> bool:
|
||||
return random.random() < chance
|
||||
|
||||
|
||||
def skill_to_dict(sk: "Skill") -> dict:
|
||||
"""Serialize a Skill (minus runtime cooldown) for persistence."""
|
||||
return {
|
||||
"name": sk.name,
|
||||
"power": sk.power,
|
||||
"cooldown": sk.cooldown,
|
||||
"target": sk.target,
|
||||
"kind": sk.kind,
|
||||
"hits": sk.hits,
|
||||
"effects": [{"kind": e.kind, "value": e.value, "duration": e.duration, "key": e.key}
|
||||
for e in sk.effects],
|
||||
"description": sk.description,
|
||||
"mechanic": sk.mechanic,
|
||||
"extra_action": sk.extra_action,
|
||||
"requires_form": sk.requires_form,
|
||||
"power_alt": sk.power_alt,
|
||||
}
|
||||
|
||||
|
||||
def skill_from_dict(d: dict) -> "Skill":
|
||||
"""Recreate a Skill from a skill_to_dict payload."""
|
||||
return Skill(
|
||||
name=d["name"],
|
||||
power=d.get("power", 0),
|
||||
cooldown=d.get("cooldown", 0),
|
||||
target=d.get("target", TARGET_ENEMY),
|
||||
kind=d.get("kind", "damage"),
|
||||
hits=d.get("hits", 1),
|
||||
effects=[Effect(**e) for e in d.get("effects", [])],
|
||||
description=d.get("description", ""),
|
||||
mechanic=d.get("mechanic", ""),
|
||||
extra_action=d.get("extra_action", False),
|
||||
requires_form=d.get("requires_form", ""),
|
||||
power_alt=d.get("power_alt", 0),
|
||||
)
|
||||
|
||||
|
||||
# --- shared status keys -------------------------------------------------
|
||||
S_SPEED_DOWN = "speed_down"
|
||||
S_CRIT_DOWN = "crit_down"
|
||||
S_ATTACK_DOWN = "attack_down"
|
||||
S_DEFENSE_DOWN = "defense_down"
|
||||
S_HEAL_REDUCTION = "healing_reduction"
|
||||
S_HEAL_BOOST = "healing_boost"
|
||||
S_SLEEP = "sleep"
|
||||
S_VULNERABLE = "vulnerable"
|
||||
S_INTOXICATE = "intoxicate"
|
||||
S_OBLIVION = "oblivion"
|
||||
S_TETHER = "tether"
|
||||
S_MADNESS = "madness"
|
||||
S_DENTING = "denting"
|
||||
S_ATTACK_UP = "attack_up"
|
||||
S_DEFENSE_UP = "defense_up"
|
||||
S_SPEED_UP = "speed_up"
|
||||
S_WILT = "wilt"
|
||||
S_DOT = "dot"
|
||||
S_HOT = "hot"
|
||||
S_SHIELD = "shield"
|
||||
S_ICICLES = "icicles"
|
||||
S_SNOWFLAKES = "snowflakes"
|
||||
S_ZINNIA_WEAKEN = "zinnia_weaken"
|
||||
S_ABSORB = "absorb"
|
||||
S_PREVENT_FIRST_DAMAGE = "prevent_first_damage"
|
||||
S_LYING_WAIT = "lying_wait"
|
||||
S_SEED = "seed" # orchid: erupts later
|
||||
S_ATTACKED_THIS_TURN = "attacked_this_turn" # marigold: first-hit guard
|
||||
Reference in New Issue
Block a user