cd /news/artificial-intelligence/the-master-s-shadow · home topics artificial-intelligence article
[ARTICLE · art-51183] src=discuss.huggingface.co ↗ pub= topic=artificial-intelligence verified=true sentiment=· neutral

The Master's Shadow

Master Malacor in 'The Master's Shadow' is a rule-bound autonomous AI using Ant-Colony Optimisation (ACO) to pursue players, with deterministic behavior governed by pheromone-based pathfinding and dynamic strategies based on player actions and trace levels.

read14 min views1 publishedJul 8, 2026
The Master's Shadow
Image: Discuss (auto-discovered)

The Master AI — Ant-Colony Optimisation

Master Malacor is not a game-over timer or an omniscient threat. He is a rule-bound autonomous agent running on the same deterministic Clockwork Dark engine as the player, subject to the same world friction: every action is a legal engine call (move_to_node

, resolve_skill_check

, craft_item

, forage/rest), governed so he cannot cheat or hallucinate outcomes. He spends Food, Energy and Mana, is slowed by hazardous nodes, and can be outlasted if he burns resources recklessly. His edge is better starting knowledge and stats; the player’s counter is that this knowledge is imperfect and corruptible.

The ACO model

Ant-Colony Optimisation (ACO) is a swarm metaheuristic: artificial ants lay pheromone on good paths, pheromone evaporates to allow adaptation, and each next-step choice combines pheromone (τ, weight alpha

) with a heuristic (η, weight beta ) via seeded roulette-wheel selection. ACO gives the Master and crowds a memory of good routes that A* alone lacks, and adapts naturally to changing traps, trace and reputation.

Hex adaptation: pheromone is stored per directed edge between cube-coordinate hexes (the 6 neighbours). Heuristic η = 1 / movement_cost

, where movement_cost

already folds in terrain, traps, trace and reputation. All random choices are seeded with game_seed + state_hash

, so ACO is fully deterministic. See World & Flow Fields for the hybrid: ACO is the strategic layer that emits a temporary flow field, blended (weight ~0.7) with the global flow field; flow fields + local steering handle cheap real-time crowd movement.

Recommended parameters (per context): Context | ants | iters | alpha | beta | evap | Q | | Master Bloodhound pursuit | 15 | 25 | 1.2 | 2.5 | 0.08 | 1.0 | | Master Architect planning | 25 | 40 | 1.0 | 2.0 | 0.12 | 0.8 | | Loyalist patrol swarms | 10 | 15 | 0.8 | 3.0 | 0.15 | 0.6 | | Rebel groups | 12 | 20 | 1.0 | 1.8 | 0.10 | 0.7 | | Monster swarms | 8 | 12 | 1.5 | 1.5 | 0.20 | 0.5 |

Tracking vectors

The Master maintains an internal world model from state flags, imperfect and degrading with time/distance:

Sympathy Trace (primary). Black spells (Drain Life, Shadow Step, Bind, Summon Familiar), heavy Black ingredients (Nightshade, Mandrake Root, Sympathy Ash) and failed Black alchemy add trace. Trace decays ~1–3 per node moved (faster with White magic, rain, Shimmering Lake). Bands drive behaviour:

Trace | Master behaviour | Player-visible | Counters | | Low (0–20) | Normal patrol / Architect | none | — | | Med (21–50) | Bloodhound chance ↑ | raven cries, scorched nodes | Grey masking, Decoy, weather | | High (51–80) | Locks onto path, faster | dead NPCs, stripped nodes on trail | White trace-purge, false trails | | Critical (81+) | Aggressive pursuit, trackers | projection appears, Loyalists converge | Shadow Cloak + high Grey, sabotage |

Last-known position + path history (from Raven Familiar, Loyalist Trackers, direct sight). Grey magic — Invisibility, Muffle, Decoy, high Concealment, Shadow Cloak — breaks or falsifies it.

Reputation & world flags (secondary): Loyalist reputation drives patrol/trap density; bribed NPCs may feed him false intel; helping/harming key characters sets persistent readable flags.

Pursuit strategies

The Master switches mode dynamically on trace, resources, last-known position, and predicted intent:

Bloodhound (reactive). Trigger: medium+ trace, recent sighting, or obvious Black magic. Runs the player’s exact recent path, spends Mana on Haste, strips resources behind them, prioritises closing distance. Countered by Haste, false trails, weather (Sudden Storm doubles all costs), or leading him into monster nodes. Architect (predictive). Trigger: low trace but the player is heading to a chokepoint (Boundary Gate, Rebel Encampment, Smuggler’s Cove) or is patterned. Diverges ahead, lays snares, bribes guards (Gorn, Vex, Captain Thorne), sets ambushes. Countered by breaking patterns, varying routes, counter-intel (Divination Mirror), or sabotaging his forward assets. Opportunistic / Idle. Casts about the strongest scent when neither loud nor cleanly predictable; Idle covers forage/rest.

He can switch mid-chase if trace spikes or he loses the trail.

Learning: memory decay & protection

The Master keeps a separate pheromone map of the player (observed spell chains, escape routes, alchemy habits, trap responses) that steers strategy, trap placement and spell priority. It is a learning but fallible memory that decays under pressure, so the player must keep adapting.

Decay base_rate = 0.06

(slower than player-side magical pheromone; he is disciplined). Multipliers: Ritual Clock 1.0 + stage*0.35

; player trace 1.0 + trace/120

; low Mana ×1.3; recent failed counter ×1.2; heavy recent Grey ×1.4; strong Water-Spirit reputation ×1.15; time-since-observed up to ×1.8. Capped at 0.28; floor 0.005.
**Protection** (else Grey trivialises him): Ritual-Clock *hardening* (`1.0 − stage*0.12`

, up to ~36% slower late), extra ×0.7 on recently-used patterns, importance weighting, resource-based resilience (stronger >60% Mana), and active tools — Trace-Burn, Clarity Projection, Pheromone Anchor, surveillance agents. Targeted Memory Fog he may detect and reinforce against, a cat-and-mouse mini-game. Player disruptor — Memory Fog (Grey). Applies a decay boost 0.18 + grey_level*0.03

(×1.5 targeted) to his player-model over 4–8 nodes (10–12 with alchemy); ~+0.5 clock at stage ≥2; recent-use penalty ×0.5 within 8 turns to stop spam. Net arc: early memory strong and teaching; mid older observations erode, he can be re-fooled; late desperation (clock) both accelerates his forgetting and hardens his prized recent counters, so he grows more brute-force and predictable — windows for skilled play.

The unified ACO loop (player + Master)

ACO also drives spell-sequence selection for both sides. Each “ant” runs a short simulated cast chain (≤4 spells); transition probability P = τ^alpha · η^beta · clock_pressure^gamma · reputation_mod^delta

, normalised (uniform fallback if none viable). The heuristic scores Mana efficiency, trace delta (heavy penalty for Black when trace >60–70; small reward for controlled Black when low), affinity match, alchemy synergy (potions as temporary pheromone boosters), and tactical context (near-traps favours Haste/Shadow Step/Decoy; low health favours Mend/Ward; density favours Bind/Sleep). Successful chains deposit pheromone, so tactics that work become reliable — but also predictable.

Ritual-Clock tuning ramps parameters by stage: alpha 1.0→1.5, beta 2.5→3.5, evaporation 0.10→0.30, with rising Black penalty and survival bias. The Master’s loop uses higher alpha (1.4–1.6, leans on learned patterns), aggressive elitist reinforcement, and grows more efficient and less exploratory as the clock advances.

Phase carry-over. Phase 1 choices seed Phase 2 pheromone: reputation flags become initial pheromone biases; Grey progress → stronger stealth-pair pheromone and better decoys; heavy Black → higher starting trace; ritual sabotage → lower starting clock and persistent low-cost corridors.

In the build

The design is realised, though the shipped C++ core is a deliberately lean, deterministic subset of the sprawling design above — not the full multi-map ACO/LLM stack.

src/ai/master_ai.hpp

/ master_ai.cpp

MasterBrain

. A single scent (pheromone) map unordered_map<Hex,float> with observe_player

(deposit kDeposit=1.0 on sighting), decay

(evaporation kEvap=0.15 , prune <0.02), and strongest_scent

with a deterministic hex-order tiebreak. `decide()`

implements the strategy FSM: forage if `food<25`

or energy<30

; else Bloodhound if trace≥50

or seen within 1 turn, Architect (interception via a_star

3 hexes ahead toward the gate) if trace<30

with a fix, else Opportunistic on strongest scent — then steps via a flow field to the goal. poison_scent(h, amt, steal_fix)

is the Nyxari false-trail hook that can steal his fix. MasterStrategy

enum lives in src/core/types.hpp : Idle, Opportunistic, Bloodhound, Architect

. src/ai/pursuit_sim.cpp

simulate_pursuit

proves the Master is rule-bound and can win or lose: a seeded headless chase (greedy player vs a Master IAgent

), used by tests and balance sweeps. agent_engine/master_agent.py

— the pluggable external-agent bridge. The Master can be driven by an LLM via LM Studio (lmstudio_client.py

, OpenAI-style tool calling, /no_think

), choosing among only legal moves through a single act(action, index, say)

tool — he still cannot cheat. It uses a loaded-only model (never force-loads) and falls back to a deterministic bloodhound heuristic()

when no model is resident, the call fails, or MS_AGENT_HEURISTIC=1

. This is the “CosySim” agent seam referenced in project history.

Note: sources differ on decay/trace constants vs. the build. Design docs specify player-model decay base=0.06

, evaporation ~0.08–0.30, and trace bands with a slow 1–3/node fade; the shipped MasterBrain

uses a single scent map with fixed kEvap=0.15

, kDeposit=1.0

, and integer thresholds kTraceBloodhound=50

/ kTraceArchitect=30

. The build values are canonical for the current implementation; the finer per-mille/per-affinity model and the separate player-model pheromone map are design-only / not yet in the C++ core.

Note: the design describes multiple pheromone maps, full ACO spell-sequence search, and Phase-3 action scoring (stabilize_flow / pressure_bond / deploy_distortion / counter_disruption). The GDD claims these; the current C++ MasterBrain

implements movement/pursuit ACO only — spell-chain ACO and the multi-map planner remain design-level. World, Flow Fields & Crowd Simulation

Phase 2 (The Forest Pursuit) and Phase 3 (The Ritual Apex) play out on a procedural hex-grid forest governed by flow fields. The same map, movement costs, and pathfinding serve the player, the Master, faction warbands, and monsters — everything is deterministic given seed plus state, honoring the Clockwork Dark philosophy. See Phases, Master AI, and Factions.

Hex Coordinate System

All spatial logic uses cube coordinates (q, r, s)

with the invariant q + r + s = 0

(stored as axial q, r

; sparse unordered_map<Hex, Tile> ). This makes the six neighbors, distance, and A* heuristics clean:

Distance = max(|Δq|, |Δr|, |Δs|) — admissible and consistent, so A* is optimal. Neighbors = the 6 cube deltas (vs. 4/8 on square grids), giving smoother turns, better packing, and no diagonal-vs-cardinal cost inconsistency.

- Deterministic tie-breaking uses
`hex_key()`

(a stable packing of q,r) so priority-queue order is reproducible.

Terrain & Movement Cost

Each Tile

carries a Terrain

, an optional special-location node

, a trap

tier, a float distortion

, and fog-of-war flags (discovered , visible

). Movement cost entering a hex = terrain base cost + distortion + trap penalty (3 × trap tier

). Water is costly, not blocking — nothing is truly impassable, only expensive.

Terrain base costs (per-mille integers, X/1000

, so the sim stays byte-stable): Terrain | cost | Terrain | cost | | Path | 0.70 | Deep Woods | 1.60 | | Grass / Clearing | 1.00 | Rock | 1.80 | | Forest | 1.20 | Swamp | 2.00 | | Ritual | 1.30 | Water | 3.00 |

Note: the pathfinding design docs described costs as base 1.0 + terrain modifier

(e.g. “Deep Woods 1.5, Spore Caves 2.0”); the build instead uses absolute per-terrain costs (above). Spore Caves is a node type placed onto Swamp terrain (2.0), not a distinct terrain.

Procedural Forest Generation

generate_forest(seed, radius=6) builds a hex disc deterministically:

Terrain — two layers of fractal value noise (fBm, 4 octaves) drive an elevation field and a moisture field; a classify()

threshold table maps them: elevation > 0.74 → Rock, > 0.60 → Deep Woods, low elevation + high moisture → Water/Swamp, very low → Grass, else Forest. Endpoints — the start clearing sits on the west edge (-radius+1, 0)

; the Boundary Gate (the winnable exit) on the east edge (radius-1, 0) , set to Ritual terrain. Node placement — candidate hexes (excluding a 2-hex radius around start/gate) are sorted for a stable base order, then Fisher-Yates shuffled with the seeded RNG, and greedily placed with a minimum spacing of 2 hexes. Some node types stamp their terrain (Lake/Spring → Water, Ritual Scar → Ritual, Spore Caves → Swamp, High Ground → Rock). Reveal — hexes within distance 2 of start begin discovered

.

Node types (18): FairyRing, WhisperingWell, GoblinMarket, TrollBridge, RebelCamp, LoyalistOutpost, AncientShrine, ShimmeringLake, SporeCaves, AbandonedMill, SmugglersCove, BoundaryGate, plus the six high-value contested nodesLey Line Nexus, Fae-Touched Grove, Corrupted Ritual Scar, Water Spirit Spring, Hidden Rebel Cache, High Ground Overlook — which offer strong rewards but draw agents, backlash, and flow distortion.

The design canon frames this as a hybrid PCG pipeline (Curious Expedition 2-inspired): Noise for organic terrain, plus WFC/template-and-prefab structure for special nodes and a guaranteed start→Gate route, then state-driven post-processing (high trace spawns more hazards; high Rebel reputation adds friendly nodes/hidden routes; advanced Ritual Clock fortifies chokepoints). The survey considered BSP, cellular automata, drunkard’s walk, DLA, Voronoi, and WFC before settling on Noise+templates.

Note: WFC and full state-driven node re-weighting are design canon but not in the current build — the build uses fBm noise + seeded shuffle + spacing. Terrain classification and node roster are implemented.

**Hex Pathfinding (A*)**

`a_star(map, start, goal)`

is standard A* on the hex grid: heuristic = true hex distance, cost = `HexMap::movement_cost`

, deterministic tie-breaking, returns the inclusive path or empty if unreachable. The player’s greedy escape and the Master’s precise approach both call it, so both feel the same world friction (traps, distortion, terrain). Design notes call out optional variants (Dijkstra for influence maps, greedy-weighted heuristic for Bloodhound haste, hierarchical/JPS for very large maps) — the build ships plain A* plus the flow field below.

Flow Fields

A flow field is a Dijkstra flood-fill outward from one or more goals: for every reachable hex it stores the best next neighbor toward the goal and the accumulated cost

. build_flow_field(map, goal) (or a vector of goals) drives crowd/warband movement and the Master’s coordinated pursuit — far cheaper than per-agent A* when many agents share few goals, and agents naturally spread out and route around cost. Multi-goal builds seed every goal at cost 0, enabling attraction (toward the player’s last-known position or a chokepoint).

Blended attraction + repulsion (design canon): compute an attraction field and a repulsion field (from traps, high-trace zones, hostile reputation, player decoys), convert each to a direction vector, and blend attr × 1.0 − rep × 0.6

, snapping to the best legal neighbor. This is the mechanism behind Decoy/Illusion pulling crowds and Grey magic (Invisibility, Muffle) letting the player slip between flow lines.

Note: the build implements single- and multi-goal attraction flow fields; repulsion blending and per-agent Boids steering weights are design-only so far.

Flow Distortion & Falloff Curves

Both player and Master can distort the field — raising movement cost in an area to deny it. apply_distortion(map, center, strength, radius, type)

adds a falloff-scaled value to each tile’s distortion

within the radius. Four falloff curves (Falloff

enum): Quadraticstrength / (1 + dist² / radius²)

: smooth, long tail.

Gaussianstrength · exp(−dist² / (2σ²)) , σ = radius/2

: soft bell.

Exponentialstrength · exp(−2·(dist/radius)) : sharp decay. Stepped — banded: full strength inside 34% of radius, ×0.5 to 67%, ×0.2 to the edge, 0 beyond.

Design canon adds dynamic falloff modifiers — the curve/strength responds to lineage (e.g. Nyxari, “The Veiled” excel at misdirection and flow control), Trace Parasite, Ritual Clock stage, and whether the Master is actively contesting. In Phase 3 the fields become violently chaotic. The Master’s ACO planner weighs flow_denial

against contest_resources

and direct_pursuit

. See Master AI. Crowd & Warband Simulation

Faction warbands are mobile forces on the hex grid (FactionWarSim

). Each turn a band finds its nearest hostile enemy, builds a flow field to it, and steps one hex along it; adjacent hostile bands then clash — resolution is d20 + strength/8

per side, loser takes 3 + |Δroll|

damage; a band at strength 0 is routed. Survivors hold territory (hex → controlling faction). The war axis is Rebels vs Loyalists, with Trolls and Goblins hostile to Loyalists for a clean three-way; Fae/Villagers stay out. The player can reinforce

a faction (capped at strength 60), tipping the balance. See Factions. The full design vision layers Boids-style local steering (separation / alignment / cohesion + obstacle avoidance) on the global flow field, with per-faction weight templates — Loyalists: high alignment/goal-focus (patrols); Rebels: high cohesion, avoid high-trace; Monsters: loose, drawn to player trace; Master’s trackers: very goal-driven, trap-smart. The GDD also describes a lightweight movement physics layer (velocity, mass, flow forces) where Trace Parasite raises effective mass. These steering/physics layers are design-only; the build’s warband sim uses flow-field marching + deterministic clash resolution.

In the build

Terrain tabledata/world/terrain.md

(cost_milli

, encounter_base

, per-mille ints), injected into ms_core

via content_tables.cpp

game_tables().terrain , consumed by src/world/hexmap.cpp

(terrain_base_cost

, movement_cost

). Hex map & coordssrc/world/hexmap.hpp/.cpp

, src/core/hex.*

(distance, neighbors, hex_key

). Procedural gensrc/world/forestgen.hpp/.cpp

(fBm noise, node roster, seeded placement). Pathfindingsrc/world/pathfind.hpp/.cpp

(A*). Flow fields & distortionsrc/world/flowfield.hpp/.cpp

(Dijkstra field, Falloff

curves, apply_distortion

). Warband crowd simsrc/world/faction_war.hpp/.cpp

. Headless pursuitsrc/ai/pursuit_sim.cpp

drives a greedy player vs. a Master IAgent

on a generated forest (Bloodhound “haste” = a second step when the Master has a fresh fix and mana), proving the rule-bound Master can win or lose; used by tests and --balance

.

── more in #artificial-intelligence 4 stories · sorted by recency
── more on @master malacor 3 stories trending now
sponsored brought to you by zahid.host 4,200+ EU-deployed projects
reading about agents? ship yours in a single git push.

Run your AI side-project on zahid.host

EU-based hosting, git-push deploys, automatic HTTPS, no cold starts. Free tier with a custom domain — perfect for shipping the agent you just read about.

$git push zahid main
Live at https://your-agent.zahid.host
Get free account → Pricing
from €0/mo · no card required
LIVE [news/the-master-s-shadow] indexed:0 read:14min 2026-07-08 ·