BS-JD-207 — Renderer material slots, material instances, and exact custom shader surfaces #51

Closed
opened 2026-07-11 18:49:46 -04:00 by Rbanh · 2 comments
Owner

Summary

Build the renderer/material foundation required by Blacksite's production authoring workflow: stable material slots on static and skinned renderers, shared Material and direct-base Material Instance assets, and a constrained custom Surface WGSL contract evaluated consistently by raster and eligible Solari geometry.

Shipped foundation

  • Static and skinned renderers share stable named slot identity, imported-source fallback, explicit assignments, orphan retention, and material-only in-place updates.
  • Dedicated skinned renderer hydration covers rigged, skinned, morph, and animated model placement while static hydration rejects that geometry.
  • Shared Material assets and sparse direct-base Material Instances support guarded editing, Apply/Revert/Create Instance, texture bindings, live dependency propagation, and Opaque/Cutout/double-sided state.
  • Registry-driven component lifecycle owns stable IDs, active state, persistence, reflected history, requirements/conflicts, and compatible composition.
  • Surface ABI v1 shares evaluator validation, packing, texture slots, tangent-space normals, emissive/unlit values, and cutout semantics between raster and eligible Solari geometry.
  • Schema v4 plus cargo upgrade-project provide explicit transactional migration, backup/rollback, canonical renderer slots, and independent component active state.
  • Deformed actors are deliberately omitted from Solari with diagnostics rather than traced as stale bind-pose geometry.

Acceptance criteria

  • Static and skinned renderer inspectors expose stable named slots with shared source/assignment semantics.
  • Shared Material edits propagate to every user; direct-base Material Instances override without mutating the base.
  • Reimport preserves matching assignments and surfaces unmatched assignments as explicit orphans.
  • Material-only edits do not reload meshes, joints, animation players, or current pose state.
  • Supported custom opaque/cutout Surface shaders use matching raster/Solari material semantics on eligible geometry.
  • Legacy scene/prefab material data upgrades transactionally with preflight, backup/report, rollback, and validation.
  • Focused schema, history, renderer-slot, shader ABI, raster/Solari, and pose-lifecycle tests pass.
  • ADRs 0033-0036, editor docs, root README checklist, and committed native screenshots are linked.

Independently scoped follow-ups

  • #53: actual runtime Material Property Block application plus transactional promote-to-instance. The existing component is only a persistence-excluded schema until that ticket closes.
  • #54: post-morph/post-skin current/previous buffers and dynamic BLAS updates. This is a P2 Solari enhancement; raster/Forward remains the documented production fallback.

These are separate subsystems with their own failure modes and acceptance fixtures. Closing this foundation does not claim either follow-up is implemented.

Published evidence

Core implementation: 0798aa5
Acceptance-boundary correction: 9a67a25

Dedicated skinned renderer and slots
Custom Surface Material Instance
Component composition
Material thumbnails

Current verification

The latest main source gate after the M3 work is green: full workspace tests (224 editor tests), all-target Clippy, formatting, and 62-dependency project validation with 0 blocking errors. Packaged tests remain owner-deferred.

## Summary Build the renderer/material foundation required by Blacksite's production authoring workflow: stable material slots on static and skinned renderers, shared Material and direct-base Material Instance assets, and a constrained custom Surface WGSL contract evaluated consistently by raster and eligible Solari geometry. ## Shipped foundation - Static and skinned renderers share stable named slot identity, imported-source fallback, explicit assignments, orphan retention, and material-only in-place updates. - Dedicated skinned renderer hydration covers rigged, skinned, morph, and animated model placement while static hydration rejects that geometry. - Shared Material assets and sparse direct-base Material Instances support guarded editing, Apply/Revert/Create Instance, texture bindings, live dependency propagation, and Opaque/Cutout/double-sided state. - Registry-driven component lifecycle owns stable IDs, active state, persistence, reflected history, requirements/conflicts, and compatible composition. - Surface ABI v1 shares evaluator validation, packing, texture slots, tangent-space normals, emissive/unlit values, and cutout semantics between raster and eligible Solari geometry. - Schema v4 plus `cargo upgrade-project` provide explicit transactional migration, backup/rollback, canonical renderer slots, and independent component active state. - Deformed actors are deliberately omitted from Solari with diagnostics rather than traced as stale bind-pose geometry. ## Acceptance criteria - [x] Static and skinned renderer inspectors expose stable named slots with shared source/assignment semantics. - [x] Shared Material edits propagate to every user; direct-base Material Instances override without mutating the base. - [x] Reimport preserves matching assignments and surfaces unmatched assignments as explicit orphans. - [x] Material-only edits do not reload meshes, joints, animation players, or current pose state. - [x] Supported custom opaque/cutout Surface shaders use matching raster/Solari material semantics on eligible geometry. - [x] Legacy scene/prefab material data upgrades transactionally with preflight, backup/report, rollback, and validation. - [x] Focused schema, history, renderer-slot, shader ABI, raster/Solari, and pose-lifecycle tests pass. - [x] ADRs 0033-0036, editor docs, root README checklist, and committed native screenshots are linked. ## Independently scoped follow-ups - #53: actual runtime Material Property Block application plus transactional promote-to-instance. The existing component is only a persistence-excluded schema until that ticket closes. - #54: post-morph/post-skin current/previous buffers and dynamic BLAS updates. This is a P2 Solari enhancement; raster/Forward remains the documented production fallback. These are separate subsystems with their own failure modes and acceptance fixtures. Closing this foundation does not claim either follow-up is implemented. ## Published evidence Core implementation: [0798aa5](https://git.spacetrainclubhouse.com/Falling-Metal-Interactive/Blacksite/commit/0798aa5d5724115b198d5ec2a2df57e051b49f60) Acceptance-boundary correction: [9a67a25](https://git.spacetrainclubhouse.com/Falling-Metal-Interactive/Blacksite/commit/9a67a25a15c3f6cbfde4e6afe5cb576797b75c9a) - [Evaluation record](https://git.spacetrainclubhouse.com/Falling-Metal-Interactive/Blacksite/src/branch/main/docs/editor/evaluations/material-renderer-foundation/README.md) - [Material-system workflow](https://git.spacetrainclubhouse.com/Falling-Metal-Interactive/Blacksite/src/branch/main/docs/editor/material-system.md) - [ADR index](https://git.spacetrainclubhouse.com/Falling-Metal-Interactive/Blacksite/src/branch/main/docs/README.md) ![Dedicated skinned renderer and slots](https://git.spacetrainclubhouse.com/attachments/fb4a04e7-88ac-4946-a81a-ef3d3ba26140) ![Custom Surface Material Instance](https://git.spacetrainclubhouse.com/attachments/b1097d1f-c07c-44f2-b9ae-3023b8d42835) ![Component composition](https://git.spacetrainclubhouse.com/attachments/259938cf-44cb-4982-99b3-a835771607c5) ![Material thumbnails](https://git.spacetrainclubhouse.com/attachments/6e796111-f345-4817-84c6-3a11801c5f54) ## Current verification The latest `main` source gate after the M3 work is green: full workspace tests (224 editor tests), all-target Clippy, formatting, and 62-dependency project validation with 0 blocking errors. Packaged tests remain owner-deferred.
Rbanh added this to the M2 - Content workspace and asset pipeline milestone 2026-07-11 18:49:46 -04:00
Rbanh added the
roadmap:jackdaw
type:architecture
priority:P0
area:rendering
labels 2026-07-11 18:49:46 -04:00
Author
Owner

Implementation evidence — local acceptance pass (2026-07-11)

Status: implemented and verified on local branch codex/renderer-material-component-foundation; not committed or pushed. This issue remains open for the deformed-ray-geometry item and publication of the committed evidence.

Implemented

  • Dedicated authored/hydrated SkinnedMeshRenderer owns rigged, skinned, morph, and animated model placement; static manifests/hydration reject that geometry.
  • Explicit edit-pose lifecycle captures descendant Transform and MorphWeights, uses one stable configured default clip, and restores the baseline on stop, controller removal, preview reset, and PIE exit.
  • Static and skinned renderers share stable named Material slots with imported source fallback, explicit assignments, orphan retention, and material-only in-place updates.
  • Versioned shared Material assets and direct-base sparse Material Instances now support Apply/Revert/Create Instance, Opaque/Cutout/double-sided state, runtime-only property blocks, and live dependency propagation.
  • Base, schema-defined, stored-custom, and instance texture slots use one project-wide picker. It includes imported model texture subassets, accepts direct texture drag/drop, ignores non-texture payloads, creates sparse instance overrides on selection/drop, and clears back to inheritance.
  • Material thumbnail spheres now use tighter dedicated framing (about 78–81% of the preview); model/mesh framing is unchanged.
  • Registry-driven component lifecycle now owns stable IDs, enable state, persistence, reflected add/remove/reset/copy/paste/history, requirements/conflicts, and compatible composition such as renderer + light.
  • Surface ABI v1 is shared across raster and the maintained Solari fork for parameter/texture packing, tangent-space normals, emissive/unlit values, cutout acceptance, and validation. Invalid revisions retain the last-good evaluator.
  • Project schema v4 and cargo upgrade-project provide explicit transactional migration, backup/rollback, canonical renderer slots, and independent component active state.

Documentation and screenshots

Canonical local record: docs/editor/evaluations/material-renderer-foundation/README.md

Key captures:

  • docs/editor/evaluations/material-renderer-foundation/skinned-mesh-renderer-material-slots.png
  • docs/editor/evaluations/material-renderer-foundation/custom-surface-on-skinned-renderer.png
  • docs/editor/evaluations/material-renderer-foundation/material-instance-sparse-overrides.png
  • docs/editor/evaluations/material-renderer-foundation/mesh-light-component-composition.png
  • docs/editor/evaluations/material-renderer-foundation/larger-material-thumbnail-previews.png

Architecture/workflow docs: ADRs 0033–0036, docs/editor/material-system.md, and docs/editor/extensibility.md.

The Gitea MCP exposes issue comments but not attachment upload, and the browser profile is not signed into this Gitea instance. The paths above are therefore recorded honestly as local branch artifacts pending publication rather than represented as uploaded attachments.

Verification

  • shared: 84 passed
  • scene: 64 passed, 1 ignored migration fixture
  • game: 37 passed
  • game_hot: 16 passed
  • editor: 171 passed
  • blacksite_surface: 3 passed plus doc tests
  • maintained bevy_solari fork: 1 passed
  • cargo --locked --offline validate-levels: 59 dependencies, 5 non-blocking findings, 0 blocking errors
  • second cargo --offline upgrade-project --project . --json: no changes or warnings
  • cargo fmt --all -- --check and git diff --check: pass

Remaining boundary

Bevy 0.19 Solari does not expose dynamic post-morph/post-skin vertex buffers and BLAS updates. Deformed actors are intentionally omitted from ray tracing with an actionable diagnostic instead of appearing as stale bind-pose ghosts. The animated ray-hit acceptance item remains open until that engine boundary is solved.

## Implementation evidence — local acceptance pass (2026-07-11) Status: implemented and verified on local branch `codex/renderer-material-component-foundation`; not committed or pushed. This issue remains open for the deformed-ray-geometry item and publication of the committed evidence. ### Implemented - Dedicated authored/hydrated `SkinnedMeshRenderer` owns rigged, skinned, morph, and animated model placement; static manifests/hydration reject that geometry. - Explicit edit-pose lifecycle captures descendant `Transform` and `MorphWeights`, uses one stable configured default clip, and restores the baseline on stop, controller removal, preview reset, and PIE exit. - Static and skinned renderers share stable named Material slots with imported source fallback, explicit assignments, orphan retention, and material-only in-place updates. - Versioned shared Material assets and direct-base sparse Material Instances now support Apply/Revert/Create Instance, Opaque/Cutout/double-sided state, runtime-only property blocks, and live dependency propagation. - Base, schema-defined, stored-custom, and instance texture slots use one project-wide picker. It includes imported model texture subassets, accepts direct texture drag/drop, ignores non-texture payloads, creates sparse instance overrides on selection/drop, and clears back to inheritance. - Material thumbnail spheres now use tighter dedicated framing (about 78–81% of the preview); model/mesh framing is unchanged. - Registry-driven component lifecycle now owns stable IDs, enable state, persistence, reflected add/remove/reset/copy/paste/history, requirements/conflicts, and compatible composition such as renderer + light. - Surface ABI v1 is shared across raster and the maintained Solari fork for parameter/texture packing, tangent-space normals, emissive/unlit values, cutout acceptance, and validation. Invalid revisions retain the last-good evaluator. - Project schema v4 and `cargo upgrade-project` provide explicit transactional migration, backup/rollback, canonical renderer slots, and independent component active state. ### Documentation and screenshots Canonical local record: `docs/editor/evaluations/material-renderer-foundation/README.md` Key captures: - `docs/editor/evaluations/material-renderer-foundation/skinned-mesh-renderer-material-slots.png` - `docs/editor/evaluations/material-renderer-foundation/custom-surface-on-skinned-renderer.png` - `docs/editor/evaluations/material-renderer-foundation/material-instance-sparse-overrides.png` - `docs/editor/evaluations/material-renderer-foundation/mesh-light-component-composition.png` - `docs/editor/evaluations/material-renderer-foundation/larger-material-thumbnail-previews.png` Architecture/workflow docs: ADRs 0033–0036, `docs/editor/material-system.md`, and `docs/editor/extensibility.md`. The Gitea MCP exposes issue comments but not attachment upload, and the browser profile is not signed into this Gitea instance. The paths above are therefore recorded honestly as local branch artifacts pending publication rather than represented as uploaded attachments. ### Verification - shared: 84 passed - scene: 64 passed, 1 ignored migration fixture - game: 37 passed - game_hot: 16 passed - editor: 171 passed - blacksite_surface: 3 passed plus doc tests - maintained bevy_solari fork: 1 passed - `cargo --locked --offline validate-levels`: 59 dependencies, 5 non-blocking findings, 0 blocking errors - second `cargo --offline upgrade-project --project . --json`: no changes or warnings - `cargo fmt --all -- --check` and `git diff --check`: pass ### Remaining boundary Bevy 0.19 Solari does not expose dynamic post-morph/post-skin vertex buffers and BLAS updates. Deformed actors are intentionally omitted from ray tracing with an actionable diagnostic instead of appearing as stale bind-pose ghosts. The animated ray-hit acceptance item remains open until that engine boundary is solved.
Author
Owner

Published evidence — 0798aa5

The verified implementation is now published on codex/renderer-material-component-foundation.

Dedicated skinned renderer and stable Material slots

Dedicated skinned renderer and slots

Custom Surface Material Instance on skinned geometry

Custom Surface Material Instance

Registry-driven mesh + light composition

Component composition

Larger material previews

Larger material thumbnails

The dynamic deformed-BLAS boundary recorded above remains open; this publication does not claim that item is complete.

## Published evidence — `0798aa5` The verified implementation is now published on `codex/renderer-material-component-foundation`. - [Evaluation record](https://git.spacetrainclubhouse.com/Falling-Metal-Interactive/Blacksite/src/commit/0798aa5d5724115b198d5ec2a2df57e051b49f60/docs/editor/evaluations/material-renderer-foundation/README.md) - [Material-system workflow](https://git.spacetrainclubhouse.com/Falling-Metal-Interactive/Blacksite/src/commit/0798aa5d5724115b198d5ec2a2df57e051b49f60/docs/editor/material-system.md) - [ADR 0033–0036 index](https://git.spacetrainclubhouse.com/Falling-Metal-Interactive/Blacksite/src/commit/0798aa5d5724115b198d5ec2a2df57e051b49f60/docs/README.md) ### Dedicated skinned renderer and stable Material slots ![Dedicated skinned renderer and slots](https://git.spacetrainclubhouse.com/attachments/fb4a04e7-88ac-4946-a81a-ef3d3ba26140) ### Custom Surface Material Instance on skinned geometry ![Custom Surface Material Instance](https://git.spacetrainclubhouse.com/attachments/b1097d1f-c07c-44f2-b9ae-3023b8d42835) ### Registry-driven mesh + light composition ![Component composition](https://git.spacetrainclubhouse.com/attachments/259938cf-44cb-4982-99b3-a835771607c5) ### Larger material previews ![Larger material thumbnails](https://git.spacetrainclubhouse.com/attachments/6e796111-f345-4817-84c6-3a11801c5f54) The dynamic deformed-BLAS boundary recorded above remains open; this publication does not claim that item is complete.
Rbanh closed this issue 2026-07-12 23:03:34 -04:00
Sign in to join this conversation.
No project
No Assignees
1 Participants
Notifications
Due Date
The due date is invalid or out of range. Please use the format 'yyyy-mm-dd'.

No due date set.

Dependencies

No dependencies set.

Reference: Falling-Metal-Interactive/Blacksite#51
No description provided.