Skip to content

Tutorial 01 Sprite And Text Tweak

bryanthaboi edited this page Jul 19, 2026 · 1 revision

Tutorial 01 — Sprite and text tweak

Goal. Recolor one Pokemon's battle sprite and rewrite one line of dialogue; see both in-game within ten minutes.

Prerequisites. Getting Started, Concepts: Lifecycle. No Lua experience assumed.

Files created.

mods/tutorial_01_firstmod/
├── manifest.json
├── main.lua
└── transforms.lua

Steps

  1. Scaffold.

    python3 tools/modkit.py scaffold tutorial_01_firstmod
    python3 tools/modkit.py validate tutorial_01_firstmod

    Outcome: validate passes on the empty mod — it drives the real loader headlessly, so a green run here means a clean load in-game.

  2. Declare an asset transform. This is the legal posture, learned first: you ship a recipe, never ROM-derived pixels. Add to manifest.json:

    "assets_transforms": "transforms.lua"

    And write transforms.lua:

    -- runs once, sandboxed, against the player's own imported cache
    return function(ctx)
      local front = ctx.readImage("battle/front/mew.png")
      ctx.writeImage(ctx.recolor(front, {
        { 255, 255, 255 }, { 255, 170, 200 }, { 180, 60, 120 }, { 40, 0, 20 },
      }), "battle/front/mew.png")
    end

    The recipe reads the cached sprite, recolors its four shades (lightest first), and writes the result under the mod's derived root. Because the derived path mirrors the cache path, it shadows the original wherever the engine loads it (src/render/Assets.lua) — no registry call needed. Outcome: on next launch the transform runs once (watch for the assets.transformed log line).

  3. Rewrite a line of dialogue. In main.lua:

    return function(mod)
      mod.content.text:override("_PalletTownSignText", "MODDED SIGN.\nHello from a mod!")
    end

    text is a record registry of generated-text labels; override replaces the string. \n breaks the line. Outcome: reading the Pallet Town sign shows your text.

  4. Enable and see it. The mod is enabled by default; restart the game, start or continue a save, and check Mew's front sprite (the dex, a battle, or the title attract) and the Pallet Town line.

Checkpoint

  • python3 tools/modkit.py validate tutorial_01_firstmod passes.
  • Mew renders in your palette; the Pallet Town sign shows your line.
  • Disable the mod in the manager and restart: both revert to vanilla exactly. That is the parity invariant, and every tutorial ends with it.

Common pitfalls

  • Shipping pixels instead of a transform. Copying a PNG out of assets/generated/ into your mod distributes Nintendo's art; modkit pack refuses cache-derived bytes. The transform generates the art on the player's machine from their own import.
  • Editing assets/generated/ directly. Re-import wipes it whole; transforms write to save/mod-derived/<id>/, which survives.
  • Case in cache paths. Cache sprite files are lowercase (battle/front/mew.png, backs at battle/back/mewb.png).

Next: Tutorial 02 — Balance Patch.

Clone this wiki locally