The full upstream README, mirrored here for reference. Install config, tool schemas, adoption signals, and an original overview live on the RpgMakerMVUltimate MCP listing page.
Quick start · What it does · Map generation · Live bridge · Intelligence · Tools
A Model Context Protocol server that lets an AI agent work on a real RPG Maker MV project on disk — database, maps, events, plugins, system — through 13 consolidated tools validated against the actual engine, so what comes out is coherent and playable.
It does three things that are usually missing:
| 🏗️ Builds | Generates maps that look hand-made, wires events from presets, and edits every database with real IDs instead of invented ones. |
| 🧠 Understands | Reads the whole project and answers why the door never opens, which map nobody can reach, which skill breaks the game. |
| 👀 Watches | Runs the game and reports back: exceptions, player position, screenshots — and reloads a map you just edited without losing the save. |
1 — Add it to your MCP client. No clone needed; the package ships an executable.
MCP clients load tool definitions once at startup, so restart the client after adding or upgrading the server.
2 — Point it at a project. RPGMAKER_PROJECT_PATH is the folder containing data/, js/ and index.html. The server starts without it; call set_project_path at runtime instead if you prefer.
3 — Let the agent look around first.
Works with Claude Desktop, Claude Code, opencode, and any MCP-compatible client.
The bottom half of that loop is what the bridge adds. Before it, the agent wrote files and hoped.
Two paths, both behind generate_map. Pick by whether your project uses RTP art.
mode: "procedural" (default) | mode: "semantic" | |
|---|---|---|
| How | Clones a hand-authored map from the 106 bundled RTP templates, closest size first | Lays out a mission graph, then paints it through a tileset profile |
| Looks like | Real multi-tile buildings, walls, furniture | Rooms and corridors shaped by what the space is for |
| Tilesets | RTP, or close to it | Any — DLC, itch.io, custom |
| Guarantees | Same seed → same map | Same seed → same map, and the key is always reachable before the door it opens |
Themes with a matching template — town, village, dungeon, interior, castle, world and more — clone a real map instead of painting tile noise. Themes without one (beach, swamp, desert…) fall back to Perlin terrain, BSP dungeons and cellular caves. Combat themes auto-wire random encounters from your existing troops; town and village auto-create enterable house interiors with two-way warps.
Themes ·
foresttownvillagecastledungeoncavebeachdesertswampruinsinteriorsnowharborvolcanosewerfortressmagic_forestmagic_interiorspace_interiorspace_exteriorworld
Other modes: blank (empty canvas), themed (simple layout), template (one specific bundled map), batch (many at once), duplicate (copy an existing map).
The bundled templates are raw MV map JSON, so their tile IDs only mean anything on RTP sheets. Change the tileset and the map turns to noise. semantic keeps the layout abstract until the last moment:
.mcp-cache/.markers naming the cell of every mission role, which is where to put events with manage_map_event.templateId (e.g. "mined-3") to re-materialise one of your own maps onto a different tileset.playtest on its own is fire-and-forget: the game opens and nothing comes back. The bridge closes the loop.
console.error/warn, scene changes, player position, which event command is executing (so a hung event can be pinpointed), FPS and heap. Frames are consumed as you read them unless you pass peek.reload_map re-reads the current MapXXX.json and rebuilds the scene without losing party state: it reserves a transfer to the player's own position with _needsMapReload, the engine's own reload seam, rather than rebuilding Spriteset_Map by hand. reload_database re-reads one data file; System.json and Tilesets.json need a fresh playtest and are refused with an explanation.take_screenshot { name: "collision-proof" } captures the live playtest through the MCP plugin, saves a timestamped PNG under .mcp-cache/screenshots/, and returns its path for inspection or QA evidence. No shell screenshot command is involved. manage_system { action: "bridge_screenshot" } remains as a compatibility alias.record_video { action: "start", name: "npc-dialogue" } begins a silent WebM capture of the live game canvas; record_video { action: "stop" } saves it under .mcp-cache/recordings/ and returns its path. Agents can stage repeatable scenes with the allowlisted interact command and fixed-button press_button input—there is still no arbitrary script or eval command.🔒 Security
The plugin returns before anything else runs unless the game is under NW.js and was launched with a
testargument. A deployed build a player double-clicks never reaches the socket code, or evenrequire('fs').It checks every argument rather than only
argv[0]the wayUtils.isOptionValiddoes, becauseplaytestpasses the project path first. So a deployed build deliberately launched with a literaltestargument would get past the guard — and then find no handshake file, and never connect.The server binds
127.0.0.1only, refuses any upgrade carrying a browserOrigin(cross-site WebSocket hijacking), and requires the session token from.mcp-bridge.json— compared in constant time — within 5 seconds or the connection is dropped.The command surface is a fixed allowlist with no
evalprimitive.
analyze_project is read-only and fully offline. It models the whole project once, so an agent can reason about a game it did not build.
| View | Answers |
|---|---|
overview | Call this first. Counts, health summary, maps unreachable from the start |
validate | Every consistency problem at once — see below |
explain | Why does this never happen? e.g. "Switch 12 is gated in 3 places but never set ON" |
usage | Every event, common event and troop that touches a switch/variable/item, with read-write roles |
graph | The map transfer network and what is reachable |
ast | One event's logic as a readable tree |
plugins | What plugins the project uses, their parameters and commands |
critique | A designer's opinion on one map: dead space, clutter, event spread, monotony |
metrics | The same map measured — see below |
balance | Database entries that are out of line with their peers — see below |
refactor | Command sequences copy-pasted across events, worth extracting into a Common Event |
search | Find things by meaning across names, dialogue and descriptions |
index | The structured digest the other views are built on |
Broken transfers, missing map files, dangling common-event/item/troop references, duplicate IDs, named-but-unused switches and variables, a bad starting position, unreachable maps — and actor names written into dialogue as \N[id] that do not resolve.
That last one is worth its own sentence: the engine resolves \N[id] at draw time, not from any structural parameter, so a bad id passes every other check and the editor shows nothing wrong. The line just renders in-game with a hole where the name should be, and a player finds it before you do.
expected (interior / dungeon / exterior).A skill dealing 400 damage is fine in a game where everything does, and broken in one where nothing else breaks 60. So each entry is scored on a power metric and compared against the others in its category: damage per MP for skills, gold per point of ATK+MAT for weapons, gold per DEF+MDF for armors, HP per EXP for enemies.
The comparison is leave-one-out — an entry is judged against statistics it had no hand in creating. Included in its own numbers, a badly broken entry drags the mean toward itself until it stops looking unusual at all.
Damage formulas are parsed, never executed (tokenise → shunting-yard → evaluate). One that cannot be read statically is listed under unreadableFormulas rather than scored as zero damage, which would pull every average down and hide the very outliers you were looking for.
Narrow with category, loosen or tighten with thresholdSd (default 2).
query_map { view: "ascii", mapId } — render a map as a character grid with event markers. The cheapest way to see a layout and pick coordinates.query_map { view: "validate", mapId } — lint one map for invalid tile IDs, broken transfers and missing event terminators.| Tool | Purpose |
|---|---|
query_database | List / get by ID / search any database (actors, classes, skills, items, weapons, armors, enemies, states, troops, tilesets, common events, animations) |
create_database_entry | Create entries, with presets: damage_skill, healing_skill, buff_skill, state_skill, boss_enemy, encounter_troop |
update_database_entry | Partial updates (incl. troops & animations); append commands to common events; add enemies to troops |
delete_database_entry | Delete entries with reference-breakage warnings |
query_map | Map tree, full map data, events, single event, lint, offline ASCII render |
generate_map | Knowledge-driven, semantic, procedural, blank, themed, template, batch or duplicate |
edit_map | Fill tile layers, set display names, organize the map tree, connect two maps, set encounters |
manage_map_event | Create (presets: npc, chest, teleport, door, shop, inn, boss, puzzle_switch), update, convert an NPC into a merchant/inn/sign in place, delete, add commands, bulk-populate |
manage_system | Title, switch/variable names, starting position, author a plugin, scaffold an editor-openable project, playtest, open/repair in editor, mine templates, and the live bridge |
take_screenshot | Capture and name a live playtest PNG through the authenticated MCP bridge |
record_video | Start or stop a named live playtest WebM recording through the authenticated MCP bridge |
analyze_project | The read-only intelligence layer above |
get_project_context | Project digest, asset index, per-tileset tile IDs, bundled-template catalog |
set_project_path | Switch projects at runtime |
analyze_image | Optional Vision-AI image analysis, plus offline tileset grid measurement and quadrant colors |
The 101 fine-grained v4 tool names still work as call aliases. Set RPGMV_LEGACY_TOOLS=1 to advertise them too.
.mcp-backups/ (last N, RPGMV_BACKUP_KEEP, default 10).dryRun: true to any mutating tool to see exactly what it would write, without touching disk.⚠️ Close the RPG Maker editor while an agent is working. The editor holds the project in memory and will overwrite changes when it saves.
| Variable | Required | Description |
|---|---|---|
RPGMAKER_PROJECT_PATH | recommended | The project folder (the one with data/ and js/). Optional — set_project_path works at runtime |
RPGMAKER_MV_INSTALL | for playtest | Engine install root, for playtest / open_editor / scaffold_project. Defaults to the standard Steam path |
RPGMV_BRIDGE_PORT | optional | Loopback port for the live bridge (default 32123) |
RPGMV_BACKUP_KEEP | optional | Backups kept per file (default 10) |
RPGMV_LEGACY_TOOLS | optional | 1 also advertises the 101 legacy tool names |
VISION_API_URL | to enable vision | Base URL of an OpenAI-compatible vision endpoint. Unset = vision disabled |
VISION_API_KEY | optional | Bearer token; only sent when set |
VISION_MODEL | optional | Model name (default meta/llama-3.2-90b-vision-instruct) |
VISION_API_PATH | optional | Endpoint path (default /v1/chat/completions) |
analyze_image { mode: "ai" } sends a project image (tileset, sprite, screenshot, battler) to any OpenAI-compatible endpoint. Nothing is sent anywhere unless you configure it; the grid and colors modes and every other tool work fully offline.
Works with OpenAI, Ollama, LocalAI, NVIDIA NIM, vLLM, LiteLLM, or any OpenAI-compatible proxy.
A portable Agent Skill teaches any model the crash-free workflow — build maps with generate_map, add content with manage_map_event presets, never hand-paint tiles or guess IDs. It lives at skill/rpgmaker-mv-mcp/SKILL.md.
Also listed in awesome-claude-skills.
| File | Content |
|---|---|
tile-ids.json | Tile ID ranges, autotile formula, sheet descriptions, layer meanings |
passage-flags.json | Flag bits, common flags, passage check logic |
event-commands.json | ~140 event command codes with parameter schemas |
enums.json | Scope, occasion, hitType, damageType, restriction, and the rest |
trait-effect-codes.json | Trait codes 11-64, effect codes 11-45 |
database-schemas.json | Full schemas for every MV data type |
image-paths.json | img/ directories, tileset slots, naming conventions |
map-templates.json | Index of the 106 bundled reference maps |
stamps.json | Mined multi-tile object stamps (trees, props) per tileset |
maps/ | The 106 RTP reference map JSONs used for template cloning |
mode: "semantic" currently generates dungeon-shaped missions. Town and open-world mission grammars are next, as is using the mined adjacency counts to decorate rather than only to describe.balance compares like with like inside a category, so a boss will legitimately look like an outlier next to random encounters. Read the flag, not the verdict.| Where | What |
|---|---|
src/server.ts | Tool handlers and MCP transport |
src/toolDefinitions.ts + src/router.ts | The 13-tool surface and its routing |
src/tools/* | Per-domain CRUD |
src/utils/mapGenerator.ts | Template cloning and procedural generation |
src/utils/graphGenerator.ts + src/utils/materialize.ts | Mission graphs and the semantic compiler |
src/bridge/* | The loopback WebSocket and the in-game plugin |
src/intel/* | The read-only layer behind analyze_project |
knowledge/ | Static reference data and bundled maps |
Actively developed, and feedback is very welcome — bug reports, weird maps, missing tools, ideas. Open a GitHub Issue with what you asked the agent to do and what you got; an exported map JSON or a screenshot helps a lot.