piclets / src /lib /services /unlockLevels.ts
Fraser's picture
battling
74f8c2c
raw
history blame
4.09 kB
/**
* Utility functions for calculating unlock levels for moves and abilities
*/
import type { BattleMove } from '$lib/db/schema';
import type { SpecialAbility } from '$lib/battle-engine/types';
/**
* Calculate unlock level for a move based on its power and characteristics
* More powerful moves unlock later, with some randomness
*/
export function calculateMoveUnlockLevel(move: BattleMove, moveIndex: number): number {
// Base unlock level based on power
let baseLevel = 1;
if (move.power === 0) {
// Status/support moves - unlock early to mid game
baseLevel = Math.floor(Math.random() * 20) + 5; // Level 5-25
} else if (move.power <= 40) {
// Weak moves - unlock early
baseLevel = Math.floor(Math.random() * 15) + 1; // Level 1-15
} else if (move.power <= 60) {
// Medium moves - unlock early to mid
baseLevel = Math.floor(Math.random() * 25) + 10; // Level 10-35
} else if (move.power <= 80) {
// Strong moves - unlock mid to late
baseLevel = Math.floor(Math.random() * 30) + 25; // Level 25-55
} else {
// Very powerful moves - unlock late
baseLevel = Math.floor(Math.random() * 25) + 40; // Level 40-65
}
// Adjust based on move position (later moves tend to be more powerful)
const positionBonus = moveIndex * 5; // 0, 5, 10, 15 for moves 1-4
baseLevel += positionBonus;
// Ensure first move is always available at level 1
if (moveIndex === 0) {
baseLevel = 1;
}
// Cap at level 80 (everything must be unlocked by then)
return Math.min(baseLevel, 80);
}
/**
* Calculate unlock level for special ability based on its power and effects
*/
export function calculateSpecialAbilityUnlockLevel(ability: SpecialAbility): number {
// Base level based on ability impact
let baseLevel = 15; // Default mid-level unlock
// Analyze ability effects to determine power level
const effects = ability.effects || [];
let powerScore = 0;
for (const effect of effects) {
switch (effect.type) {
case 'damage':
powerScore += effect.amount === 'strong' ? 3 : effect.amount === 'normal' ? 2 : 1;
break;
case 'heal':
powerScore += effect.amount === 'large' ? 3 : effect.amount === 'medium' ? 2 : 1;
break;
case 'modifyStats':
// Stat modifications are powerful
powerScore += 2;
break;
case 'applyStatus':
powerScore += 2;
break;
case 'removeStatus':
powerScore += 1;
break;
case 'manipulatePP':
powerScore += 1;
break;
default:
powerScore += 1;
}
}
// Convert power score to unlock level
if (powerScore <= 2) {
baseLevel = Math.floor(Math.random() * 20) + 10; // Level 10-30
} else if (powerScore <= 4) {
baseLevel = Math.floor(Math.random() * 25) + 20; // Level 20-45
} else if (powerScore <= 6) {
baseLevel = Math.floor(Math.random() * 25) + 30; // Level 30-55
} else {
baseLevel = Math.floor(Math.random() * 25) + 40; // Level 40-65
}
// Cap at level 80
return Math.min(baseLevel, 80);
}
/**
* Get all unlocked moves for a Piclet at a given level
*/
export function getUnlockedMoves(moves: BattleMove[], currentLevel: number): BattleMove[] {
return moves.filter(move => move.unlockLevel <= currentLevel);
}
/**
* Check if special ability is unlocked at given level
*/
export function isSpecialAbilityUnlocked(unlockLevel: number, currentLevel: number): boolean {
return currentLevel >= unlockLevel;
}
/**
* Generate unlock levels for a new Piclet's moves and ability
* This should be called when a Piclet is first generated
*/
export function generateUnlockLevels(moves: BattleMove[], specialAbility: SpecialAbility): {
movesWithUnlocks: BattleMove[];
abilityUnlockLevel: number;
} {
const movesWithUnlocks = moves.map((move, index) => ({
...move,
unlockLevel: calculateMoveUnlockLevel(move, index)
}));
const abilityUnlockLevel = calculateSpecialAbilityUnlockLevel(specialAbility);
return {
movesWithUnlocks,
abilityUnlockLevel
};
}