diff --git a/.cursor-plugin/plugin.json b/.cursor-plugin/plugin.json index bb943c8..00cf94a 100644 --- a/.cursor-plugin/plugin.json +++ b/.cursor-plugin/plugin.json @@ -75,6 +75,7 @@ "examples/shape-key-blend", "examples/swatch-grid", "examples/temp-override-join", + "examples/text-version-stamp", "examples/turntable", "examples/wave-displace" ] diff --git a/.github/workflows/blender-smoke.yml b/.github/workflows/blender-smoke.yml index 4f9b73a..baa6f5b 100644 --- a/.github/workflows/blender-smoke.yml +++ b/.github/workflows/blender-smoke.yml @@ -298,3 +298,16 @@ jobs: # Exits non-zero on failure. xvfb-run -a "$BLENDER" --background \ --python examples/armature-bend/armature_bend.py -- + + - name: Shipped example - text version stamp (TextCurve solids + version string) + run: | + set -euo pipefail + # Check only (no render): a TextCurve whose body is the live + # bpy.app.version_string; asserts the Curve subclass and built-in + # font contracts, that flat text is filled but planar, the closed + # form z-extent = 2*(extrude+bevel_depth), body edits regenerating + # geometry, that version_string starts with the dotted version tuple + # ("4.5.11 LTS" is not bare semver), and that a Mesh reference dies + # at to_mesh_clear(). Exits non-zero on failure. + xvfb-run -a "$BLENDER" --background \ + --python examples/text-version-stamp/text_version_stamp.py -- diff --git a/AGENTS.md b/AGENTS.md index 3859022..8cad4c5 100644 --- a/AGENTS.md +++ b/AGENTS.md @@ -27,7 +27,7 @@ The content base (counts are CI-enforced against README.md and the manifest): - 2 templates: `extension-addon-template` for Extensions Platform add-ons, and `headless-batch-script-template` for unattended batch jobs. - 17 snippets covering canonical patterns. -- 18 examples under `examples//`: runnable scripts that assert a real +- 19 examples under `examples//`: runnable scripts that assert a real API contract with deterministic checks, exit non-zero on failure, and optionally render a still via `--output`. Each is executed headless on Blender 4.5 LTS and 5.1 by `blender-smoke.yml`; its render ships in the @@ -41,7 +41,7 @@ Blender-Developer-Tools/ rules/.mdc # 6 rule files templates// # 2 starter templates snippets/.py # 17 standalone Python snippets - examples// # 18 runnable smoke-gated examples (+ gallery.json) + examples// # 19 runnable smoke-gated examples (+ gallery.json) scripts/build_gallery.py # generates docs/gallery/ (stdlib only) scripts/site/ # vendored landing-page build (build_site.py + template) docs/gallery/ # committed generated gallery pages + hero assets diff --git a/CLAUDE.md b/CLAUDE.md index f37452c..a4996d5 100644 --- a/CLAUDE.md +++ b/CLAUDE.md @@ -19,7 +19,7 @@ skills//SKILL.md - AI workflow definitions, 12 total rules/.mdc - Anti-pattern rules, 6 total templates// - Starter projects, 2 total snippets/.py - Standalone code patterns, 17 total -examples// - Runnable smoke-gated examples, 18 total (+ gallery.json) +examples// - Runnable smoke-gated examples, 19 total (+ gallery.json) scripts/build_gallery.py - Regenerates docs/gallery/ from gallery.json (stdlib only) scripts/site/ - Vendored landing-page build (Jinja2) docs/gallery/ - Committed generated gallery pages + hero renders @@ -80,11 +80,11 @@ v0.1.0: canonical object creation and deletion, depsgraph evaluated mesh, bmesh v0.2.0: Principled BSDF material, driver-with-custom-function via `driver_namespace`, application handler registration, shader node group with cross-version `interface` API, `foreach_get` bulk vertex read, version-branch skeleton, and USD export with `evaluation_mode='RENDER'`. -## Examples (18) +## Examples (19) Runnable scripts at `examples//`, each asserting a real API contract with deterministic checks (exit non-zero on failure) and optionally rendering a still via -`--output`. All eighteen run headless on Blender 4.5 LTS and 5.1 in `blender-smoke.yml`; +`--output`. All nineteen run headless on Blender 4.5 LTS and 5.1 in `blender-smoke.yml`; their renders ship in the site gallery at `docs/gallery/`. `examples/gallery.json` is the gallery's source of truth. When authoring a new one, copy the anatomy of `examples/bmesh-gear/` (script structure, README shape, dark-studio render recipe) and diff --git a/README.md b/README.md index 79d255f..ade00f2 100644 --- a/README.md +++ b/README.md @@ -17,14 +17,14 @@

- 12 skills  •  6 rules  •  2 templates  •  17 snippets  •  18 examples + 12 skills  •  6 rules  •  2 templates  •  17 snippets  •  19 examples

--- ## Overview -This repository ships **12 skills, 6 rules, 2 templates, 17 snippets, and 18 runnable examples** for Blender Python development targeting Blender 5.1 (current stable) with Blender 4.5 LTS fallback support. +This repository ships **12 skills, 6 rules, 2 templates, 17 snippets, and 19 runnable examples** for Blender Python development targeting Blender 5.1 (current stable) with Blender 4.5 LTS fallback support. The content is consumed by AI coding agents (Cursor, Claude Code, any MCP-capable client) when working on Blender add-ons, geometry nodes scripts, batch pipelines, or animation tooling. There is no build step. Edit the markdown and Python files directly. @@ -314,6 +314,24 @@ linear blend skinning — every evaluated vertex equals Σ wᵢ · (`pose_bone.matrix` @ `bone.matrix_local.inverted()`) @ rest, with the root ring pinned and the tip deflected. A straight tube is a failure. + + + + +Text version stamp: beveled brass 5.1.2 numerals standing on a dark studio floor over a glowing teal underline, with a small steel BLENDER caption above — the body text is the live bpy.app.version_string + + + +### [text-version-stamp](examples/text-version-stamp/) + +A beveled 3D stamp of the running Blender version — a `TextCurve` whose `body` is the +live `bpy.app.version_string`, so every render self-documents which Blender made it. +Asserts the TextCurve solids closed form (evaluated z-extent = 2 × (extrude + +bevel_depth), bevel widening the outline by 2 × bevel_depth), that flat text is filled +but planar, that body edits regenerate geometry, that `version_string` is not bare +semver on LTS builds (`"4.5.11 LTS"`), and that a Mesh reference dies at +`to_mesh_clear()`. + diff --git a/ROADMAP.md b/ROADMAP.md index 8c35cab..0d63cd1 100644 --- a/ROADMAP.md +++ b/ROADMAP.md @@ -97,7 +97,7 @@ Not committed; target list for the next content version. (v0.3.0 shipped the smo - Refresh the `slotted-actions-animation` skill against any 5.2 changes - Bump `blender_version_min` in the templates if 5.2 APIs are used - Additional snippets for asset library scripting, EXR baking, multi-file extensions -- Gallery coverage follow-ups from the GPv3 review: `text-version-stamp` (TextCurve self-labeling renders); lower priority: light-linking, bulk `pixels.foreach_set`, VSE sequences-to-strips witness (`grease-pencil-rosette` and `armature-bend` shipped first) +- Gallery coverage follow-ups from the GPv3 review: light-linking, bulk `pixels.foreach_set`, VSE sequences-to-strips witness (`grease-pencil-rosette`, `armature-bend`, and `text-version-stamp` shipped first) ## Future (uncommitted) diff --git a/docs/gallery/assets/text-version-stamp-hero.webp b/docs/gallery/assets/text-version-stamp-hero.webp new file mode 100644 index 0000000..c9787ca Binary files /dev/null and b/docs/gallery/assets/text-version-stamp-hero.webp differ diff --git a/docs/gallery/index.html b/docs/gallery/index.html index 13309b8..4a1b6c3 100644 --- a/docs/gallery/index.html +++ b/docs/gallery/index.html @@ -399,6 +399,17 @@

armature-bend

View example +
+ + text-version-stamp — The TextCurve data API — curves + +
+

text-version-stamp

+

The TextCurve data API — curves.new(type='FONT'), live body text from bpy.app.version_string, extrude and bevel_depth solids, and evaluated-mesh conversion — so every render self-documents which Blender produced it.

+

witnesses TextCurve solids are exactly predictable: evaluated z-extent = 2 × (extrude + bevel_depth), bevel widens the outline by 2 × bevel_depth, editing body regenerates geometry — and version_string is not bare semver on LTS ("4.5.11 LTS"), so parse bpy.app.version instead.

+ View example +
+