/** * Auto-mode profiles: 50 specialisations in 5 families. * Used by player auto mode and bot zoos (bots still use legacy random fast/slow/balanced). * Params: spendThreshold (multiplier on cost to allow spend), upgradeChance (0–1), sellChance (0–1, bots only). */ /** @typedef {{ id: number, familyId: number, spendThreshold: number, upgradeChance: number, sellChance: number, labelKey: string, prioritiesKey: string, risksKey: string }} AutoModeProfile */ /** Families 1–5: Conservateurs, Éleveurs, Commerçants, Expansionnistes, Scientifiques. */ export const AUTO_MODE_FAMILY_IDS = [1, 2, 3, 4, 5]; /** Profile id range per family: 1–10, 11–20, 21–30, 31–40, 41–50. */ const FAMILY_RANGES = [[1, 10], [11, 20], [21, 30], [31, 40], [41, 50]]; /** Legacy profile name to default profile id (balanced=25, fast=33, slow=7). */ export const LEGACY_PROFILE_TO_ID = { balanced: 25, fast: 33, slow: 7 }; /** * All 50 profiles. Params tuned per family. * @type {AutoModeProfile[]} */ const PROFILES = []; function buildProfiles() { for (let familyId = 1; familyId <= 5; familyId++) { const [minId, maxId] = FAMILY_RANGES[familyId - 1]; for (let id = minId; id <= maxId; id++) { const i = (id - minId) / (maxId - minId); const spendThreshold = 0.5 + i * 2; const upgradeChance = 0.05 + i * 0.5; const sellChance = familyId === 2 ? 0.02 + i * 0.08 : familyId === 3 ? 0.08 + i * 0.12 : 0.02 + i * 0.1; PROFILES.push({ id, familyId, spendThreshold: Math.round(spendThreshold * 100) / 100, upgradeChance: Math.round(upgradeChance * 100) / 100, sellChance: Math.round(sellChance * 100) / 100, labelKey: `autoProfile.specialisation.${id}`, prioritiesKey: `autoProfile.priorities.${id}`, risksKey: `autoProfile.risks.${id}`, }); } } } buildProfiles(); /** * Resolve effective profile id from state (autoModeProfileId or legacy autoModeProfile). * @param {{ autoModeProfileId?: number, autoModeProfile?: string }} state * @returns {number} */ export function getEffectiveProfileId(state) { const id = state.autoModeProfileId; if (id !== null && id !== undefined && id >= 1 && id <= 50) return id; const legacy = state.autoModeProfile; if (legacy === "fast" || legacy === "slow" || legacy === "balanced") return LEGACY_PROFILE_TO_ID[legacy]; return LEGACY_PROFILE_TO_ID.balanced; } /** * Get profile by id (1–50). Returns default balanced params if not found. * @param {number} profileId * @returns {AutoModeProfile} */ export function getProfileById(profileId) { const p = PROFILES.find((x) => x.id === profileId); if (p) return p; const def = PROFILES.find((x) => x.id === 25); return def ?? PROFILES[0]; } /** * Params for use in bot/player auto logic. * @param {number} profileId * @returns {{ spendThreshold: number, upgradeChance: number, sellChance: number }} */ export function getProfileParams(profileId) { const p = getProfileById(profileId); return { spendThreshold: p.spendThreshold, upgradeChance: p.upgradeChance, sellChance: p.sellChance, }; } /** * All profiles in the given family (1–5). * @param {number} familyId * @returns {AutoModeProfile[]} */ export function getProfilesByFamily(familyId) { return PROFILES.filter((p) => p.familyId === familyId); } /** All 50 profiles. * @returns {AutoModeProfile[]} */ export function getAllProfiles() { return [...PROFILES]; } export { FAMILY_RANGES };