Files
Mana-Loop/src/lib/game/data/guardian-data.ts
T
n8n-gitea 2f580ef0fe
Build and Publish Mana Loop Docker Image / build-and-publish (push) Successful in 1m30s
fix: pact system boon counts and signedPactDetails population
- Fix multi-element guardians (floors 130,140,150,170,190,200,210,230,240) to have exactly 2 boons per spec instead of 3-4
- Fix signedPactDetails never being populated: pipeline processPactRitual now includes signedPactDetails in writes with floor, guardianId, signedAt time, and skillLevels
- Fix completePactRitual in prestigeStore to also populate signedPactDetails
- Update gameStore.ts call site to pass signedPactDetails and current day/hour to processPactRitual

Fixes #309, fixes #308
2026-06-08 14:27:53 +02:00

331 lines
15 KiB
TypeScript
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
// ─── Static Guardian Definitions ─────────────────────────────────────────────────
// Expanded guardian progression:
//
// Tier 1: Base Elements (floors 1080)
// Fire, Water, Air, Earth, Light, Dark, Death, Transference
// Tier 2: Composite Elements (floors 90160)
// Metal, Sand, Lightning, Frost, BlackFlame, Radiant Flames, Miasma, Shadow Glass
// Tier 3: Exotic Elements (floors 170240)
// Crystal, Stellar, Void, Soul, Time, Plasma + convergence guards
//
// Floors 250+ are procedurally generated in guardian-encounters.ts.
import type { GuardianDef } from '../types';
import { resolveMultiUnlockChain } from '../utils/guardian-utils';
// ─── Shared Helpers ─────────────────────────────────────────────────────────────
function hp(floor: number): number {
const base = 5000;
const exponent = 1.1 + (floor / 200);
return Math.floor(base * Math.pow(floor / 10, exponent));
}
function pactCost(hpVal: number, power: number, armor: number, shield: number, barrier: number): number {
return Math.floor(hpVal * 0.3 + power * 5 + hpVal * armor * 0.5 + shield * 2 + hpVal * barrier * 0.3);
}
function mk(
floor: number,
name: string,
element: string[],
color: string,
armor: number,
pactMult: number,
boons: GuardianDef['boons'],
uniquePerk: string,
effects: GuardianDef['effects'],
defensive?: {
shield?: number;
shieldRegen?: number;
barrier?: number;
barrierRegen?: number;
healthRegen?: number;
healthRegenIsPercent?: boolean;
},
): GuardianDef {
const hpVal = hp(floor);
const power = Math.floor(hpVal * 0.5);
const arm = armor;
const shield = defensive?.shield ?? 0;
const barrier = defensive?.barrier ?? 0;
const pc = pactCost(hpVal, power, arm, shield, barrier);
const pt = 2 + Math.floor(floor / 10);
return {
name,
element,
hp: hpVal,
pact: pactMult,
color,
armor: arm,
shield,
shieldRegen: defensive?.shieldRegen ?? 0,
barrier,
barrierRegen: defensive?.barrierRegen ?? 0,
healthRegen: defensive?.healthRegen ?? 0,
healthRegenIsPercent: defensive?.healthRegenIsPercent ?? false,
boons,
pactCost: pc,
pactTime: pt,
uniquePerk,
power,
effects,
signingCost: { mana: pc, time: pt },
unlocksMana: resolveMultiUnlockChain(element),
damageMultiplier: 1.0 + floor * 0.01,
insightMultiplier: 1.0 + floor * 0.005,
};
}
// ═══════════════════════════════════════════════════════════════════════════════
// TIER 1: Base Elements (Floors 1080)
// ═══════════════════════════════════════════════════════════════════════════════
const TIER1: Record<number, GuardianDef> = {
10: mk(10, 'Ignis Prime', ['fire'], '#FF6B35', 0.10, 1.5,
[
{ type: 'elementalDamage', value: 5, desc: '+5% Fire damage' },
{ type: 'maxMana', value: 50, desc: '+50 max mana' },
],
'Fire spells cast 10% faster',
[{ type: 'burn', value: 0.1 }],
),
20: mk(20, 'Aqua Regia', ['water'], '#4ECDC4', 0.15, 1.75,
[
{ type: 'elementalDamage', value: 5, desc: '+5% Water damage' },
{ type: 'manaRegen', value: 0.5, desc: '+0.5 mana regen' },
],
'Water spells deal +15% damage',
[{ type: 'armor_pierce', value: 0.15 }],
{ healthRegen: 10, healthRegenIsPercent: false },
),
30: mk(30, 'Ventus Rex', ['air'], '#00D4FF', 0.18, 2.0,
[
{ type: 'elementalDamage', value: 5, desc: '+5% Air damage' },
{ type: 'castingSpeed', value: 5, desc: '+5% casting speed' },
],
'Air spells have 15% crit chance',
[{ type: 'cast_speed', value: 0.05 }],
),
40: mk(40, 'Terra Firma', ['earth'], '#F4A261', 0.25, 2.25,
[
{ type: 'elementalDamage', value: 5, desc: '+5% Earth damage' },
{ type: 'maxMana', value: 100, desc: '+100 max mana' },
],
'Earth spells deal +25% damage to guardians',
[{ type: 'armor_pierce', value: 0.2 }],
{ shield: 200, shieldRegen: 5 },
),
50: mk(50, 'Lux Aeterna', ['light'], '#FFD700', 0.20, 2.5,
[
{ type: 'elementalDamage', value: 10, desc: '+10% Light damage' },
{ type: 'insightGain', value: 10, desc: '+10% insight gain' },
],
'Light spells reveal enemy weaknesses (+20% damage)',
[{ type: 'crit_chance', value: 0.1 }],
{ barrier: 0.05, barrierRegen: 0.01 },
),
60: mk(60, 'Umbra Mortis', ['dark'], '#9B59B6', 0.22, 2.75,
[
{ type: 'elementalDamage', value: 10, desc: '+10% Dark damage' },
{ type: 'critDamage', value: 15, desc: '+15% crit damage' },
],
'Dark spells deal +25% damage to armored enemies',
[{ type: 'crit_damage', value: 0.15 }],
{ healthRegen: 5, healthRegenIsPercent: true },
),
70: mk(70, 'Mors Ultima', ['death'], '#778CA3', 0.25, 3.0,
[
{ type: 'elementalDamage', value: 10, desc: '+10% Death damage' },
{ type: 'rawDamage', value: 10, desc: '+10% raw damage' },
],
'Death spells execute enemies below 20% HP',
[{ type: 'raw_damage', value: 0.1 }],
{ shield: 400, shieldRegen: 10 },
),
80: mk(80, 'Vinculum Arcana', ['transference'], '#1ABC9C', 0.20, 3.25,
[
{ type: 'maxMana', value: 150, desc: '+150 max mana' },
{ type: 'manaRegen', value: 1.0, desc: '+1.0 mana regen' },
],
'Transference spells have 25% reduced cost',
[{ type: 'cost_reduction', value: 0.25 }],
{ barrier: 0.08, barrierRegen: 0.02, healthRegen: 3, healthRegenIsPercent: true },
),
};
// ═══════════════════════════════════════════════════════════════════════════════
// TIER 2: Composite Elements (Floors 90160) — 8 guardians
// Original: Metal, Sand, Lightning
// New: Frost, BlackFlame, Radiant Flames, Miasma, Shadow Glass
// ═══════════════════════════════════════════════════════════════════════════════
const TIER2: Record<number, GuardianDef> = {
90: mk(90, '', ['metal'], '#BDC3C7', 0.30, 3.5,
[
{ type: 'elementalDamage', value: 15, desc: '+15% Metal damage' },
{ type: 'maxMana', value: 150, desc: '+150 max mana' },
],
'Metal spells pierce 20% armor',
[{ type: 'armor_pierce', value: 0.2 }],
{ shield: 600, shieldRegen: 15, healthRegen: 4, healthRegenIsPercent: true },
),
100: mk(100, '', ['sand'], '#D4AC0D', 0.25, 3.75,
[
{ type: 'elementalDamage', value: 15, desc: '+15% Sand damage' },
{ type: 'manaRegen', value: 1.5, desc: '+1.5 mana regen' },
],
'Sand spells slow enemies by 25%',
[{ type: 'slow', value: 0.25 }],
{ barrier: 0.10, barrierRegen: 0.03, healthRegen: 5, healthRegenIsPercent: true },
),
110: mk(110, '', ['lightning'], '#FFEB3B', 0.22, 4.0,
[
{ type: 'elementalDamage', value: 15, desc: '+15% Lightning damage' },
{ type: 'castingSpeed', value: 15, desc: '+15% casting speed' },
],
'Lightning spells chain to 2 additional targets',
[{ type: 'chain', value: 2 }],
{ shield: 800, shieldRegen: 20, barrier: 0.05, barrierRegen: 0.01 },
),
120: mk(120, '', ['frost'], '#A8D8EA', 0.28, 4.25,
[
{ type: 'elementalDamage', value: 15, desc: '+15% Frost damage' },
{ type: 'castingSpeed', value: 10, desc: '+10% casting speed' },
],
'Frost spells freeze enemies, reducing their attack speed by 20%',
[{ type: 'freeze', value: 0.2 }],
{ shield: 900, shieldRegen: 22, barrier: 0.08, barrierRegen: 0.02 },
),
130: mk(130, '', ['metal', 'fire', 'earth'], '#8B2500', 0.32, 4.5,
[
{ type: 'elementalDamage', value: 15, desc: '+15% BlackFlame damage' },
{ type: 'rawDamage', value: 10, desc: '+10% raw damage' },
],
'Multi-element BlackFlame spells apply a curse that reduces enemy resistances by 15%',
[{ type: 'curse', value: 0.15 }, { type: 'burn', value: 0.15 }, { type: 'armor_pierce', value: 0.2 }],
{ shield: 1000, shieldRegen: 25, healthRegen: 5, healthRegenIsPercent: true },
),
140: mk(140, '', ['sand', 'earth', 'water'], '#FFAA33', 0.25, 4.75,
[
{ type: 'elementalDamage', value: 15, desc: '+15% Radiant Earth damage' },
{ type: 'maxMana', value: 200, desc: '+200 max mana' },
],
'Radiant Earth spells blind enemies, reducing their accuracy and damage by 15%',
[{ type: 'blind', value: 0.15 }, { type: 'armor_pierce', value: 0.1 }],
{ barrier: 0.12, barrierRegen: 0.03, healthRegen: 6, healthRegenIsPercent: true },
),
150: mk(150, '', ['lightning', 'fire', 'air'], '#6B8E23', 0.28, 5.0,
[
{ type: 'elementalDamage', value: 15, desc: '+15% Storm Lightning damage' },
{ type: 'castingSpeed', value: 15, desc: '+15% casting speed' },
],
'Storm Lightning spells corrode armor and spread chain lightning in swarm rooms',
[{ type: 'chain', value: 2 }, { type: 'cast_speed', value: 0.1 }, { type: 'burn', value: 0.1 }],
{ shield: 1100, shieldRegen: 28, barrier: 0.05, barrierRegen: 0.01 },
),
160: mk(160, '', ['shadowglass'], '#2C2C54', 0.33, 5.25,
[
{ type: 'elementalDamage', value: 20, desc: '+20% Shadow Glass damage' },
{ type: 'critDamage', value: 15, desc: '+15% crit damage' },
],
'Shadow Glass spells create piercing spikes ignoring 30% armor',
[{ type: 'armor_pierce', value: 0.3 }, { type: 'pierce', value: 0.25 }],
{ shield: 1200, shieldRegen: 30, healthRegen: 5, healthRegenIsPercent: true },
),
};
// ═══════════════════════════════════════════════════════════════════════════════
// TIER 3: Exotic Elements (Floors 170240) — 6 exotics + 2 convergence guards
// Original: Crystal, Stellar, Void (floors 170-200)
// New: Soul, Time, Plasma + a convergence guardian
// ═══════════════════════════════════════════════════════════════════════════════
const TIER3: Record<number, GuardianDef> = {
170: mk(170, '', ['crystal'], '#85C1E9', 0.35, 5.5,
[
{ type: 'elementalDamage', value: 20, desc: '+20% Crystal damage' },
{ type: 'maxMana', value: 300, desc: '+300 max mana' },
],
'Crystal spells reflect 15% damage back to attackers',
[{ type: 'reflect', value: 0.15 }],
{ shield: 2000, shieldRegen: 50, barrier: 0.10, barrierRegen: 0.03 },
),
180: mk(180, '', ['stellar'], '#F0E68C', 0.30, 6.0,
[
{ type: 'elementalDamage', value: 25, desc: '+25% Stellar damage' },
{ type: 'insightGain', value: 20, desc: '+20% insight gain' },
],
'Stellar spells deal +30% damage at night',
[{ type: 'night_bonus', value: 0.3 }],
{ barrier: 0.15, barrierRegen: 0.04, healthRegen: 8, healthRegenIsPercent: true },
),
190: mk(190, '', ['void'], '#4A235A', 0.35, 6.5,
[
{ type: 'elementalDamage', value: 25, desc: '+25% Void damage' },
{ type: 'rawDamage', value: 15, desc: '+15% raw damage' },
],
'Void spells ignore 40% of all resistances',
[{ type: 'resist_ignore', value: 0.4 }],
{ shield: 2500, shieldRegen: 60, barrier: 0.10, barrierRegen: 0.02, healthRegen: 6, healthRegenIsPercent: true },
),
200: mk(200, '', ['crystal', 'stellar', 'void'], '#E8D5F5', 0.35, 7.0,
[
{ type: 'elementalDamage', value: 30, desc: '+30% Exotic damage' },
{ type: 'maxMana', value: 400, desc: '+400 max mana' },
],
'Exotic convergence: Crystal/Stellar/Void spells bypass all defenses and shields',
[{ type: 'defense_pierce', value: 0.3 }, { type: 'resist_ignore', value: 0.2 }, { type: 'reflect', value: 0.1 }],
{ shield: 2800, shieldRegen: 55, barrier: 0.08, barrierRegen: 0.02 },
),
210: mk(210, '', ['soul', 'time', 'plasma'], '#C5B99A', 0.32, 7.5,
[
{ type: 'elementalDamage', value: 25, desc: '+25% Astral damage' },
{ type: 'castingSpeed', value: 20, desc: '+20% casting speed' },
],
'Astral convergence: Soul/Time/Plasma spells slow and pierce all defenses',
[{ type: 'defense_pierce', value: 0.3 }, { type: 'slow', value: 0.2 }, { type: 'chain', value: 2 }],
{ barrier: 0.15, barrierRegen: 0.04, healthRegen: 9, healthRegenIsPercent: true },
),
220: mk(220, '', ['plasma'], '#FF6B9D', 0.28, 8.0,
[
{ type: 'elementalDamage', value: 25, desc: '+25% Plasma damage' },
{ type: 'manaRegen', value: 2.5, desc: '+2.5 mana regen' },
],
'Plasma spells chain to 3 targets with 30% damage each',
[{ type: 'chain', value: 3 }, { type: 'burn', value: 0.1 }],
{ shield: 3200, shieldRegen: 70, barrier: 0.10, barrierRegen: 0.02 },
),
230: mk(230, '', ['crystal', 'stellar', 'void'], '#B39DDB', 0.40, 8.5,
[
{ type: 'elementalDamage', value: 25, desc: '+25% Exotic damage' },
{ type: 'insightGain', value: 20, desc: '+20% insight gain' },
],
'Primordial gaze: Crystal/Stellar/Void spells gain +20% effectiveness',
[{ type: 'reflect', value: 0.1 }, { type: 'resist_ignore', value: 0.15 }],
{ shield: 3500, shieldRegen: 90, barrier: 0.12, barrierRegen: 0.03 },
),
240: mk(240, '', ['soul', 'time', 'plasma'], '#D5A0E0', 0.42, 9.0,
[
{ type: 'elementalDamage', value: 25, desc: '+25% Astral damage' },
{ type: 'spellEfficiency', value: 15, desc: '+15% spell efficiency' },
],
'Astral convergence: Soul/Time/Plasma spells gain +20% effectiveness',
[{ type: 'defense_pierce', value: 0.2 }, { type: 'chain', value: 1 }],
{ shield: 3800, shieldRegen: 100, barrier: 0.14, barrierRegen: 0.03, healthRegen: 12, healthRegenIsPercent: true },
),
};
// ═══════════════════════════════════════════════════════════════════════════════
// COMBINED STATIC GUARDIANS
// ═══════════════════════════════════════════════════════════════════════════════
const STATIC_GUARDIANS: Record<number, GuardianDef> = {
...TIER1,
...TIER2,
...TIER3,
};
export { STATIC_GUARDIANS, TIER1, TIER2, TIER3 };