doc updates
All checks were successful
CI / React UI Build (push) Successful in 11s
CI / Native Windows Build And Tests (push) Successful in 2m22s
CI / Windows Release Package (push) Successful in 2m27s

This commit is contained in:
2026-05-08 18:49:27 +10:00
parent 1ea44ba3ae
commit 27bf2ae45c
5 changed files with 89 additions and 14 deletions

View File

@@ -2,7 +2,7 @@
Native video shader host with an OpenGL render path, pluggable video I/O boundary, DeckLink backend, Slang shader packages, and a local React control UI. Native video shader host with an OpenGL render path, pluggable video I/O boundary, DeckLink backend, Slang shader packages, and a local React control UI.
The app loads shader packages from `shaders/`, compiles Slang to GLSL at runtime, renders a configurable layer stack, and exposes a browser-based control surface over a local HTTP/WebSocket server. The app loads shader packages from `shaders/`, compiles Slang to GLSL at runtime, renders a configurable layer stack, and exposes a browser-based control surface over a local HTTP/WebSocket server. Shader compilation is prepared off the frame path where possible, then committed on the render thread so editing shader files does not block video output for the whole compile.
## Repository Layout ## Repository Layout
@@ -62,6 +62,14 @@ npm run build
The native app serves `ui/dist` when it exists, otherwise it falls back to the source UI directory during development. The native app serves `ui/dist` when it exists, otherwise it falls back to the source UI directory during development.
The control UI provides:
- A searchable shader library for adding layers.
- Compact parameter rows with inline descriptions and OSC copy controls.
- Stack save/recall presets.
- Manual shader reload.
- Screenshot capture from the final output render target.
## Package ## Package
Build the UI, build the native Release target, then install into a portable runtime folder: Build the UI, build the native Release target, then install into a portable runtime folder:
@@ -123,6 +131,7 @@ Current native test coverage includes:
- Shader manifest parsing, temporal manifest validation, and package registry scanning. - Shader manifest parsing, temporal manifest validation, and package registry scanning.
- Video I/O format helpers, v210/Ay10 row-byte math, v210 pack/unpack math, playout scheduler timing, and fake backend contract coverage. - Video I/O format helpers, v210/Ay10 row-byte math, v210 pack/unpack math, playout scheduler timing, and fake backend contract coverage.
- OSC packet parsing. - OSC packet parsing.
- Slang validation for every available shader package.
## Runtime Configuration ## Runtime Configuration
@@ -182,7 +191,11 @@ http://127.0.0.1:<serverPort>/docs
Use those docs to inspect the `/api/state`, layer control, stack preset, and reload endpoints. Live state updates are also sent over the `/ws` WebSocket. Use those docs to inspect the `/api/state`, layer control, stack preset, and reload endpoints. Live state updates are also sent over the `/ws` WebSocket.
The control UI also has a Screenshot button. It queues a capture of the final output render target and writes a PNG under: The control UI has a **Reload shaders** button. It rescans `shaders/`, re-reads manifests, queues shader compilation, refreshes shader availability/errors, and keeps the previous working shader stack running if a changed shader fails to compile.
Each parameter row also includes a small **OSC** button. Clicking it copies that parameter's OSC route to the clipboard.
The control UI also has a **Screenshot** button. It queues a capture of the final output render target and writes a PNG under:
```text ```text
runtime/screenshots/ runtime/screenshots/
@@ -210,7 +223,7 @@ shaders/<id>/
optional-font-or-texture-assets optional-font-or-texture-assets
``` ```
See `SHADER_CONTRACT.md` for the manifest schema, parameter types, texture assets, font/text assets, temporal history support, optional render-pass declarations, and the Slang entry point contract. `shaders/text-overlay/` is the reference live text package and bundles Roboto Regular with its OFL license. See `SHADER_CONTRACT.md` for the manifest schema, parameter types, texture assets, font/text assets, temporal history support, optional render-pass declarations, and the Slang entry point contract. `shaders/text-overlay/` is the reference live text package and bundles Roboto Regular with its OFL license. Broken shader packages are shown as unavailable in the selector with their error text instead of preventing the app from launching.
## Generated Files ## Generated Files
@@ -250,14 +263,13 @@ If `SLANG_ROOT` is not set, the workflow falls back to the repo-local default un
- Audio. - Audio.
- Genlock. - Genlock.
- Find a better UI library for React.
- Logs. - Logs.
- Add more video I/O backends now that the DeckLink path is behind `videoio/`. - Add more video I/O backends now that the DeckLink path is behind `videoio/`.
- Support a separate sound shader `.slang` file in shader packages. (https://www.shadertoy.com/view/XsBXWt) - Support a separate sound shader `.slang` file in shader packages. (https://www.shadertoy.com/view/XsBXWt)
- Add WebView2 - Add WebView2 for an embedded native control surface.
- MSDF typography rasterisation - MSDF typography rasterisation
- More shader-library organisation and filtering as the built-in library grows. - More shader-library organisation and filtering as the built-in library grows.
- linear compositing? - Optional linear-light compositing mode.
- compute shaders or a small 1x1 or nx1 RGBA16f render target for arbitrary data storage - compute shaders or a small 1x1 or nx1 RGBA16f render target for arbitrary data storage
- allow shaders to read other shaders data store based on name? or output over OSC - allow shaders to read other shaders data store based on name? or output over OSC
- Mipmapping for shader-declared textures - Mipmapping for shader-declared textures

View File

@@ -55,7 +55,7 @@ float4 shadeVideo(ShaderContext context)
} }
``` ```
With `autoReload` enabled in `config/runtime-host.json`, edits to shader source, manifests, and declared texture assets are picked up automatically. With `autoReload` enabled in `config/runtime-host.json`, edits to shader source, manifests, and declared texture assets are picked up automatically. You can also use **Reload shaders** in the control UI to manually rescan the shader library.
## Guidance For Shaders ## Guidance For Shaders
@@ -80,7 +80,7 @@ Important rules:
- If adapting third-party code, include attribution and source URL in the manifest description when the license allows adaptation. - If adapting third-party code, include attribution and source URL in the manifest description when the license allows adaptation.
- If the source license is unclear or incompatible, do not add the shader package. - If the source license is unclear or incompatible, do not add the shader package.
Before finishing, compile-check the shader through the runtime wrapper or launch the app and verify the shader appears without an error in the selector. Before finishing, compile-check the shader through the runtime wrapper or launch the app and verify the shader appears without an error in the selector. CI also runs shader validation, so every available package in `shaders/` should compile successfully. Intentionally broken examples should stay visibly marked as broken rather than pretending to be production shaders.
## Manifest Fields ## Manifest Fields
@@ -102,7 +102,7 @@ Optional fields:
- `fonts`: packaged font assets for live text parameters. - `fonts`: packaged font assets for live text parameters.
- `temporal`: history-buffer requirements. - `temporal`: history-buffer requirements.
Parameter objects may also include an optional `description` string. The control UI displays it as helper text underneath the parameter label, so use it for short operational guidance rather than long documentation. Parameter objects may also include an optional `description` string. The control UI displays it as one-line helper text with the full text available on hover, so use it for short operational guidance rather than long documentation.
Shader-visible identifiers must be valid Slang-style identifiers: Shader-visible identifiers must be valid Slang-style identifiers:
@@ -126,7 +126,7 @@ Most shaders should omit `passes`. The runtime then creates one implicit pass:
} }
``` ```
Advanced shaders may declare explicit passes: Advanced shaders may declare explicit passes. All passes may live in one `.slang` file by using different `entryPoint` values, or they may be split across multiple source files:
```json ```json
{ {
@@ -165,6 +165,28 @@ Pass input names:
If `inputs` is omitted, the first pass samples `layerInput` and later passes sample `previousPass`. If `inputs` is omitted, the first pass samples `layerInput` and later passes sample `previousPass`.
Single-file multipass example:
```json
{
"passes": [
{
"id": "mask",
"source": "shader.slang",
"entryPoint": "makeMask",
"output": "maskBuffer"
},
{
"id": "final",
"source": "shader.slang",
"entryPoint": "finish",
"inputs": ["maskBuffer"],
"output": "layerOutput"
}
]
}
```
Pass output names: Pass output names:
- `layerOutput`: the final visible output of this layer. - `layerOutput`: the final visible output of this layer.
@@ -609,6 +631,8 @@ When a shader compiles, the runtime writes generated files under `runtime/shader
These files are ignored by git and are useful for debugging compiler output. If a shader fails to compile, inspect the wrapper first; it shows the exact generated Slang code including your included shader. These files are ignored by git and are useful for debugging compiler output. If a shader fails to compile, inspect the wrapper first; it shows the exact generated Slang code including your included shader.
For multipass shaders, these files reflect the most recently compiled pass. If a package has several passes, the reported compile error and pass name are usually more useful than assuming the cache contains the first pass.
## Common Pitfalls ## Common Pitfalls
- Do not use hyphens in parameter IDs, texture IDs, or entry point names. - Do not use hyphens in parameter IDs, texture IDs, or entry point names.

View File

@@ -47,6 +47,8 @@ Matching is exact first. If that fails, names are compared in a simplified form
If multiple layers use the same shader package ID or display name, the first matching layer in the stack is controlled. Use the internal layer ID shown in the UI when you need to target one duplicate layer precisely. If multiple layers use the same shader package ID or display name, the first matching layer in the stack is controlled. Use the internal layer ID shown in the UI when you need to target one duplicate layer precisely.
In the control UI, each parameter row has a small **OSC** button. Clicking it copies that parameter's exact OSC address to the clipboard, which is the safest way to target controls with long names or duplicate shader layers.
## Values ## Values
The listener accepts these OSC argument types: The listener accepts these OSC argument types:
@@ -65,7 +67,7 @@ Examples:
/VideoShaderToys/fisheye-reproject/panDegrees 45.0 /VideoShaderToys/fisheye-reproject/panDegrees 45.0
/VideoShaderToys/fisheye-reproject/fisheyeModel "equisolid" /VideoShaderToys/fisheye-reproject/fisheyeModel "equisolid"
/VideoShaderToys/video-transform/pan 0.25 -0.5 /VideoShaderToys/video-transform/pan 0.25 -0.5
/VideoShaderToys/composition-guides/lineColor 1.0 0.8 0.1 1.0 /VideoShaderToys/safe-area-guides/lineColor 1.0 0.8 0.1 1.0
``` ```
Values are validated with the same shader parameter rules used by the REST API. Invalid values or unknown addresses are ignored and reported to the native debug output. Values are validated with the same shader parameter rules used by the REST API. Invalid values or unknown addresses are ignored and reported to the native debug output.

View File

@@ -201,6 +201,7 @@ paths:
post: post:
tags: [Runtime] tags: [Runtime]
summary: Reload shaders summary: Reload shaders
description: Rescans the shader library, re-reads manifests, queues shader compilation, and refreshes shader availability/errors. If a changed shader fails, the previous working stack remains active where possible.
operationId: reloadShaders operationId: reloadShaders
requestBody: requestBody:
required: false required: false
@@ -465,6 +466,18 @@ components:
type: number type: number
budgetUsedPercent: budgetUsedPercent:
type: number type: number
completionIntervalMs:
type: number
smoothedCompletionIntervalMs:
type: number
maxCompletionIntervalMs:
type: number
lateFrameCount:
type: number
droppedFrameCount:
type: number
flushedFrameCount:
type: number
ShaderSummary: ShaderSummary:
type: object type: object
properties: properties:
@@ -476,6 +489,12 @@ components:
type: string type: string
category: category:
type: string type: string
available:
type: boolean
description: False when the shader package exists but failed manifest or compile validation.
error:
type: string
description: Error text for unavailable shader packages.
temporal: temporal:
$ref: "#/components/schemas/TemporalState" $ref: "#/components/schemas/TemporalState"
TemporalState: TemporalState:
@@ -514,9 +533,21 @@ components:
type: string type: string
label: label:
type: string type: string
description:
type: string
description: Short helper text shown under the parameter label in the control UI.
type: type:
type: string type: string
enum: [float, vec2, color, bool, enum, text, trigger] enum: [float, vec2, color, bool, enum, text, trigger]
defaultValue:
description: Default parameter value from the shader manifest.
oneOf:
- type: number
- type: boolean
- type: string
- type: array
items:
type: number
min: min:
type: array type: array
items: items:
@@ -533,6 +564,12 @@ components:
type: array type: array
items: items:
$ref: "#/components/schemas/ParameterOption" $ref: "#/components/schemas/ParameterOption"
maxLength:
type: number
description: Maximum length for text parameters.
font:
type: string
description: Font asset id used by text parameters, when declared.
value: value:
description: Current parameter value. description: Current parameter value.
oneOf: oneOf:

View File

@@ -14,9 +14,9 @@ Packaged documentation:
Generated files: Generated files:
- `shader_cache/active_shader_wrapper.slang`: generated Slang wrapper for the active shader/layer. - `shader_cache/active_shader_wrapper.slang`: generated Slang wrapper for the most recently compiled shader pass.
- `shader_cache/active_shader.raw.frag`: raw GLSL emitted by `slangc`. - `shader_cache/active_shader.raw.frag`: raw GLSL emitted by `slangc` for the most recently compiled pass.
- `shader_cache/active_shader.frag`: patched GLSL consumed by the OpenGL path. - `shader_cache/active_shader.frag`: patched GLSL consumed by the OpenGL path for the most recently compiled pass.
- `runtime_state.json`: autosaved latest layer stack, layer order, bypass state, shader assignments, and parameter values. The host reloads this file on startup. - `runtime_state.json`: autosaved latest layer stack, layer order, bypass state, shader assignments, and parameter values. The host reloads this file on startup.
- `stack_presets/*.json`: user-saved layer stack presets. - `stack_presets/*.json`: user-saved layer stack presets.
- `screenshots/*.png`: screenshots captured from the final output render target through the control UI/API. - `screenshots/*.png`: screenshots captured from the final output render target through the control UI/API.