#wgsl-edit
Web component for editing WESL/WGSL with CodeMirror 6. Features syntax highlighting, linting, multi-file tabs, and light/dark themes out of the box.
#Installation
npm install wgsl-edit
#Usage
<script type="module">import "wgsl-edit";</script>
<wgsl-edit></wgsl-edit>
#Inline Source
Include shader code directly via <script> tags.
Multiple tags create a multi-file editor with tabs:
<wgsl-edit>
<script type="text/wesl" data-name="main.wesl">
import package::utils;
@fragment fn main(@builtin(position) pos: vec4f) -> @location(0) vec4f {
return vec4f(utils::gradient(pos.xy), 1.0);
}
</script>
<script type="text/wesl" data-name="utils.wesl">
fn gradient(uv: vec2f) -> vec3f { return vec3f(uv, 0.5); }
</script>
</wgsl-edit>
#With wgsl-play
Link an editor to a player for live shader preview:
<wgsl-edit id="editor" lint-from="player" theme="auto">
<script type="text/wesl">/* shader code */</script>
</wgsl-edit>
<wgsl-play id="player" source="editor"></wgsl-play>
The play component reads sources from the editor and live-previews the shader.
#Programmatic Control
const editor = document.querySelector("wgsl-edit");
editor.source = shaderCode; // set active file content
editor.sources = { // set all files
"package::main": mainCode,
"package::utils": utilsCode,
};
editor.addFile("helpers.wesl", code); // add a file
editor.activeFile = "helpers.wesl"; // switch tabs
#Using with wesl-plugin
For more control, use wesl-plugin to assemble shaders and libraries at build time.
import shaderConfig from "./shader.wesl?link";
editor.project = {
...shaderConfig,
conditions: { MOBILE: isMobileGPU },
constants: { num_lights: 4 }
};
#API Reference
#Attributes
| Attribute | Values | Default | Description |
|---|---|---|---|
src |
URL | - | Load source from URL |
theme |
light dark auto |
auto |
Color theme |
readonly |
boolean | false |
Disable editing |
tabs |
boolean | true |
Show tab bar |
lint |
on off |
on |
Real-time WESL validation |
lint-from |
element ID | - | Element ID of a wgsl-play to receive compile errors from |
line-numbers |
true false |
false |
Show line numbers |
shader-root |
string | - | Root path for shader imports |
#Properties
| Property | Type | Description |
|---|---|---|
source |
string |
Get/set active file content |
sources |
Record<string, string> |
Get/set all files (keyed by module path) |
project |
WeslProject |
Set full project (sources, conditions, packageName, etc.) |
activeFile |
string |
Get/set active file name |
fileNames |
string[] |
List all file names |
#Methods
| Method | Description |
|---|---|
addFile(name, content?) |
Add a new file |
removeFile(name) |
Remove a file |
renameFile(oldName, newName) |
Rename a file |
#Events
| Event | Detail | Description |
|---|---|---|
change |
{ source, sources, activeFile } |
Any edit |
file-change |
{ action, file } |
File add/remove/rename |
#CLI
Edit a shader file in the browser with live reload:
npx wgsl-edit path/to/shader.wesl
npx wgsl-edit shader.wgsl --port 3000 --no-open
#Bundle Size
~136 KB brotli for the full bundle with all dependencies.
| Component | Brotli |
|---|---|
| CodeMirror | ~104 KB |
| lezer-wesl (grammar + lezer runtime) | ~26 KB |
| wesl linker (powers live linting) | ~14 KB |