import { db } from './index'; import type { Encounter, PicletInstance } from './schema'; import { EncounterType } from './schema'; import { getOrCreateGameState, markEncountersRefreshed } from './gameState'; import { getCaughtPiclets } from './piclets'; // Configuration const ENCOUNTER_REFRESH_HOURS = 2; const MIN_WILD_ENCOUNTERS = 2; const MAX_WILD_ENCOUNTERS = 4; export class EncounterService { // Check if encounters should be refreshed static async shouldRefreshEncounters(): Promise { const state = await getOrCreateGameState(); const hoursSinceRefresh = (Date.now() - state.lastEncounterRefresh.getTime()) / (1000 * 60 * 60); return hoursSinceRefresh >= ENCOUNTER_REFRESH_HOURS; } // Force encounter refresh static async forceEncounterRefresh(): Promise { await db.encounters.clear(); await markEncountersRefreshed(); } // Get current encounters static async getCurrentEncounters(): Promise { return await db.encounters .orderBy('createdAt') .reverse() .toArray(); } // Clear all encounters static async clearEncounters(): Promise { await db.encounters.clear(); } // Generate new encounters - simplified to only wild battles static async generateEncounters(): Promise { const encounters: Omit[] = []; // Check if player has any Piclets const caughtPiclets = await getCaughtPiclets(); if (caughtPiclets.length === 0) { // No Piclets yet - show empty state, they need to scan first console.log('Player has no caught piclets - returning empty encounters'); await db.encounters.clear(); await markEncountersRefreshed(); return []; } // Player has Piclets - generate wild battle encounters console.log('Generating wild battle encounters'); const wildEncounters = await this.generateWildBattleEncounters(); encounters.push(...wildEncounters); // Clear existing encounters and add new ones await db.encounters.clear(); for (const encounter of encounters) { await db.encounters.add(encounter); } await markEncountersRefreshed(); return await this.getCurrentEncounters(); } // Generate wild battle encounters using existing caught Piclets private static async generateWildBattleEncounters(): Promise[]> { const encounters: Omit[] = []; // Get all caught piclets to use as potential opponents const caughtPiclets = await getCaughtPiclets(); if (caughtPiclets.length === 0) { return encounters; } // Generate 2-4 random wild encounters const numEncounters = Math.floor(Math.random() * (MAX_WILD_ENCOUNTERS - MIN_WILD_ENCOUNTERS + 1)) + MIN_WILD_ENCOUNTERS; for (let i = 0; i < numEncounters; i++) { // Pick a random Piclet from caught ones to use as opponent const randomPiclet = caughtPiclets[Math.floor(Math.random() * caughtPiclets.length)]; // Use the piclet's name for display const displayName = randomPiclet.typeId.replace(/-/g, ' ').replace(/\b\w/g, l => l.toUpperCase()); const encounter: Omit = { type: EncounterType.WILD_PICLET, title: `Wild ${displayName}`, description: `A wild ${displayName} appears! Ready for battle?`, picletInstanceId: randomPiclet.id, picletTypeId: randomPiclet.typeId, enemyLevel: 5, // Simplified - no level variance needed createdAt: new Date() }; encounters.push(encounter); } return encounters; } // Get a specific encounter by ID static async getEncounter(id: number): Promise { return await db.encounters.get(id); } // Delete an encounter (after it's been completed) static async deleteEncounter(id: number): Promise { await db.encounters.delete(id); } }