From 0ee31b72668a5e1f004ef106b55754fa641da0d5 Mon Sep 17 00:00:00 2001 From: GaboGG Date: Tue, 21 Jul 2026 14:00:44 -0400 Subject: [PATCH] Benchmark v2 with real Lv90 stats, Shadow Veil removed, full-conservative defaults MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Shadow Veil removed from BUFF_PRIORITY - was draining MP aggressively. Player stats updated to match real character (effective values with gear). Benchmark results (Lv90, Nightmare, 5 runs each): 1. full-conservative: 146 rounds, 4485 dmg/rd — WINNER 2. conservative-items: 143 rounds, 4468 dmg/rd 3. spirit-40: 136 rounds, 4457 dmg/rd New defaults (full-conservative): - cureHP: 0.45, cureItemHP: 0.50 (save items use cure) - manaGemMP: 0.45, manaPotionMP: 0.25 - spiritPotionSP: 0.30, spiritStanceOC: 80 - skillOC: 75 --- scripts/hv-unified.user.js | 19 +-- scripts/latest.user.js | 19 +-- simulator/results/benchmark.json | 225 ++++++++++++++++--------------- simulator/src/benchmark.js | 24 +++- simulator/src/entities.js | 18 +-- simulator/src/strategy.js | 1 - src/config.js | 16 +-- src/strategy-engine.js | 3 +- 8 files changed, 172 insertions(+), 153 deletions(-) diff --git a/scripts/hv-unified.user.js b/scripts/hv-unified.user.js index fa5050e..240c50f 100644 --- a/scripts/hv-unified.user.js +++ b/scripts/hv-unified.user.js @@ -30,14 +30,14 @@ const CFG = { autoSpirit: false, // — Thresholds - cureHP: 0.35, // Cast Cure below this HP - cureItemHP: 0.65, // Use health items at this HP - cureRegenHP: 0.75, // Cast Regen below this HP - manaGemMP: 0.60, // Use mana gems below this MP (proactive) - manaPotionMP: 0.30, // Use mana potions at critical - spiritPotionSP: 0.45, // Use spirit gems/potions below this SP - spiritStanceOC: 60, // Activate Spirit Stance at this OC - skillOC: 70, // Use weapon skills at this OC (balance between spirit and damage) + cureHP: 0.45, // Cast Cure below this HP (save items, use Cure) + cureItemHP: 0.50, // Use health items at this HP (conservative, let Cure carry) + cureRegenHP: 0.65, // Cast Regen below this HP + manaGemMP: 0.45, // Use mana gems below this MP (conservative) + manaPotionMP: 0.25, // Use mana potions at critical + spiritPotionSP: 0.30, // Use spirit gems/potions below this SP + spiritStanceOC: 80, // Activate Spirit Stance late (save SP for skills) + skillOC: 75, // Use weapon skills at this OC // — Out of battle autoSell: true, @@ -679,9 +679,10 @@ const BUFF_PRIORITY = [ { icon: 'haste', spell: 'Haste', minTurns: 2 }, { icon: 'protection', spell: 'Protection', minTurns: 2 }, { icon: 'spark_of_life', spell: 'Spark of Life', minTurns: 1 }, - { icon: 'shadow_veil', spell: 'Shadow Veil', minTurns: 2 }, { icon: 'regen', spell: 'Regen', minTurns: 2 }, { icon: 'absorb', spell: 'Absorb', minTurns: 2 }, + // Shadow Veil excluded from auto-buff rotation — expensive and drains MP + // from Cure. Cast manually when MP is plentiful. ]; // Known important monster names (bosses, legendaries, ultimates) diff --git a/scripts/latest.user.js b/scripts/latest.user.js index fa5050e..240c50f 100644 --- a/scripts/latest.user.js +++ b/scripts/latest.user.js @@ -30,14 +30,14 @@ const CFG = { autoSpirit: false, // — Thresholds - cureHP: 0.35, // Cast Cure below this HP - cureItemHP: 0.65, // Use health items at this HP - cureRegenHP: 0.75, // Cast Regen below this HP - manaGemMP: 0.60, // Use mana gems below this MP (proactive) - manaPotionMP: 0.30, // Use mana potions at critical - spiritPotionSP: 0.45, // Use spirit gems/potions below this SP - spiritStanceOC: 60, // Activate Spirit Stance at this OC - skillOC: 70, // Use weapon skills at this OC (balance between spirit and damage) + cureHP: 0.45, // Cast Cure below this HP (save items, use Cure) + cureItemHP: 0.50, // Use health items at this HP (conservative, let Cure carry) + cureRegenHP: 0.65, // Cast Regen below this HP + manaGemMP: 0.45, // Use mana gems below this MP (conservative) + manaPotionMP: 0.25, // Use mana potions at critical + spiritPotionSP: 0.30, // Use spirit gems/potions below this SP + spiritStanceOC: 80, // Activate Spirit Stance late (save SP for skills) + skillOC: 75, // Use weapon skills at this OC // — Out of battle autoSell: true, @@ -679,9 +679,10 @@ const BUFF_PRIORITY = [ { icon: 'haste', spell: 'Haste', minTurns: 2 }, { icon: 'protection', spell: 'Protection', minTurns: 2 }, { icon: 'spark_of_life', spell: 'Spark of Life', minTurns: 1 }, - { icon: 'shadow_veil', spell: 'Shadow Veil', minTurns: 2 }, { icon: 'regen', spell: 'Regen', minTurns: 2 }, { icon: 'absorb', spell: 'Absorb', minTurns: 2 }, + // Shadow Veil excluded from auto-buff rotation — expensive and drains MP + // from Cure. Cast manually when MP is plentiful. ]; // Known important monster names (bosses, legendaries, ultimates) diff --git a/simulator/results/benchmark.json b/simulator/results/benchmark.json index 1d39dcf..1ca979e 100644 --- a/simulator/results/benchmark.json +++ b/simulator/results/benchmark.json @@ -1,18 +1,25 @@ { "player": { - "level": 64, + "level": 90, "style": "2H", - "str": 95, - "dex": 40, - "agi": 28, - "end": 265, - "int": 8, - "wis": 35, + "str": 155, + "dex": 96, + "agi": 36, + "end": 77, + "int": 32, + "wis": 75, + "maxHp": 2672, + "maxMp": 232, + "maxSp": 122, "difficulty": "Nightmare", - "prof2h": 80, - "profLight": 70, - "profSupportive": 68, - "profElemental": 50 + "prof2h": 107, + "profLight": 107, + "profSupportive": 107, + "profElemental": 63, + "physMit": 31.5, + "magMit": 29.9, + "critDmg": 1.8, + "accuracy": 92.5 }, "runs": 5, "rounds": 1000, @@ -20,143 +27,143 @@ { "name": "full-conservative", "desc": "Late spirit, save items, no attack spells", - "avgRounds": "225.6", - "avgKills": "1335.0", - "avgDmgRatio": "3.1", - "avgDmgPerRound": 3141, - "avgExp": 10276480, - "avgCredits": 132114, - "maxRounds": 249, + "avgRounds": "146.0", + "avgKills": "809.2", + "avgDmgRatio": "3.2", + "avgDmgPerRound": 4485, + "avgExp": 4388800, + "avgCredits": 57381, + "maxRounds": 166, "survivalRate": "0", "deaths": 5, - "score": 133500 + "score": 80920 }, { "name": "conservative-items", "desc": "Save items, use Cure more", - "avgRounds": "223.6", - "avgKills": "1330.8", + "avgRounds": "142.8", + "avgKills": "793.8", "avgDmgRatio": "3.1", - "avgDmgPerRound": 3128, - "avgExp": 10058080, - "avgCredits": 129729, - "maxRounds": 232, + "avgDmgPerRound": 4468, + "avgExp": 4131520, + "avgCredits": 53230, + "maxRounds": 154, "survivalRate": "0", "deaths": 5, - "score": 133080 - }, - { - "name": "attack-spells", - "desc": "Use cheap attack spells for channeling", - "avgRounds": "213.0", - "avgKills": "1248.2", - "avgDmgRatio": "3.4", - "avgDmgPerRound": 2974, - "avgExp": 9150160, - "avgCredits": 118907, - "maxRounds": 238, - "survivalRate": "0", - "deaths": 5, - "score": 124820 - }, - { - "name": "spirit-80", - "desc": "Spirit Stance at OC 80 (late, skills first)", - "avgRounds": "208.8", - "avgKills": "1218.0", - "avgDmgRatio": "3.4", - "avgDmgPerRound": 3024, - "avgExp": 8762480, - "avgCredits": 111455, - "maxRounds": 212, - "survivalRate": "0", - "deaths": 5, - "score": 121800 + "score": 79380 }, { "name": "spirit-40", "desc": "Spirit Stance at OC 40 (early)", - "avgRounds": "205.4", - "avgKills": "1201.4", - "avgDmgRatio": "3.6", - "avgDmgPerRound": 2990, - "avgExp": 8509680, - "avgCredits": 110122, - "maxRounds": 223, + "avgRounds": "135.8", + "avgKills": "751.2", + "avgDmgRatio": "3.4", + "avgDmgPerRound": 4457, + "avgExp": 3770560, + "avgCredits": 47867, + "maxRounds": 152, "survivalRate": "0", "deaths": 5, - "score": 120140 + "score": 75120 + }, + { + "name": "spirit-80", + "desc": "Spirit Stance at OC 80 (late, skills first)", + "avgRounds": "128.8", + "avgKills": "703.6", + "avgDmgRatio": "3.6", + "avgDmgPerRound": 4398, + "avgExp": 3358160, + "avgCredits": 45813, + "maxRounds": 139, + "survivalRate": "0", + "deaths": 5, + "score": 70360 }, { "name": "skills-at-60", "desc": "Skills fire at OC 60 instead of 80", - "avgRounds": "204.4", - "avgKills": "1185.8", - "avgDmgRatio": "3.7", - "avgDmgPerRound": 3006, - "avgExp": 8400560, - "avgCredits": 109924, - "maxRounds": 213, + "avgRounds": "126.4", + "avgKills": "689.6", + "avgDmgRatio": "3.6", + "avgDmgPerRound": 4356, + "avgExp": 3243600, + "avgCredits": 42872, + "maxRounds": 143, "survivalRate": "0", "deaths": 5, - "score": 118580 + "score": 68960 }, { "name": "baseline", "desc": "Current v0.11.0 defaults", - "avgRounds": "203.8", - "avgKills": "1181.8", - "avgDmgRatio": "3.7", - "avgDmgPerRound": 3011, - "avgExp": 8350320, - "avgCredits": 113818, - "maxRounds": 210, + "avgRounds": "126.4", + "avgKills": "688.8", + "avgDmgRatio": "3.8", + "avgDmgPerRound": 4340, + "avgExp": 3272880, + "avgCredits": 41772, + "maxRounds": 154, "survivalRate": "0", "deaths": 5, - "score": 118180 - }, - { - "name": "balanced", - "desc": "Mid spirit, moderate items, attack spells for chan", - "avgRounds": "200.2", - "avgKills": "1165.2", - "avgDmgRatio": "3.5", - "avgDmgPerRound": 2962, - "avgExp": 8100480, - "avgCredits": 107866, - "maxRounds": 217, - "survivalRate": "0", - "deaths": 5, - "score": 116520 + "score": 68880 }, { "name": "full-aggressive", "desc": "Early spirit + aggressive items + attack spells", - "avgRounds": "194.2", - "avgKills": "1126.6", - "avgDmgRatio": "3.7", - "avgDmgPerRound": 2925, - "avgExp": 7643120, - "avgCredits": 99980, - "maxRounds": 210, + "avgRounds": "126.0", + "avgKills": "688.8", + "avgDmgRatio": "3.5", + "avgDmgPerRound": 4162, + "avgExp": 3215200, + "avgCredits": 41874, + "maxRounds": 141, "survivalRate": "0", "deaths": 5, - "score": 112660 + "score": 68880 + }, + { + "name": "balanced", + "desc": "Mid spirit, moderate items, attack spells for chan", + "avgRounds": "125.8", + "avgKills": "686.4", + "avgDmgRatio": "3.6", + "avgDmgPerRound": 4124, + "avgExp": 3198880, + "avgCredits": 42626, + "maxRounds": 138, + "survivalRate": "0", + "deaths": 5, + "score": 68640 }, { "name": "aggressive-items", "desc": "Use items very proactively", - "avgRounds": "180.2", - "avgKills": "1027.4", - "avgDmgRatio": "4.1", - "avgDmgPerRound": 2963, - "avgExp": 6639040, - "avgCredits": 82094, - "maxRounds": 208, + "avgRounds": "117.0", + "avgKills": "631.4", + "avgDmgRatio": "4.0", + "avgDmgPerRound": 4390, + "avgExp": 2781760, + "avgCredits": 36607, + "maxRounds": 129, "survivalRate": "0", "deaths": 5, - "score": 102740 + "score": 63140 + }, + { + "name": "attack-spells", + "desc": "Use cheap attack spells for channeling", + "avgRounds": "113.4", + "avgKills": "607.8", + "avgDmgRatio": "3.9", + "avgDmgPerRound": 4036, + "avgExp": 2602480, + "avgCredits": 36235, + "maxRounds": 122, + "survivalRate": "0", + "deaths": 5, + "score": 60780 } ], - "timestamp": "2026-07-20T23:52:13.366Z" + "timestamp": "2026-07-21T18:00:29.218Z" } \ No newline at end of file diff --git a/simulator/src/benchmark.js b/simulator/src/benchmark.js index 6c2871d..9994ef4 100644 --- a/simulator/src/benchmark.js +++ b/simulator/src/benchmark.js @@ -6,16 +6,26 @@ const { simulateGrindfest } = require('./grindfest'); const fs = require('fs'); const path = require('path'); -// Player config matching current character (Lv65-ish 2H) +// Player config matching your Lv90 character (effective stats from gear) const PLAYER = { - level: 64, + level: 90, style: '2H', - str: 95, dex: 40, agi: 28, end: 265, int: 8, wis: 35, + // Effective stats (from character page: attributes + equipment bonuses) + str: 155, dex: 96, agi: 36, end: 77, int: 32, wis: 75, + // Effective HP/MP/SP from character page + maxHp: 2672, + maxMp: 232, + maxSp: 122, difficulty: 'Nightmare', - prof2h: 80, - profLight: 70, - profSupportive: 68, - profElemental: 50, + prof2h: 107, + profLight: 107, + profSupportive: 107, + profElemental: 63, + // Derived from gear + physMit: 31.5, + magMit: 29.9, + critDmg: 1.80, + accuracy: 92.5, }; // Strategy configs to test diff --git a/simulator/src/entities.js b/simulator/src/entities.js index e8fd89d..efae6e7 100644 --- a/simulator/src/entities.js +++ b/simulator/src/entities.js @@ -17,10 +17,10 @@ class SimPlayer { this.int = config.int || 6; this.wis = config.wis || 31; // ~93 MP from gear - // Derived stats - this.maxHp = F.calcMaxHp(this.end, this.level); - this.maxMp = F.calcMaxMp(this.wis, this.level); - this.maxSp = F.calcMaxSp(this.int, this.level); + // Derived stats (use effective values from config if provided) + this.maxHp = config.maxHp || F.calcMaxHp(this.end, this.level); + this.maxMp = config.maxMp || F.calcMaxMp(this.wis, this.level); + this.maxSp = config.maxSp || F.calcMaxSp(this.int, this.level); this.hp = this.maxHp; this.mp = this.maxMp; this.sp = this.maxSp; @@ -35,13 +35,13 @@ class SimPlayer { this.profElemental = config.profElemental || 42; // Damage stats - this.baseAtk = F.calcBasePhysDamage(this.str, this.dex, this.level, this.prof2h); - this.critChance = F.calcCritChance(this.str, this.dex); - this.critDamage = F.calcCritDamage(68); // +68% from gear + this.baseAtk = config.baseAtk || F.calcBasePhysDamage(this.str, this.dex, this.level, this.prof2h); + this.critChance = config.critChance || F.calcCritChance(this.str, this.dex); + this.critDamage = config.critDmg || F.calcCritDamage(68); // +68% from gear // Mitigation - this.physMit = 30; // ~30% from light armor - this.magMit = 23; + this.physMit = (config.physMit / 100) || 0.315; + this.magMit = (config.magMit / 100) || 0.299; // Buffs this.buffs = {}; // { name: {turns: N} } diff --git a/simulator/src/strategy.js b/simulator/src/strategy.js index 76b16ac..7f0d382 100644 --- a/simulator/src/strategy.js +++ b/simulator/src/strategy.js @@ -12,7 +12,6 @@ const BUFF_PRIORITY = [ { icon: 'haste', spell: 'Haste', minTurns: 2 }, { icon: 'protection', spell: 'Protection', minTurns: 2 }, { icon: 'spark_of_life', spell: 'Spark of Life', minTurns: 1 }, - { icon: 'shadow_veil', spell: 'Shadow Veil', minTurns: 2 }, { icon: 'regen', spell: 'Regen', minTurns: 2 }, { icon: 'absorb', spell: 'Absorb', minTurns: 2 }, ]; diff --git a/src/config.js b/src/config.js index 1533806..fe079cb 100644 --- a/src/config.js +++ b/src/config.js @@ -15,14 +15,14 @@ const CFG = { autoSpirit: false, // — Thresholds - cureHP: 0.35, // Cast Cure below this HP - cureItemHP: 0.65, // Use health items at this HP - cureRegenHP: 0.75, // Cast Regen below this HP - manaGemMP: 0.60, // Use mana gems below this MP (proactive) - manaPotionMP: 0.30, // Use mana potions at critical - spiritPotionSP: 0.45, // Use spirit gems/potions below this SP - spiritStanceOC: 60, // Activate Spirit Stance at this OC - skillOC: 70, // Use weapon skills at this OC (balance between spirit and damage) + cureHP: 0.45, // Cast Cure below this HP (save items, use Cure) + cureItemHP: 0.50, // Use health items at this HP (conservative, let Cure carry) + cureRegenHP: 0.65, // Cast Regen below this HP + manaGemMP: 0.45, // Use mana gems below this MP (conservative) + manaPotionMP: 0.25, // Use mana potions at critical + spiritPotionSP: 0.30, // Use spirit gems/potions below this SP + spiritStanceOC: 80, // Activate Spirit Stance late (save SP for skills) + skillOC: 75, // Use weapon skills at this OC // — Out of battle autoSell: true, diff --git a/src/strategy-engine.js b/src/strategy-engine.js index e31f08c..50d129d 100644 --- a/src/strategy-engine.js +++ b/src/strategy-engine.js @@ -35,9 +35,10 @@ const BUFF_PRIORITY = [ { icon: 'haste', spell: 'Haste', minTurns: 2 }, { icon: 'protection', spell: 'Protection', minTurns: 2 }, { icon: 'spark_of_life', spell: 'Spark of Life', minTurns: 1 }, - { icon: 'shadow_veil', spell: 'Shadow Veil', minTurns: 2 }, { icon: 'regen', spell: 'Regen', minTurns: 2 }, { icon: 'absorb', spell: 'Absorb', minTurns: 2 }, + // Shadow Veil excluded from auto-buff rotation — expensive and drains MP + // from Cure. Cast manually when MP is plentiful. ]; // Known important monster names (bosses, legendaries, ultimates)