using System.Text.Json.Serialization; namespace Theriapolis.Core.Data; /// /// Immutable item definition loaded from items.json. Covers weapons, /// armor, shields, consumables, adventuring gear, and natural-weapon /// enhancers. Phase 5 ships a curated subset focused on combat readiness; /// the remaining catalog from equipment.md fills in over later phases. /// public sealed record ItemDef { [JsonPropertyName("id")] public string Id { get; init; } = ""; [JsonPropertyName("name")] public string Name { get; init; } = ""; /// "weapon", "armor", "shield", "consumable", "gear", "natural_weapon_enhancer". [JsonPropertyName("kind")] public string Kind { get; init; } = "gear"; [JsonPropertyName("cost_fang")] public float CostFang { get; init; } = 0f; [JsonPropertyName("weight_lb")] public float WeightLb { get; init; } = 0f; /// Sizes this item is manufactured for: "small" / "medium" / "large". [JsonPropertyName("sizes")] public string[] Sizes { get; init; } = new[] { "medium" }; /// Free-text properties from equipment.md (e.g. "finesse", "light", "two_handed", "versatile", "heavy", "loading", "thrown", "reach", "ammunition"). [JsonPropertyName("properties")] public string[] Properties { get; init; } = Array.Empty(); /// Free-text description for tooltips and codex. [JsonPropertyName("description")] public string Description { get; init; } = ""; // ── Weapon fields (kind = "weapon") ───────────────────────────────── /// Weapon proficiency category: "simple", "martial", "natural", "firearm". [JsonPropertyName("proficiency")] public string Proficiency { get; init; } = ""; /// Damage dice expression (e.g. "1d6", "2d6", "1d8+2"). Empty for non-weapons. [JsonPropertyName("damage")] public string Damage { get; init; } = ""; /// Versatile two-handed damage dice (e.g. "1d10" when used two-handed). Empty if not versatile. [JsonPropertyName("damage_versatile")] public string DamageVersatile { get; init; } = ""; [JsonPropertyName("damage_type")] public string DamageType { get; init; } = ""; /// Melee reach in tactical tiles. 0 / unset = default (1 for M, 2 for L). [JsonPropertyName("reach_tiles")] public int ReachTiles { get; init; } = 0; /// Ranged: short / long ranges in tactical tiles. (0,0) for melee. [JsonPropertyName("range_short_tiles")] public int RangeShortTiles { get; init; } = 0; [JsonPropertyName("range_long_tiles")] public int RangeLongTiles { get; init; } = 0; // ── Armor / shield fields (kind = "armor" | "shield") ────────────── /// Base AC value (armor) or AC bonus (shield). [JsonPropertyName("ac_base")] public int AcBase { get; init; } = 0; /// Max DEX modifier added to AC (medium = 2, heavy = 0). -1 = unlimited. [JsonPropertyName("ac_max_dex")] public int AcMaxDex { get; init; } = -1; /// "light", "medium", "heavy" — for armor only. [JsonPropertyName("armor_class")] public string ArmorClass { get; init; } = ""; [JsonPropertyName("min_str")] public int MinStr { get; init; } = 0; [JsonPropertyName("stealth_disadvantage")] public bool StealthDisadvantage { get; init; } = false; // ── Natural-weapon-enhancer fields (kind = "natural_weapon_enhancer") ─ /// Which natural-weapon location this enhancer attaches to: "fang", "claw", "hoof", "antler", "horn", "tail". [JsonPropertyName("enhancer_slot")] public string EnhancerSlot { get; init; } = ""; /// Damage modifier added to the natural attack (e.g. +1 or +2). [JsonPropertyName("damage_bonus")] public int DamageBonus { get; init; } = 0; /// Clades this enhancer is fitted for. Empty = universal. [JsonPropertyName("clade_fit")] public string[] CladeFit { get; init; } = Array.Empty(); // ── Consumable fields (kind = "consumable") ───────────────────────── /// "healing", "poison", "pheromone", "performance", "scent_mask", etc. [JsonPropertyName("consumable_kind")] public string ConsumableKind { get; init; } = ""; /// Healing dice expression for healing consumables (e.g. "1d4", "2d6"). [JsonPropertyName("healing")] public string Healing { get; init; } = ""; }