Store architecture, methods, properties, and types for the MobX Clicker Game Engine.
For setup instructions see Quickstart. For JSON schemas see Data Contracts.
The engine consists of interconnected MobX stores:
RootStore
├── GameStore - game loop, click action
├── ResourcesStore - energy, output, reputation, money
├── WorkersStore - hiring, passive production
├── OperationsStore - conduct/claim, cooldowns
├── UpgradesStore - purchase upgrades, multipliers
├── LevelStore - progression, unlocking
├── AchievementsStore - unlock conditions, rewards
├── PrestigeStore - BP calculation, reset mechanics
├── CodexStore - article unlocking
├── SyncStore - save/load, localStorage
├── ConfigStore - game constants
├── ToastStore - notifications
└── ConfirmationStore - modal dialogs
Workers → Energy → Click → Output → Operations → Reputation → Money → Workers
- Energy: Consumed by clicks, produced by workers
- Output: Gained from clicks, spent on operations
- Reputation: Earned from operations, generates money over time
- Money: Used for workers and upgrades
- Runs in 1-second intervals when
game.start()is called - Each round: workers produce resources, reputation generates money
- Auto-saves every 5 seconds (configurable)
- Handles offline progress calculation
Your dataUrls object must contain exactly these keys:
workers: Team members that generate resourceslevels: Progression zones with unlock requirementsoperations: Actions that consume resources and grant rewardsupgrades: Permanent improvements with multiplier effectsachievements: Milestone rewards with unlock conditionsarticles: Lore content unlocked through operationsprestigeUpgrades: Meta-progression purchased with prestige points
Creates and initializes the game engine.
Parameters:
options.dataUrls: Object mapping required data URLs
Returns: RootStore instance with all child stores
The main container for all game stores.
dataReady: boolean- True when all JSON data has loaded successfullyoptions: RootStoreOptions- Configuration passed tocreateEngine()dataSource: EngineDataSource- Handles fetching JSON data
All child stores are accessible as properties:
game,resources,workers,operations,upgrades,levelachievements,prestige,codex,sync,config,toast,confirmation
Controls the main game loop and core click action.
Starts the game loop (1-second intervals).
Stops the game loop and saves progress.
Stops the game and resets all progress.
Executes the main click action: spend energy to gain output.
running: boolean- Whether game loop is activeenergyCost: number- Energy cost for next clickoutputGain: number- Output gained from next click
Manages the four core resources and their production rates.
Adds resources safely (validates non-negative).
Attempts to spend resources. Returns true if successful.
Spends multiple resources atomically. Returns true if all costs were paid.
energy: number- Current energy amountoutput: number- Current output amountreputation: number- Current reputation amountmoney: number- Current money amountenergyPerRound: number- Energy produced each game roundoutputPerRound: number- Output produced each game roundmoneyPerRound: number- Money produced each game round
Handles hiring workers and calculating production bonuses.
Hires a worker if you have enough money. Throws error if insufficient funds.
Calculates the cost to hire the next worker of this type.
workers: Worker[]- All available worker definitions (from JSON)hiredWorkers: Record<string, number>- Count of each worker type hiredunlockedWorkers: Worker[]- Workers that meet unlock conditionstotalWorkers: number- Total count of all hired workerstotalEnergyProduction: number- Energy multiplier from all workerstotalOutputProduction: number- Output multiplier from all workers
Manages operations (research actions) with duration and cooldown mechanics.
Starts an operation if you can afford it. Returns duration in seconds for animations.
Claims rewards from a completed operation.
Combined method: conducts if idle, claims if ready. Returns duration or 0.
Checks if you have enough resources to start an operation.
operations: Operation[]- All available operations (from JSON)availableOperations: Operation[]- Operations available at current leveloperationsFinished: Record<string, number>- Completion count per operationtotalOperationsCompleted: number- Total operations completed this runoperationsInProgress: Set<string>- Operations currently runningoperationsClaimable: Set<string>- Operations ready to claimoperationsInCooldown: Set<string>- Operations in cooldown period
Handles purchasing permanent upgrades that provide multiplier bonuses.
Purchases the next level of an upgrade. Throws error if can't afford or maxed out.
Checks if upgrade can be purchased (affordable, unlocked, not maxed).
upgrades: Upgrade[]- All available upgrades (from JSON)unlockedUpgrades: Record<string, number>- Current level of each upgradevisibleUpgrades: Upgrade[]- Upgrades that should show in UImultipliers: MultipliersMap- Combined multiplier effects from all upgrades
Manages progression through different game levels/zones.
Changes to a different unlocked level. Throws error if level not unlocked.
levels: Level[]- All level definitions (from JSON)unlockedLevels: Level[]- Levels that meet unlock conditionscurrentLevel: number- Index of currently selected levelmaxLevelReached: number- Highest level ever unlockedcurrentLevelConfig: Level- Configuration for current level
Tracks achievement unlock conditions and provides rewards.
achievements: Achievement[]- All achievement definitions (from JSON)unlockedAchievements: Set<string>- Achievement IDs that have been earnedmultipliers: MultipliersMap- Multiplier bonuses from unlocked achievements- Stats tracking properties:
totalResources,totalWorkers,operationsCompleted, etc.
Handles meta-progression through prestige resets.
Performs prestige reset: awards points, resets progress, applies bonuses.
Purchases a prestige upgrade with breakthrough points.
Calculates breakthrough points that would be earned from prestiging now.
Returns true if you meet the minimum requirements to prestige.
upgrades: PrestigeUpgrade[]- Available prestige upgrades (from JSON)points: number- Spendable breakthrough pointslifetimePoints: number- Total BP ever earnedprestigeCount: number- Number of prestiges completedpurchasedUpgrades: Record<string, number>- Levels of owned prestige upgrades
Manages unlockable lore articles.
Unlocks an article and shows a toast notification.
articles: Article[]- All article definitions (from JSON)unlockedArticles: Set<string>- Article IDs that have been unlocked
Handles save/load operations with localStorage.
Saves current game state to localStorage (generator function, use with flowResult).
Loads game state from localStorage. Returns save timestamp or undefined.
Resets all stores to initial state and clears localStorage.
state: "idle" | "saving" | "loading" | "error"- Current operation stateisDirty: boolean- Whether unsaved changes existlastSave: number- Timestamp of last successful save
Shows temporary notification messages.
Displays a toast notification with auto-dismiss.
Manually dismisses a specific toast.
Convenience method for achievement notifications.
Convenience method for article unlock notifications.
toasts: Map<number, ToastMessage>- Currently displayed toasts
Handles modal confirmation dialogs.
Shows a confirmation dialog and returns user's choice.
Resolves the current confirmation dialog.
currentConfirmation: ConfirmationRequest | null- Active confirmation dialog
const RESOURCES = ["energy", "output", "reputation", "money"] as const
type Resource = typeof RESOURCES[number]const RARITY = ["common", "uncommon", "rare", "epic", "legendary"] as const
type Rarity = typeof RARITY[number]type GainMultiplier
= | "energyGain"
| "outputGain"
| "operationCostReduction"
| "reputationGain"
| "moneyGain"
| "workersEfficiency"
| "operationDurationReduction"
| "offlineEfficiency"
| "workerCostReduction"The engine saves data in this format:
interface GameSaveSnapshot {
version: string
timestamp: number
resources: {
energy: number
output: number
reputation: number
money: number
}
workers: {
hiredWorkers: Record<string, number>
}
operations: {
operationsFinished: Record<string, number>
operationsProgress: Record<string, { claimableAt: number, cooldownTill: number }>
activeBonuses: Array<{ bonus: Bonus, expiresAt: number }>
}
// ... other store snapshots
}The engine automatically calculates offline progress when loading saves:
- Compares
timestampin save data to current time - Simulates resource production for elapsed time (capped at 8 hours)
- Applies 50% efficiency multiplier to offline gains
- Does not progress operations or other active mechanics
You can extend the engine by wrapping stores:
import { createEngine } from "@miskamyasa/mobx-clicker-game-engine"
class ExtendedGameStore {
constructor(private baseStore: GameStore) {
makeObservable(this)
}
superClick() {
for (let i = 0; i < 10; i++) {
this.baseStore.click()
}
}
get running() { return this.baseStore.running }
start() { this.baseStore.start() }
}
const baseEngine = createEngine(options)
const engine = {
...baseEngine,
game: new ExtendedGameStore(baseEngine.game)
}Modify game balance by accessing ConfigStore:
engine.config.baseEnergyCost = 10 // Higher click costs
engine.config.localSaveInterval = 10000 // Save every 10 seconds
engine.config.operationScaleFactor.rare = 2.0 // More expensive rare operations