Skip to content

Releases: DiegoLopez0208/RpgMakerMVUltimate-MCP

v5.21.0

Choose a tag to compare

@github-actions github-actions released this 12 Oct 20:50
ba34c19

Fixed

  • Refuse filesystem escapes through symlinks and Windows junctions, including new files under linked parents.
  • Validate System JSON and known fields before selecting a project; reject MZ engine files while supporting partial MV data.
  • Match Unicode names in offline text search, including CJK and normalized Unicode.
  • Report skipped/unreadable files and incomplete analysis; empty search results now explain their limits.
  • Refuse stale-read writes, competing file writers and failed backups; use unique temporary files and backup identifiers. Multi-file edits are still not transactions.
  • Update Sharp, the MCP SDK and test dependencies; make high-severity npm audit findings fail CI, with Windows and Linux test jobs.

Added

  • Read-only --doctor [projectPath] environment check and three first-result recipes.

Changed

  • Require Node.js 20.19.0+; align docs with 18 tools and lexical search.

v5.20.0

Choose a tag to compare

@github-actions github-actions released this 07 Oct 13:17
9afce6b

Upgrade notes. No bridge reinstall is needed. playtest now starts the game with its own NW.js profile under .mcp-cache/nw-profile (add it to your .gitignore if the project is under git) and closes the game an earlier playtest started; pass keepRunning: true to keep the old one. Tool results for take_screenshot and run_playtest now include the PNG as an image block; set RPGMV_INLINE_IMAGES=0 to get paths only. analyze_project validate can report new warnings (missing-asset, asset-case), and generate_map and the manage_map_event presets can return warnings; none of them blocks the write, except presets that point at a troop, item, weapon, armor or switch that does not exist, which are now refused.

Added

  • manage_system action stop_playtest closes the game this server started for the active project, together with the processes it spawned.
  • manage_system action resize_list {section, size} sets the highest valid switch or variable id (1 to 5000), like the editor's "Change Maximum". MV ignores ids past the end of these arrays, so an event writing variable 40 into a 20-variable project did nothing and gave no error. Growing adds empty names; shrinking past a named id is refused unless force: true.
  • manage_system actions list_backups and restore_backup. Every write already kept the previous version in .mcp-backups/; now they can be listed ({file?}, grouped by file, newest first) and put back ({file, backup?}, default the newest, which undoes the last write). Restoring is a write too, so the version it replaces is backed up and a restore can be undone. Covers data/*.json and plugins.js; a backup that is not valid JSON is refused.
  • create_database_entry takes entries (up to 200 data objects) instead of data, to create many items, skills or enemies in one call. It returns {count, created[]}; a failing entry stops the run and the error names the entries already created.
  • analyze_project validate reports image and audio files the project lacks (missing-asset, warning). It reads the names the engine would request, from map battlebacks, parallax and BGM/BGS, event graphics, audio, picture and battleback commands, actors, enemies, animations, tilesets and System.json, and compares them with img/ and audio/. Each distinct file is reported once with the first place that uses it and how many times. A file that exists only under a different letter case is reported as asset-case, since it loads on Windows and fails on a case-sensitive web host. A folder that does not exist is skipped, and RTP assets that are not copied into the project show up too, so the message says so. The counts feed bySeverity and the overview health.
  • generate_map checks that the map can be walked. Every mode except blank and duplicate now returns walkability per generated map (walkable tiles, size of the main walkable area, tiles cut off from it) and warnings when the map has no walkable tile, only a tiny one, or more than a fifth of its walkable tiles unreachable from the main area. The map is still written; the warning says what to fix.
  • manage_map_event presets validate before writing. A troop, item, weapon, armor or switch that does not exist, or a position outside the map, is refused. A tile the player cannot stand on, a tile that already holds an event, and a teleport or door destination that is unwalkable or whose map does not exist yet come back as warnings on the created event. Action-button doors may sit on wall tiles without a warning.
  • Screenshots and renders come back as pictures. take_screenshot (live game, or headless with mapId) and run_playtest frames are now attached to the tool result as MCP image blocks next to the JSON, so the client model can see the map instead of only reading a file path. Only PNGs this server wrote under .mcp-cache/renders or .mcp-cache/screenshots are attached, at most 4 per result and 1.5 MB each; set RPGMV_INLINE_IMAGES=0 to get paths only.

Changed

  • create_plugin keeps js/plugins.js in the editor's format. It used to rewrite the whole file as indented JSON under a different header. It now keeps the file's own header and line endings and writes one compact entry per line, so adding or replacing a plugin changes only that line.
  • populate places events on free tiles of the main walkable area instead of random coordinates that could land in a wall or an unreachable pocket. It stops with a warning when the area is full, and refuses a map with no free tile. Explicit opts.x/opts.y are used as given.
  • The set_starting_position description now says what it already did: a tile the player cannot stand on is moved to the nearest walkable one, reported as relocated.

Fixed

  • Relaunching a playtest restarted nothing. NW.js, like Chromium, runs a single instance per profile: a second game.exe on the shared profile handed its command to the game already open and exited, so the pid returned was dead and the old game kept running (with the old code and its bridge connection) until someone killed it by hand. playtest now gives each project its own profile under .mcp-cache/nw-profile, remembers the game it started, and closes that one first. A pid is only killed if it is still a process of the executable that was launched, so a pid the system has since reused is never touched; keepRunning: true leaves the earlier game open. The result carries replacedPid.

v5.19.0

Choose a tag to compare

@github-actions github-actions released this 05 Oct 02:17

Upgrade notes. Projects that use the live bridge must reinstall its plugin (manage_system action install_bridge_plugin) and restart the playtest: older plugins are refused, and bridge_status says so in lastAuthError. delete_database_entry now refuses entries that are still referenced; pass dryRun: true to see where, or force: true to delete anyway. Node.js 20 or newer is required.

Added

  • edit_map action paint writes one tile into a list of cells or a rectangle of one layer. An autotile is written as its kind, and the painted cells and their eight neighbours get the shapes the editor would give them, so shorelines and wall edges join up; the rest of the map keeps the shapes it was saved with. Layer 5 takes region ids.
  • analyze_project validate reports invalid-autotile: autotile cells whose shape the engine has no table entry for, which make MV throw while drawing the map. edit_map action repair_autotiles fixes only those cells.
  • manage_system action export_web builds an HTML5 deployment folder and a ZIP with index.html at its root, ready for itch.io: runtime scripts, fonts, data and assets, with encrypted assets copied byte for byte and no saves or backups. prune: true drops img/audio/movies files that no data or script references; it is off by default because assets a plugin names only at runtime would be lost. The output must be outside the project and new, empty or a previous export; an existing <outDir>.zip that a previous export did not write is never overwritten. Ported from #20, which pruned by default and overwrote any zip at that path.
  • run_playtest, a new tool. Plays a script of steps headless with the real engine in Chromium: load a map with party, gold, switches and items; startEvent; advanceText returns the lines shown; choose; walk reports where the player ended or which tile blocked; press; wait; autoBattle fights to the end (fast-forwarded unless realtime); screenshot; eval. No editor, NW.js or running game is needed, and project data is not changed. Long runs send MCP progress notifications when the client asks with a progressToken.
  • take_screenshot with mapId renders a map headless, the whole map or a view centred on a tile, as the engine draws it (autotiles, events, optional switches and autorun events). Without mapId it still captures the live playtest.
  • Both need the optional playwright-core and a cached Chromium (or RPGMAKER_MCP_CHROMIUM); without them only these two calls fail, with instructions. PNGs go under .mcp-cache/renders/. Ported from #20 without its caller-chosen output path.
  • The server closes headless browsers and the live bridge when the client disconnects or on SIGINT/SIGTERM.
  • RPGMV_TOOLSET narrows the advertised tools to profiles: core (always on), events, mapgen, media. A data-only session with core lists 11 tools in about 11k tokens instead of 17 in about 18k. Calling a tool outside the toolset says which profile to add; an unknown profile stops the server at startup.
  • A test fails when the default tool list grows past 72 KB (about 20k tokens) or any single tool past 16 KB, and every advertised tool must belong to exactly one profile. CI now also runs lint and the stdio protocol check.
  • build_event_commands kind move_route: Set Movement Route from named steps (the engine's ROUTE_* names, with times to repeat). Writes the route on the 205 row and one 505 row per step without the end marker, as the editor does; #20's version included the end marker.
  • update_database_entry with entity: "troops" and addPage inserts one battle-event page from a compact trigger (turn, enemyHpBelow, actorHpBelow, switchId, turnEnd) without resending the other pages. Pages that could never run are refused. Also available as the legacy add_troop_page tool.
  • build_event_commands gains 16 kinds: gold, items/weapons/armors, party members, actor HP/MP/EXP/level/state/recover all, audio, screen fade/tint/flash/shake, pictures, animations, balloons, battle processing with result branches, shops, name input, and the troop commands enemy appear, enemy state and abort battle. insert_event_commands checks the references they introduce (items, actors, states, animations, variables). Ported from the builders in #20 and checked slot by slot against the MV 1.6.1 interpreter.
  • show_text can wrap: wrap: true reflows the lines and splits them into four-line boxes; "hard" keeps each line as a break. Without it, lines longer than about 55 characters (38 with a face) produce a warning.
  • npm run test:mv-effects: runs the new builders through a local MV interpreter with spied game objects and checks every call it makes.
  • build_event_commands: project-independent, read-only builders for MV dialogue, choices, conditions, switches/self switches, variables, transfers, common-event calls, flow control, and plugin commands. Nested branches compose without mutating input arrays; schemas reject invalid fields and MZ-only formats.
  • insert_event_commands: validated insertion into map-event, common-event, and troop-page lists. Supports dry-run previews, safe nested insertion boundaries, relevant reference checks (including weapon and armor conditions), and the existing atomic backup-protected writer. The result reports the new list length and its command codes; verbose: true adds the full before/after lists. When Cancel rows (code 403) are accepted both empty and with the [6, null] parameters the editor saves.
  • Stdio protocol verification for both normal and legacy tool listings, plus an optional headless check against a locally installed MV interpreter. The runtime check does not redistribute engine files or modify game projects.

Changed

  • delete_database_entry refuses to delete an entry that is still referenced, listing every place: events, common events, troop pages, page conditions, map encounters, the starting party, actor classes and starting equipment, class learnings, enemy actions and drops, troop members, traits, item and skill effects, animations. dryRun: true previews the list; force: true deletes anyway and returns brokenReferences. Deleting used to null the entry silently and leave the game to fail at runtime.
  • Event command names, parameter counts, numeric slots and block structure now come from one table (eventCommandTable.ts) shared by the validator, the event outline and the numeric normaliser.

Security

  • The live bridge only accepts a game from its own project. The plugin sends the realpath of the folder it runs from with the token, and a game from another folder is refused. Windows paths compare without case. Reinstall the plugin (manage_system action install_bridge_plugin) and restart the playtest: an older plugin is refused, and bridge_status says so in its new lastAuthError field.
  • reload_database can no longer write arbitrary globals in the game. The plugin accepted any file and globalVar pair; it now only reloads the database files the server allows, each into its own global (the same list, baked into the plugin).
  • The plugin waits for the server to confirm authentication before sending anything else, and ignores commands until then.
  • bridge_status no longer returns the session token.
  • Telemetry frames over 64 KB are dropped and the buffer is capped at 2 MB; a message assembled from fragments is capped like a single frame; high-frequency frames are dropped in the game when the socket backs up.
  • Bridge commands are refused with out-of-range arguments (teleport coordinates and direction, button hold time, timeout), and the plugin refuses a transfer while an event, message or reload is in progress.
  • A bridge left running for another project is stopped before any telemetry, command, screenshot or recording reaches it.

Fixed

  • Generated maps no longer crash the tile renderer on waterfalls. Only A1 kinds 5 and 7 were treated as waterfalls; the engine also counts 9, 11, 13 and 15. Those got floor shapes up to 47 from the autotile pass, but the waterfall table has 4, so ShaderTilemap threw while drawing them. Waterfalls now keep a valid shape, and an out-of-range one (as in maps generated before this fix) is reset to 0 the next time the map's autotiles are recomputed. Found by the headless renderer on a real project.
  • A second bridge cannot overwrite a live one's handshake, and a dead one's does not block. The handshake is created exclusively; one left by a server that was killed (its pid is gone) is replaced, one held by a live process is refused with its pid. Stopping only deletes a handshake the bridge itself wrote.
  • A reloaded game (F5) is no longer stuck behind its previous connection: the newest authenticated game replaces the older one, and bridge_status counts only live connections.
  • Shop Processing is written the way the engine reads it. The engine reads the 302 row as the first good and purchase-only from its fifth slot; the builder wrote [0, purchaseOnly], so purchase-only was ignored, a purchase-only shop gained item #1, and shops from the map generator carried an empty first good.
  • Reference checks now see what shops sell. Shops were read as if 302 held a list of goods, so items, weapons and armors sold in shops were invisible to validation and reference search.
  • Show Animation references the right animation. References and the event outline read the wait flag (parameters[2]) instead of the animation id (parameters[1]).
  • Change Weapons/Armors and Show Animation write their last flag (include equipment, wait) like the editor does.
  • A client with no active project can now call set_project_path; the previous transport guard refused the very call needed to select one. Pure command builders also work without a project. Project-dependent calls remain guarded.

v5.18.0

Choose a tag to compare

@github-actions github-actions released this 08 Sep 14:43
590e37d

Added

  • record_video, a new tool. Records the live playtest canvas through the authenticated bridge: action:"start" begins a silent WebM capture inside the game runtime, action:"stop" saves it under .mcp-cache/recordings/ and returns {path, bytes, mimeType, durationMs, name}. Only the game canvas is captured, never the desktop. fps (1-60) and bitrateKbps (250-10000) control the artifact.
  • bridge_command can drive the game, not just watch it. Two new instructions: interact, and press_button with button (ok, cancel, menu, and the four directions) and a durationMs hold of 30-1000 ms. Until now the bridge could teleport the player and reload data but had no way to press anything, so a playtest could be set up and never actually played.

Fixed

  • A refused bridge command no longer returns as if it had worked. bridgeCommand returned the game's error frame inside a {sent: true} envelope, so a rejection read as success at the call site. It now throws with the game's own message.

Changed

  • record_video and press_button numeric arguments are validated with the same strict integer fields introduced in 5.17.0, against the ranges the tool definitions advertise. They were declared as the permissive idLike, which would have carried fps: "abc" through to Number() and handed MediaRecorder a NaN frame rate.

v5.17.0

Choose a tag to compare

@github-actions github-actions released this 08 Sep 14:30
a749fab

Reported as #15. Both defects in that report reproduce, and chasing them turned up the reason they shipped at all.

Fixed

  • generate_map threw away the tileset of every template it cloned. createMapFromTemplate wrote tilesetId: params.tilesetId || 1, ignoring the map it had just copied. The tileset selects which tile tables a map renders with, so cloning templateId: 33 — an interior authored for Inside (3) — produced a map flagged as Overworld and rendered as garbage in the engine. 105 of the 111 bundled templates carry a tilesetId other than 1, so this was the normal case, not an edge one. The procedural path had the same hole from the other direction: a forced templateId skips the tileset hard-filter that protects the auto-pick, so theme:"town" with templateId:33 cloned Inside tile data onto an Outside map. generateFromTemplate and cloneTemplateForTheme now return the tileset their data belongs to, and both create paths resolve valid explicit override → cloned template's tileset → theme default. Auto-picked templates are unaffected, and a test pins that.
  • The template test suite could not see the code it was testing. knowledge/ was resolved with one hardcoded relative path that only matched the built layout, so loaded from src/ every template lookup silently returned null. tests/mapGenerator.test.ts therefore imported from dist/ on purpose — testing whatever was last compiled rather than the working tree — and tests/integration.test.ts asserted that mode:"template" throws, codifying the failure as expected behaviour. The whole template write path had no coverage, which is exactly where the tileset bug lived. Resolution now probes both layouts. The fix also drops a dependency on import.meta.dirname, which is undefined below Node 20.11 while engines.node says >=18.
  • Event presets persisted numeric strings where the editor writes numbers. Agents routinely pass stringly-typed numbers, the preset handlers copied x/y and command parameters straight out of their arguments, and validateConsolidated discarded the args Zod had already coerced — its own comment said "this only checks, it never rewrites them". So preset:"door" with x:"1", destX:"3" wrote "x": "1" and parameters: [0, 1, "3", "4", 0, 0]. MV coerces most of that at runtime, but the file is then non-canonical: the editor rewrites those values on the next save, and type-aware tooling, diffs and $dataMap consumers see mixed types. Fixed in three layers — the router forwards the parsed args, ManageMapEventSchema declares the numeric fields the presets actually take, and writeMapJson runs a new normalizeMapEvents() as a last line of defence.
  • A resized template clone silently lost every event it carried, because the resize branch returned [] regardless of keepEvents. Events now survive a resize; any that fall outside the new bounds become null rather than being spliced out, since the engine reads an event's id from its index in the array and compacting would renumber everything after the hole.
  • createMapBatch left a half-written run on disk when a later spec was invalid. Every spec is validated before any is written.

Changed

  • Numbers are parsed strictly, and junk is now an error rather than a wrong value. toNum used parseInt, which accepts anything beginning with digits and truncates the rest: "2.5" became 2, "2x" became 2, "0x10" became 16, "1e3" became 1. z.coerce.number() was worse in the other direction — null, "" and " " all became 0 before any handler ran, so a blank coordinate was accepted and written as 0. Both are replaced by parsers that take a whole number or a string holding exactly one. width and height additionally have to fall within 1..256, the editor's own cap; they previously went straight into Number(), so "2.5" produced a map with "width": 2.5 and a fractional-length data array, and "1e3" produced a 1000-tile side without comment.
  • An explicit tilesetId is validated against the project's Tilesets.json and rejected before any file is written, listing the ids that do exist, instead of || 1 quietly turning 0, "abc" or a nonexistent id into the Overworld tileset.

Notes

normalizeMapEvents() coerces only the slots RPG Maker MV defines as numeric, per opcode, from an explicit table. There is deliberately no blanket recursion: 101[0] is a face image filename, 401/405 are message text, 102[0] holds the choice labels, 108/118/119 are comments and label names, 320[1] is an actor name, 355/655 are script lines, 356 is a plugin command, and 122's operand is JavaScript when operandType is 4. Coercing those would corrupt messages and break plugins. Opcodes not in the table pass through untouched.

v5.16.1

Choose a tag to compare

@github-actions github-actions released this 31 Aug 20:27
67a85da

Fixed

  • The live bridge never connected on a real playtest. Two independent causes, both about how the runtime is launched. Utils.isOptionValid only inspects nw.App.argv[0], but playtest spawns game.exe <projectPath> test, so the project path sat in argv[0] and the test token in argv[1]: the plugin guard was never true and the plugin returned on its first statement. And recent NW.js serves index.html from a chrome-extension:// origin, where the pathname says nothing about where the project lives, so the handshake file was never found. The guard now scans every argument, and the project root falls back to process.cwd() — with playtest spawning cwd: projectPath so that fallback is correct by construction rather than by luck. Without it the game inherited the MCP server's directory and looked for the handshake in the wrong place entirely.
  • Editor-only bits in the bundled template shadow layers. MV renders the shadow layer as a four-bit quadrant mask; four cells across Map012, Map014, Map015 and Map025 carry values outside 0-15 (for example 0x40000005). Harmless in-engine, but it produced non-canonical project data and made the project's own validator report invalid_shadow. Normalised with & 0x0f on both materialisation paths.
  • Three cases where || swallowed a legitimate zero. MV trigger 0 is Action Button, so trigger || 1 silently turned every explicitly-Action-Button transfer into Player Touch. opts.x || … replaced a requested column or row 0 with a random coordinate. count || 3 turned a request for zero events into three.
  • process && process.cwd in the generated plugin threw ReferenceError rather than short-circuiting when the global was absent.

Added

  • A credential-free diagnostic log at .mcp-cache/bridge-plugin.log, because a socket that fails before it connects cannot report why it failed.
  • npm run lint as a real gate. The baseline was 102 errors; test files now scope no-explicit-any off (they deliberately inspect untyped MV JSON) and the genuinely unused imports are gone.

Changed

  • The bridge tests now execute the generated plugin against stubbed engine globals and assert what it did — whether it opened a socket, which path it read the handshake from, whether the token ever reached disk — instead of asserting on its source text, which passed for any refactor that broke the behaviour and failed for any that preserved it.
  • The README no longer claims a deployed build can never open a socket. Scanning all of argv is right given how playtest launches, but it is wider than the engine's own check, and the docs now say so.

v5.16.0

Choose a tag to compare

@github-actions github-actions released this 31 Aug 16:32
c600523

Added

  • analyze_project view balance. Scores every database entry on a power metric and compares it against its PEERS rather than against thresholds invented by the tool, so it works on a game at any power level: damage per MP for skills, gold per point of ATK+MAT for weapons, gold per point of DEF+MDF for armors, HP per point of EXP for enemies. The comparison is leave-one-out — an entry is judged against statistics it had no hand in creating, which is what stops a badly broken entry from dragging the mean toward itself until it stops looking unusual. Narrow with category, loosen or tighten with thresholdSd (default 2). Each outlier carries a sentence about what it means for the player.
  • A damage-formula reader that never executes anything (src/utils/formulaEval.ts). Tokenise, shunting-yard, evaluate: arithmetic, unary minus, parentheses, game variables and the Math functions damage formulas actually use. A formula it cannot read statically comes back with a reason rather than a number, and balance lists those under unreadableFormulas instead of scoring them as zero damage — scoring them zero would pull every average down and hide the outliers the analysis exists to find.
  • validate now reads dialogue text. \N[id] is resolved by the engine at draw time rather than from any structural parameter, so an id pointing at no actor passed every existing check and the editor showed nothing wrong; the line simply rendered in-game with a hole where the name should be. References are collected from every text-bearing command: 401 and 405 lines, 102 choice arrays, and 402 branch labels.

Notes

Both features are ideas taken from the Efold499e fork, reimplemented rather than ported. Two deliberate departures:

  • that version scores a damage formula by substituting the six stat names and passing the rest to eval(). Substitution sanitises the tokens it knows and leaves the rest of the string intact, so a crafted Skills.json runs arbitrary code in whoever analyses the project — which matters precisely because this is a tool you point at projects you did not write.
  • it also validates \I[n] against Items.json. That escape is an icon index (processEscapeCharacter case 'I' calls processDrawIcon, which indexes IconSet.png), not an item id, so the check flags every valid icon on a project with few items. Icon indices are still collected here; nothing validates them against the database.

v5.15.0

Choose a tag to compare

@github-actions github-actions released this 31 Aug 12:58
a4519dd

Added

  • The live bridge: the game talks back. playtest used to be fire-and-forget. manage_system gains install_bridge_plugin, bridge_start, bridge_status, bridge_telemetry, bridge_command, bridge_screenshot and bridge_stop. The generated js/plugins/McpBridge.js connects out to a loopback WebSocket and streams exceptions (with stack traces), console.error/warn, scene changes, player position, the event command currently executing, FPS and heap. bridge_command "reload_map" re-reads the current map from disk and rebuilds the scene without losing party state, using the engine's own reload seam (a reserved transfer with Game_Player._needsMapReload) rather than hand-rebuilding Spriteset_Map; reload_database hot-reloads one data file, and refuses System.json/Tilesets.json with an explanation because those need a fresh playtest. bridge_screenshot writes a PNG for analyze_image.
    • Security: the plugin returns immediately unless Utils.isNwjs() && Utils.isOptionValid('test'), so a deployed build never opens a socket. The server binds 127.0.0.1 only, refuses upgrades carrying a browser Origin (cross-site WebSocket hijacking), and requires the session token from .mcp-bridge.json, compared in constant time, within 5 seconds. The command surface is a fixed allowlist with no eval primitive.
    • The WebSocket server is hand-rolled over http + crypto (~230 LOC): no new runtime dependency.
  • analyze_project view metrics. Measures a map instead of judging it: flood-fill reachability from the real entry point (stranded walkable tiles, and events with no reachable tile beside them — softlocks, not style notes), dead-space ratio against a band for expected interior/dungeon/exterior, the walkable area thinned with Zhang-Suen and read as a graph (endpoints, junctions, cycles, critical path, linearity), Shannon entropy over 5x5 tile windows for monotony, and — for maps with encounters — how many steps the player is from a shop/inn/save point.
  • manage_system action mine_templates. Reads every map in the project and derives, into .mcp-cache/: semantic layouts with the art stripped out (multi-tile props kept whole, doors and points of interest inferred from event commands), a tileset profile per tileset naming the concrete tile the project uses for ground/wall/water/roof by observed frequency, and token adjacency counts. The project itself is not modified. This is what makes generation work on tilesets the bundled RTP templates cannot target.
  • generate_map mode semantic. Lays out a mission — entrance, key, locked door, treasure, boss, exit, side rooms — as a graph, then materialises it through a tileset profile, so one layout works on any tileset including DLC and third-party packs. The key always sits on the entrance side of the lock, so the map is solvable by construction; autotile shapes are recomputed from the finished neighbourhood at the end. Returns markers naming the cell of every mission role. Pass a mined templateId to re-materialise one of the project's own maps onto a different tileset.

Fixed

  • The consolidated manage_system and generate_map Zod schemas rejected every new action and mode with a bare Invalid enum value; validateConsolidated now knows about them.

v5.14.2 — README docs update

Choose a tag to compare

@DiegoLopez0208 DiegoLopez0208 released this 23 Jul 21:02

Changed

  • Documentation: the README now covers the capabilities added in 5.13–5.14 — write safety (atomic writes, rotated backups, dryRun), project scaffolding, playtest / open-in-editor, plugin authoring, and full troop/animation CRUD. No code changes.

v5.14.1 — playtest runtime fix

Choose a tag to compare

@DiegoLopez0208 DiegoLopez0208 released this 23 Jul 21:02

Fixed

  • playtest now actually runs the game. 5.14.0 launched nwjs-win/Game.exe, which is a deploy runtime pinned by its own package.json to www/index.html — so it ignored the project path and showed ERR_FILE_NOT_FOUND. playtest now auto-selects an nwjs runtime whose directory has no sibling package.json (e.g. nwjs-win-test/game.exe), so the project path is honored and the project renders. Verified live end-to-end: an MCP-scaffolded project with a generated town map opens and is playable. A gameExe param allows overriding the runtime.