From 62348fe70af9073f52bb06e0bef6e79669234f2c Mon Sep 17 00:00:00 2001 From: Nat Quayle Nelson Date: Wed, 18 May 2022 23:59:21 -0400 Subject: [PATCH] blades-engine read creature data --- .../blades-engine/source/data/CreatureData.hx | 187 ++++++++++++++++++ .../source/data/CreatureData.kiss | 41 ++++ .../blades-engine/source/data/ScenData.hx | 27 +++ 3 files changed, 255 insertions(+) create mode 100644 projects/blades-engine/source/data/CreatureData.hx create mode 100644 projects/blades-engine/source/data/CreatureData.kiss diff --git a/projects/blades-engine/source/data/CreatureData.hx b/projects/blades-engine/source/data/CreatureData.hx new file mode 100644 index 00000000..9bf4d6b6 --- /dev/null +++ b/projects/blades-engine/source/data/CreatureData.hx @@ -0,0 +1,187 @@ +package data; + +using Type; +using Reflect; +import kiss.Prelude; + +enum MeleeAbility { + Poison; + Slow; + Disease; + Sleep; + Paralyze; + Acid; + Fire; + Cold; + DrainXP; + ColdDrainXP; + Web; +} + +enum RayAbility { + CurseAndWeaken; + TurnToStone; + Charm; + Sleep; + Paralyze; + DrainSP; + Confuse; + Terrify; + Fire; + MagicDamage; +} + +enum ThrowAbility { + Web4; // range 4 + Rocks; + Spines; // damage and paralysis +} + +enum FieldAbility { + Fire; + Cold; + AntiMagic; + Sleep; + Stink; + Blade; +} + +enum BreathAbility { + Fire; + Cold; + Acid; + Darkness; +} + +enum SpecialAbility { + None; + Melee(a: MeleeAbility); + Ray(a: RayAbility); + Throw(a: ThrowAbility); + Radiate(a: FieldAbility); + Breath(a: BreathAbility); + Invisible; + SplitsWhenHit; + ForceCage; +} + +enum Attitude { + Friendly; + Neutral; + HostileA; + HostileB; +} + +enum Species { + Human; + Humanoid; + Nephil; // bonus missle weapons and dexterity + Slith; // bonus pole weapons and fire resistance + Giant; + Reptile; // won't pick up or use items + Beast; // same + Demon; // same + vulnerable to Repel Spirit at high levels + immune to mental spells + Undead; // same + vulnerable to Repel Spirit + same + Insect; // same + immune to mental spells + immune to webs + SlimeOrPlant; // same + same + immune to assassination + StoneOrGolem; // same + same + immune to beams + Special; // immune to assassination and lethal blow. Immune to simulacrum. Immune to webs. + Vahnatai; + Other; +} + +enum AttackType { + Strike; + Claw; + Bite; + Slimes; + Punches; + Stings; + Clubs; + Burns; + Harms; + Stabs; + Kicks; +} + +enum StrategyType { + Default; + ArcherOrCaster; +} + +typedef Strategy = { + type: StrategyType, + persistentTarget: Bool +}; + +@:build(kiss.Kiss.build()) +class CreatureData { + public function new() {} + + public function clone():CreatureData { + var cd = new CreatureData(); + for (field in CreatureData.getInstanceFields()) { + cd.setField(field, this.field(field)); + } + return cd; + } + + public var name:String = ""; + public var default_script:String = "basicnpc"; + public var level = 2; + public var hp_bonus = 0; + public var sp_bonus = 0; + private var special_abil = 0; + // specialAbility() defined in kiss file + + private var default_attitude = 2; + public function defaultAttitude() { + return Attitude.createEnumIndex(default_attitude - 2); + } + + private var species = 0; + public function getSpecies() { + return Species.createEnumIndex(species); + } + public var natural_armor = 0; + public var attack_1 = 0; + public var attack_2 = 0; + public var attack_3 = 0; + private var attack_1_type = 0; + public function attack1Type() { + return AttackType.createEnumIndex(attack_1_type); + } + private var attack_23_type = 0; + public function attack23Type() { + return AttackType.createEnumIndex(attack_23_type); + } + public var ap_bonus = 0; + private var default_strategy = 0; + public function defaultStrategy():Strategy { + return { + type: StrategyType.createEnumIndex(default_strategy % 10), + persistentTarget: default_strategy >= 10 + }; + } + + private var default_aggression = 100; + public function defaultAggression() { + return default_aggression / 100.0; + } + private var default_courage = 100; + public function defaultCourage() { + return default_courage / 100.0; + } + public var which_sheet = 0; + public var icon_adjust = 0; + private var small_or_large_template = 0; + public var which_sheet_upper = -1; + public var summon_class = -1; + private var what_stat_adjust:Array = []; + private var amount_stat_adjust:Array = []; + private var start_item:Array = []; + private var start_item_chance:Array = []; + private var immunities:Array = []; + + // TODO public functions that return and contextualize the array variables +} diff --git a/projects/blades-engine/source/data/CreatureData.kiss b/projects/blades-engine/source/data/CreatureData.kiss new file mode 100644 index 00000000..e0889585 --- /dev/null +++ b/projects/blades-engine/source/data/CreatureData.kiss @@ -0,0 +1,41 @@ +(method specialAbility [] + (case special_abil + (0 None) + (1 (Melee Poison)) + (2 (Ray CurseAndWeaken)) + (3 (Ray TurnToStone)) + (4 (Melee Slow)) + (5 (Throw Web4)) + (6 (Melee Disease)) + (7 (Ray Charm)) + (8 (Melee Sleep)) + (9 (Ray Sleep)) + (10 (Melee Paralyze)) + (11 (Ray Paralyze)) + (12 (Melee Acid)) + (13 (Ray DrainSP)) + (14 (Ray Confuse)) + (15 (Ray Terrify)) + (16 (Throw Rocks)) + (17 (Breath Fire)) + (18 (Breath Cold)) + (19 (Breath Acid)) + (20 (Melee Fire)) + (21 (Melee Cold)) + (22 (Melee DrainXP)) + (23 (Melee ColdDrainXP)) + (24 Invisible) + (26 (Radiate Fire)) + (27 (Radiate Cold)) + (28 (Radiate AntiMagic)) + (29 SplitsWhenHit) + (30 (Ray Fire)) + (32 (Ray MagicDamage)) + (33 (Breath Darkness)) + (34 (Throw Spines)) + (35 ForceCage) + (36 (Melee Web)) + (37 (Radiate Sleep)) + (38 (Radiate Stink)) + (39 (Radiate Blade)) + (otherwise (throw "undefined special_abil")))) \ No newline at end of file diff --git a/projects/blades-engine/source/data/ScenData.hx b/projects/blades-engine/source/data/ScenData.hx index 987fc335..a6ba5b48 100644 --- a/projects/blades-engine/source/data/ScenData.hx +++ b/projects/blades-engine/source/data/ScenData.hx @@ -4,6 +4,7 @@ import hscript.Parser; import hscript.Interp; import sys.io.File; +using Reflect; using StringTools; class ScenData { @@ -11,6 +12,7 @@ class ScenData { public var floorData:Map = []; public var terrainData:Map = []; + public var creatureData:Map = []; static var failed:Array = []; static var passed = 0; @@ -33,6 +35,10 @@ class ScenData { assert(floorData[129].which_sheet == 704, "floors can import other floors' data"); assert(floorData[129].specialProperty() == BlockedToNPCs, "blocked special property becomes enum"); assert(terrainData[12].name == "Door", "door is door"); + assert(terrainData[404].name == "Hitching Post", "multi-token name string"); + + assert(creatureData[23].field("start_item")[2] == 55, "array properties (nephil starter item)"); + assert(creatureData[23].field("start_item_chance")[2] == 100, "array properties (nephil starter item)"); trace('$passed assertions passed'); if (failed.length > 0) { @@ -59,6 +65,8 @@ class ScenData { floorData; case "terrain": terrainData; + case "creature": + creatureData; default: null; }; @@ -80,6 +88,8 @@ class ScenData { new FloorData(); case "terrain": new TerrainData(); + case "creature": + new CreatureData(); default: null; }; @@ -120,11 +130,28 @@ class ScenData { line = "data." + line.substr(3); } else if (line.startsWith("te_")) { line = "data." + line.substr(3); + } else if (line.startsWith("cr_")) { + line = "data." + line.substr(3); } else if (line == "clear;") { line = "clear();"; } else if (line.startsWith("import =")) { line = "_" + line.replace("=", "(").replace(";", ");"); } + + // Wrap array assignments: + if (line.startsWith("data.")) { + var tokens = line.split(" "); + var isString = false; + for (token in tokens) { + if (token.indexOf('"') != -1) + isString = true; + } + // = or = + if (!isString && tokens.length > 3) { + line = tokens[0] + '[${tokens[1]}] = ' + tokens[3]; + } + } + try { interp.execute(parser.parseString(line)); } catch (e) {