Files
deepseek ac00687480 Arcane Tycoon — Heroes & Magic theme park tycoon game
Complete browser game inspired by OpenRCT2 with fantasy twist:
- Custom roller coaster designer with physics-based ratings + on-ride POV
- 10 animated rides, 7 shops, 16 scenery items, path network & guest AI
- Heroes guild vs monster invasions (5 classes, XP/gear/bosses)
- Magic spell system (8 spells), research tree, economy/marketing/loans
- Day-night cycle, weather, park rating, awards, 4 scenarios
- Save/load slots + autosave, procedural WebAudio SFX/music
- Isometric canvas renderer, minimap, diagnostics overlay
- Test suites: smoke(13), linkcheck, inputcheck, framecheck, rendercheck, flow
2026-08-23 06:59:21 +00:00

33 lines
1.0 KiB
JavaScript

// ============ research.js — unlock tree ============
import { UNLOCKS, RESEARCH_TRACKS } from '../core/config.js';
export function isUnlocked(state, key) {
if (state.sandbox) return true;
return state.research.unlocked.includes(key);
}
export function canBuy(state, u) {
if (isUnlocked(state, u.key)) return { ok: false, why: 'owned' };
if (state.research.rp >= u.rp) return { ok: true };
return { ok: false, why: 'rp' };
}
export function buyUnlock(state, key) {
const u = UNLOCKS.find(u => u.key === key);
if (!u) return false;
const chk = canBuy(state, u);
if (!chk.ok) return false;
state.research.rp -= u.rp;
state.research.spentTotal += u.rp;
state.research.unlocked.push(key);
state.toasts.push({ kind: 'good', title: 'Research complete!', text: `${u.label} is now available to build.` });
return true;
}
export function unlocksByTrack() {
const out = {};
for (const t of Object.keys(RESEARCH_TRACKS)) out[t] = [];
for (const u of UNLOCKS) (out[u.track] || (out[u.track] = [])).push(u);
return out;
}