Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions docs/skill-cheat-sheet.md
Original file line number Diff line number Diff line change
Expand Up @@ -181,6 +181,7 @@ owned by [docs/catalog-taxonomy.md](catalog-taxonomy.md).
| [`/adhd:clarify`](../plugins/adhd/skills/clarify/SKILL.md) | `adhd` | Reshape a dense, decision-heavy message into clear one-decision-at-a-time chunks, losing nothing |
| [`/adhd:shape`](../plugins/adhd/skills/shape/SKILL.md) | `adhd` | Set a standing action-first output posture. Lead with the next action, cut preamble |
| [`/ai-slop:audit`](../plugins/ai-slop/skills/audit/SKILL.md) | `ai-slop` | Detect and remove AI-writing tells from markdown prose |
| [`/animation:check-prerequisites`](../plugins/animation/skills/check-prerequisites/SKILL.md) | `animation` | Report whether the tools animation declares resolve. Never installs. |
| [`/architecture:record-decision`](../plugins/architecture/skills/record-decision/SKILL.md) | `architecture` | Record an architecture decision in the repository's existing ADR convention |
| [`/attribution:audit`](../plugins/attribution/skills/audit/SKILL.md) | `attribution` | Find prose copied from external sources and convert it into pointers |
| [`/autonomy:check`](../plugins/autonomy/skills/check/SKILL.md) | `autonomy` | Report whether node and jq resolve for the autonomy hooks. Never installs. |
Expand Down
2 changes: 1 addition & 1 deletion plugins/animation/.claude-plugin/plugin.json
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"name": "animation",
"version": "0.3.2",
"version": "0.4.0",
"description": "Hand-drawn-style 2D animation as code, rendered in headless Chromium by an ink brush engine. rotoscope copies a reference clip drawing by drawing: trace to vector paths, render, measure against the source (XOR, SSIM), and fit per-shot brush overrides. learn-style measures a clip into a style pack (ships woodcut-ink) and checks films against it. produce turns a brief into approved boards, a shot list, frames, and a delivered file. setup checks ffmpeg, Node, Chromium, and Python.",
"author": {
"name": "Melodic Software",
Expand Down
11 changes: 11 additions & 0 deletions plugins/animation/CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,17 @@
All notable changes to the `animation` plugin are documented here. Format follows
[Keep a Changelog](https://keepachangelog.com/en/1.1.0/); this plugin uses semantic versioning.

## [0.4.0] - 2026-10-03

### Added

- A `SessionStart` hook row reports a missing `node` once per session, on both hook channels, and works on Windows without Git Bash. The notice names `/animation:check-prerequisites`.
- `/animation:check-prerequisites`, a read-only report of whether the tools in `prerequisites.json` resolve, through the shared Node checker.

### Changed

- Each `prerequisites.json` entry's `check` names `/animation:check-prerequisites`, so a failed row sends the user back to the plugin's own check.

## [0.3.2] - 2026-10-03

### Changed
Expand Down
1 change: 1 addition & 0 deletions plugins/animation/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@ Canvas 2D modules (`renderFrame(t)`), headless Chromium draws the frames, and ff
| Skill | What it does |
|---|---|
| `/animation:rotoscope <clip> <work dir>` | Copies a reference clip drawing by drawing: traces each distinct drawing to vector paths, renders them through the ink.js brush engine, measures every drawing against its source (XOR against a codec-noise floor, SSIM, edge-band SSIM, paper color), fits per-shot brush overrides, and reviews 1:1 crops. Each run appends to a learnings file, and a retro step promotes recurring findings into the defaults. |
| `/animation:check-prerequisites` | Read-only report of whether the tools the plugin declares in `prerequisites.json` resolve; installs nothing. |
| `/animation:setup` | Checks the prerequisites (ffmpeg with libx264, ffprobe, Node, playwright-core with Chromium, the pinned numpy and opencv, and the `playwright_core` option when set) and prints a PASS/FAIL/INFO table with one remedy line per failure. Check-only: it installs nothing (the SessionStart hook installs the Python packages). |
| `/animation:learn-style <work dir> <pack dir>` | Measures a rotoscope work directory into a style pack: palette and tone ramp, the seven style knobs, and statistic bands (edge softness, stroke and gap widths, edge roughness, gray inside the ink, boil of the frame and caption, holds on 1s/2s/3s). Then proves the pack by authoring a new scene with ink.js and checking its render against the bands. |
| `/animation:produce <production dir>` | From a brief and one or more style packs, writes pre-production boards and stops for approval. After that, a shot list, scenes, rendered frames, a delivered file, and a review against the pack. `shots.json` is the cut list `inkstats.py --cuts` reads. |
Expand Down
6 changes: 6 additions & 0 deletions plugins/animation/hooks/hooks.json
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,12 @@
],
"timeout": 300,
"statusMessage": "Installing animation Python packages..."
},
{
"type": "command",
"command": "sh \"${CLAUDE_PLUGIN_ROOT}/lib/prerequisites.sh\" node-notice /animation:check-prerequisites; ${BASH_VERSION:+exit}; powershell -NoProfile -ExecutionPolicy Bypass -File \"${CLAUDE_PLUGIN_ROOT}/lib/prerequisites.ps1\" node-notice /animation:check-prerequisites",
"timeout": 10,
"statusMessage": "Checking that node is on PATH..."
}
]
}
Expand Down
12 changes: 6 additions & 6 deletions plugins/animation/prerequisites.json
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,7 @@
"winget": "OpenJS.NodeJS.LTS",
"apt": "nodejs"
},
"check": "/harness-ops:prerequisites"
"check": "/animation:check-prerequisites"
},
{
"id": "python3",
Expand Down Expand Up @@ -48,7 +48,7 @@
"winget": "Python.Python.3.12",
"apt": "python3"
},
"check": "/harness-ops:prerequisites"
"check": "/animation:check-prerequisites"
},
{
"id": "jq",
Expand All @@ -69,7 +69,7 @@
"winget": "jqlang.jq",
"apt": "jq"
},
"check": "/harness-ops:prerequisites"
"check": "/animation:check-prerequisites"
},
{
"id": "ffmpeg",
Expand All @@ -92,7 +92,7 @@
"winget": "Gyan.FFmpeg",
"apt": "ffmpeg"
},
"check": "/harness-ops:prerequisites"
"check": "/animation:check-prerequisites"
},
{
"id": "ffprobe",
Expand All @@ -115,7 +115,7 @@
"winget": "Gyan.FFmpeg",
"apt": "ffmpeg"
},
"check": "/harness-ops:prerequisites"
"check": "/animation:check-prerequisites"
},
{
"id": "libx264",
Expand Down Expand Up @@ -143,7 +143,7 @@
"winget": "Gyan.FFmpeg",
"apt": "ffmpeg"
},
"check": "/harness-ops:prerequisites"
"check": "/animation:check-prerequisites"
}
]
}
38 changes: 38 additions & 0 deletions plugins/animation/skills/check-prerequisites/SKILL.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,38 @@
---
description: "Read-only report of whether the external tools the animation plugin declares in prerequisites.json resolve, through the shared Node checker. /animation:setup is the fuller setup report; this skill is the shared checker's. Use when: 'animation node notice', 'is animation ready', a hook notice says node is missing. It does not verify the hook-installed Python packages; /animation:setup does. Does not install."
user-invocable: true
disable-model-invocation: false
metadata:
workflow-stage: anytime
summary: Report whether the tools animation declares resolve. Never installs.
---

## Purpose

Run the read-only check. Do not install anything, and do not edit `prerequisites.json`.

The plugin has no `check` skill, so the prerequisites check has its own name. A hook notice names it.

## Check

Run the shared checker through its stub, which reports a missing `node` instead of failing to start:

```bash
sh "${CLAUDE_PLUGIN_ROOT}/lib/prerequisites.sh" check "${CLAUDE_PLUGIN_ROOT}" --data-dir "${CLAUDE_PLUGIN_DATA}"
```

Where there is no `sh` (Windows without Git Bash), run the PowerShell stub with the same arguments instead:

```powershell
powershell -NoProfile -ExecutionPolicy Bypass -File "${CLAUDE_PLUGIN_ROOT}/lib/prerequisites.ps1" check "${CLAUDE_PLUGIN_ROOT}" --data-dir "${CLAUDE_PLUGIN_DATA}"
```

Report the PASS/FAIL rows as a table. On a FAIL, give the install hints the checker printed. Stop.
Comment thread
kyle-sexton marked this conversation as resolved.

## Next

/animation:setup

## Gotchas

This skill does not install. A hook notice is not permission to install Node.js.
41 changes: 41 additions & 0 deletions plugins/animation/skills/check-prerequisites/evals/evals.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,41 @@
{
"skill_name": "check-prerequisites",
"evals": [
{
"id": 1,
"name": "node-notice-runs-the-check",
"prompt": "A session-start notice said node is missing for animation. What else is missing?",
"expected_output": "Runs the shared checker through lib/prerequisites.sh check with the plugin root and data dir, then reports each PASS/FAIL row with the install hints it printed.",
"files": [],
"expectations": [
"Runs `lib/prerequisites.sh check` with the plugin root and --data-dir",
"Reports each FAIL row with the install hint the checker printed",
"Installs nothing"
]
},
{
"id": 2,
"name": "install-request-is-declined",
"prompt": "/animation:check-prerequisites\n\nnode is missing. Install it.",
"expected_output": "Reports the rows and the install hints, and does not install Node.js.",
"files": [],
"expectations": [
"Does not run an installer",
"Prints the install hints the checker produced",
"Does not edit prerequisites.json"
]
},
{
"id": 3,
"name": "windows-without-sh-uses-the-powershell-stub",
"prompt": "/animation:check-prerequisites on Windows without Git Bash.",
"expected_output": "Runs lib/prerequisites.ps1 with the same arguments instead of the sh stub.",
"files": [],
"expectations": [
"Uses `lib/prerequisites.ps1` when there is no `sh`",
"Passes the same check, plugin root and --data-dir arguments",
"Reports the PASS/FAIL rows as a table"
]
}
]
}
2 changes: 0 additions & 2 deletions scripts/node-notice-rows.test.sh
Original file line number Diff line number Diff line change
Expand Up @@ -15,14 +15,12 @@ ROOT="$(cd "$SELF_DIR/.." && pwd)"
# shellcheck source=lib/test-harness.sh
. "$SELF_DIR/lib/test-harness.sh"

EXEMPT=(animation) # no prerequisites file or check skill yet; the batch that declares it adds both
MARKER='prerequisites.sh" node-notice'

# --- fleet shape ----------------------------------------------------------------
rows_checked=0
for hooks in "$ROOT"/plugins/*/hooks/hooks.json; do
plugin="$(basename "$(dirname "$(dirname "$hooks")")")"
[[ " ${EXEMPT[*]} " == *" $plugin "* ]] && continue
mapfile -t rows < <(jq -r '[.hooks.SessionStart[]?.hooks[]? | select((.command // "") | contains("prerequisites.sh")) | .command] | .[]' "$hooks")
if ((${#rows[@]} != 1)); then
bad "$plugin: want exactly one node-notice SessionStart row" "found ${#rows[@]}"
Expand Down
7 changes: 4 additions & 3 deletions scripts/skill-leaf-name-registry.txt
Original file line number Diff line number Diff line change
Expand Up @@ -154,9 +154,10 @@ check actionlint,autonomy,bash-format,biome-format,harness-ops,context-budget,co

# The prerequisites check, for a plugin whose `check` already means something
# else (docs/conventions/prerequisites/). instruction-placement gates rule
# globs, skill-quality gates a skill, toolchain builds and tests a project. A
# hook notice names this skill where it would name `check`.
check-prerequisites instruction-placement,skill-quality,toolchain
# globs, skill-quality gates a skill, toolchain builds and tests a project;
# animation has no `check` skill. A hook notice names this skill where it would
# name `check`.
check-prerequisites animation,instruction-placement,skill-quality,toolchain

# Fixed verb meaning: mutates the target. disk-hygiene cleans an arbitrary
# directory tree, repo-hygiene cleans a repository's caches and git metadata.
Expand Down
Loading