@gjsify/webgl 0.22.0 → 0.23.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/README.md CHANGED
@@ -30,9 +30,43 @@ widget.onReady((canvas, gl) => {
30
30
  window.set_child(widget);
31
31
  ```
32
32
 
33
+ ## Globals
34
+
35
+ The package root is a **side-effect-free barrel** — importing it gives you named
36
+ exports and nothing else. Browser globals are installed by the dedicated
37
+ `/register` subpath:
38
+
39
+ ```typescript
40
+ import '@gjsify/webgl/register'; // globalThis.WebGLRenderingContext, globalThis.WebGL2RenderingContext
41
+ ```
42
+
43
+ You normally never write that import: `gjsify build` defaults to `--globals auto`,
44
+ which detects a free `WebGLRenderingContext` / `WebGL2RenderingContext` reference in
45
+ the bundled output and injects the subpath for you. Application and example code
46
+ should rely on that (see the tree-shakeable-globals convention in `AGENTS.md`) — an
47
+ explicit `/register` import in app code hides auto-detection gaps.
48
+
49
+ What each entry point gives you:
50
+
51
+ | | `@gjsify/webgl` | `@gjsify/webgl/register` | `WebGLBridge.installGlobals()` |
52
+ |---|---|---|---|
53
+ | `WebGLRenderingContext`, `WebGL2RenderingContext`, `HTMLCanvasElement`, `WebGLBridge`, the WebGL object + extension classes | named exports | — | — |
54
+ | `globalThis.WebGLRenderingContext`, `globalThis.WebGL2RenderingContext` | — | ✅ (installed only when absent) | ✅ (installed unconditionally) |
55
+ | `globalThis.requestAnimationFrame`, `globalThis.cancelAnimationFrame`, `globalThis.performance` | — | — | ✅ |
56
+
57
+ The `'webgl'` / `'webgl2'` contexts themselves need no register: this package's
58
+ `HTMLCanvasElement` subclass answers `getContext('webgl')` directly, so a
59
+ `WebGLBridge` works even with `--globals none`.
60
+
61
+ > **Changed after 0.22.0** — up to and including 0.22.0, `import { WebGLBridge } from '@gjsify/webgl'`
62
+ > installed `WebGLRenderingContext` / `WebGL2RenderingContext` on `globalThis` as an
63
+ > import side effect. They now come from `/register` (or `installGlobals()`). See
64
+ > [ADR 0012](https://github.com/gjsify/gjsify/blob/main/docs/adr/0012-framework-register-ownership.md).
65
+
33
66
  ## Running GJS apps that use this package
34
67
 
35
- This package ships prebuilt native libraries for supported platforms:
68
+ This package ships prebuilt native libraries for the platforms listed under
69
+ [Platform coverage](#platform-coverage) — today that is Linux only:
36
70
 
37
71
  ```
38
72
  prebuilds/
@@ -43,6 +77,9 @@ prebuilds/
43
77
  linux-riscv64/ libgwebgl.so + Gwebgl-0.1.typelib
44
78
  ```
45
79
 
80
+ There is **no macOS or Windows prebuild**; on those platforms `getContext('webgl')`
81
+ has no native backend.
82
+
46
83
  Use the gjsify CLI to run your app — it automatically sets `LD_LIBRARY_PATH` and
47
84
  `GI_TYPELIB_PATH` so GJS can find the native library:
48
85
 
@@ -86,6 +123,25 @@ to the repository. They are included in the npm package via the `files` field.
86
123
  - [stackgl/headless-gl](https://github.com/stackgl/headless-gl)
87
124
  - [Maia-Everett/valagl](https://github.com/Maia-Everett/valagl)
88
125
 
126
+ ## Platform coverage
127
+
128
+ | Platform | Prebuild | Built by |
129
+ |---|---|---|
130
+ | `linux-x86_64` | ✅ `libgwebgl.so` + `Gwebgl-0.1.typelib` | native runner |
131
+ | `linux-aarch64` | ✅ | native runner |
132
+ | `linux-ppc64`, `linux-s390x`, `linux-riscv64` | ✅ | QEMU emulation |
133
+ | macOS (`darwin-arm64` / `darwin-x64`) | ❌ | **unverified, see below** |
134
+ | Windows | ❌ | — no Vala/GI bridge in this repo targets Windows |
135
+
136
+ **macOS is not blocked — it is unverified, and a green build would not be enough.** The
137
+ build needs gtk4 + libepoxy + gdk-pixbuf from Homebrew (all available). The real question is
138
+ runtime: GTK4's macOS (Quartz) backend goes through CGL, which tops out at desktop OpenGL 4.1
139
+ Core and offers no GLES 3.2 — the profile this Vala bridge is written against. So compiling
140
+ successfully on macOS would say nothing about whether `Gtk.GLArea` can actually render a
141
+ WebGL2 context there. `meson.build` already emits the correct `.dylib` typelib leaf; the
142
+ manual-dispatch `build-prebuilds-macos-experimental` job in the prebuilds workflow exists to
143
+ establish the compile half of the answer.
144
+
89
145
  ## License
90
146
 
91
147
  MIT
package/lib/esm/index.js CHANGED
@@ -1 +1 @@
1
- import{WebGLContextAttributes as e}from"./webgl-context-attributes.js";import{WebGLUniformLocation as t}from"./webgl-uniform-location.js";import{OESElementIndexUint as n,getOESElementIndexUint as r}from"./extensions/oes-element-index-unit.js";import{OESStandardDerivatives as i,getOESStandardDerivatives as a}from"./extensions/oes-standard-derivatives.js";import{OESTextureFloat as o,getOESTextureFloat as s}from"./extensions/oes-texture-float.js";import{OESTextureFloatLinear as c,getOESTextureFloatLinear as l}from"./extensions/oes-texture-float-linear.js";import{STACKGLDestroyContext as u,getSTACKGLDestroyContext as d}from"./extensions/stackgl-destroy-context.js";import{STACKGLResizeDrawingBuffer as f,getSTACKGLResizeDrawingBuffer as p}from"./extensions/stackgl-resize-drawing-buffer.js";import{EXTBlendMinMax as m,getEXTBlendMinMax as h}from"./extensions/ext-blend-minmax.js";import{EXTColorBufferFloat as g,getEXTColorBufferFloat as _}from"./extensions/ext-color-buffer-float.js";import{EXTColorBufferHalfFloat as v,getEXTColorBufferHalfFloat as y}from"./extensions/ext-color-buffer-half-float.js";import{EXTTextureFilterAnisotropic as b,getEXTTextureFilterAnisotropic as x}from"./extensions/ext-texture-filter-anisotropic.js";import{OESTextureHalfFloat as S,getOESTextureHalfFloat as C}from"./extensions/oes-texture-half-float.js";import{WebGLTextureUnit as w}from"./webgl-texture-unit.js";import{WebGLBuffer as T}from"./webgl-buffer.js";import{WebGLVertexArrayGlobalAttribute as E,WebGLVertexArrayGlobalState as D,WebGLVertexArrayObjectAttribute as O,WebGLVertexArrayObjectState as k}from"./webgl-vertex-attribute.js";import{WebGLFramebuffer as A}from"./webgl-framebuffer.js";import{WebGLProgram as j}from"./webgl-program.js";import{WebGLRenderbuffer as M}from"./webgl-renderbuffer.js";import{WebGLShader as N}from"./webgl-shader.js";import{WebGLTexture as P}from"./webgl-texture.js";import{WebGLDrawingBufferWrapper as F}from"./webgl-drawing-buffer-wrapper.js";import{WebGLShaderPrecisionFormat as I}from"./webgl-shader-precision-format.js";import{WebGLActiveInfo as L}from"./webgl-active-info.js";import{WebGLContextBase as R}from"./webgl-context-base.js";import{WebGLRenderingContext as z}from"./webgl-rendering-context.js";import{WebGLQuery as B}from"./webgl-query.js";import{WebGLSampler as V}from"./webgl-sampler.js";import{WebGLSync as H}from"./webgl-sync.js";import{WebGLTransformFeedback as U}from"./webgl-transform-feedback.js";import{WebGLVertexArrayObject as W}from"./webgl-vertex-array-object.js";import{WebGL2RenderingContext as G}from"./webgl2-rendering-context.js";import{HTMLCanvasElement as K}from"./html-canvas-element.js";import{WebGLBridge as q}from"./webgl-bridge.js";import"@girs/gtk-4.0";import"@girs/gjs";import"@girs/gio-2.0";const J=globalThis;J.WebGLRenderingContext=z,J.WebGL2RenderingContext=G;export{m as EXTBlendMinMax,g as EXTColorBufferFloat,v as EXTColorBufferHalfFloat,b as EXTTextureFilterAnisotropic,K as HTMLCanvasElement,n as OESElementIndexUint,i as OESStandardDerivatives,o as OESTextureFloat,c as OESTextureFloatLinear,S as OESTextureHalfFloat,u as STACKGLDestroyContext,f as STACKGLResizeDrawingBuffer,G as WebGL2RenderingContext,L as WebGLActiveInfo,q as WebGLBridge,T as WebGLBuffer,e as WebGLContextAttributes,R as WebGLContextBase,F as WebGLDrawingBufferWrapper,A as WebGLFramebuffer,j as WebGLProgram,B as WebGLQuery,M as WebGLRenderbuffer,z as WebGLRenderingContext,V as WebGLSampler,N as WebGLShader,I as WebGLShaderPrecisionFormat,H as WebGLSync,P as WebGLTexture,w as WebGLTextureUnit,U as WebGLTransformFeedback,t as WebGLUniformLocation,E as WebGLVertexArrayGlobalAttribute,D as WebGLVertexArrayGlobalState,W as WebGLVertexArrayObject,O as WebGLVertexArrayObjectAttribute,k as WebGLVertexArrayObjectState,h as getEXTBlendMinMax,_ as getEXTColorBufferFloat,y as getEXTColorBufferHalfFloat,x as getEXTTextureFilterAnisotropic,r as getOESElementIndexUint,a as getOESStandardDerivatives,s as getOESTextureFloat,l as getOESTextureFloatLinear,C as getOESTextureHalfFloat,d as getSTACKGLDestroyContext,p as getSTACKGLResizeDrawingBuffer};
1
+ import{WebGLContextAttributes as e}from"./webgl-context-attributes.js";import{WebGLUniformLocation as t}from"./webgl-uniform-location.js";import{OESElementIndexUint as n,getOESElementIndexUint as r}from"./extensions/oes-element-index-unit.js";import{OESStandardDerivatives as i,getOESStandardDerivatives as a}from"./extensions/oes-standard-derivatives.js";import{OESTextureFloat as o,getOESTextureFloat as s}from"./extensions/oes-texture-float.js";import{OESTextureFloatLinear as c,getOESTextureFloatLinear as l}from"./extensions/oes-texture-float-linear.js";import{STACKGLDestroyContext as u,getSTACKGLDestroyContext as d}from"./extensions/stackgl-destroy-context.js";import{STACKGLResizeDrawingBuffer as f,getSTACKGLResizeDrawingBuffer as p}from"./extensions/stackgl-resize-drawing-buffer.js";import{EXTBlendMinMax as m,getEXTBlendMinMax as h}from"./extensions/ext-blend-minmax.js";import{EXTColorBufferFloat as g,getEXTColorBufferFloat as _}from"./extensions/ext-color-buffer-float.js";import{EXTColorBufferHalfFloat as v,getEXTColorBufferHalfFloat as y}from"./extensions/ext-color-buffer-half-float.js";import{EXTTextureFilterAnisotropic as b,getEXTTextureFilterAnisotropic as x}from"./extensions/ext-texture-filter-anisotropic.js";import{OESTextureHalfFloat as S,getOESTextureHalfFloat as C}from"./extensions/oes-texture-half-float.js";import{WebGLTextureUnit as w}from"./webgl-texture-unit.js";import{WebGLBuffer as T}from"./webgl-buffer.js";import{WebGLVertexArrayGlobalAttribute as E,WebGLVertexArrayGlobalState as D,WebGLVertexArrayObjectAttribute as O,WebGLVertexArrayObjectState as k}from"./webgl-vertex-attribute.js";import{WebGLFramebuffer as A}from"./webgl-framebuffer.js";import{WebGLProgram as j}from"./webgl-program.js";import{WebGLRenderbuffer as M}from"./webgl-renderbuffer.js";import{WebGLShader as N}from"./webgl-shader.js";import{WebGLTexture as P}from"./webgl-texture.js";import{WebGLDrawingBufferWrapper as F}from"./webgl-drawing-buffer-wrapper.js";import{WebGLShaderPrecisionFormat as I}from"./webgl-shader-precision-format.js";import{WebGLActiveInfo as L}from"./webgl-active-info.js";import{WebGLContextBase as R}from"./webgl-context-base.js";import{WebGLRenderingContext as z}from"./webgl-rendering-context.js";import{WebGLQuery as B}from"./webgl-query.js";import{WebGLSampler as V}from"./webgl-sampler.js";import{WebGLSync as H}from"./webgl-sync.js";import{WebGLTransformFeedback as U}from"./webgl-transform-feedback.js";import{WebGLVertexArrayObject as W}from"./webgl-vertex-array-object.js";import{WebGL2RenderingContext as G}from"./webgl2-rendering-context.js";import{HTMLCanvasElement as K}from"./html-canvas-element.js";import{WebGLBridge as q}from"./webgl-bridge.js";import"@girs/gtk-4.0";import"@girs/gjs";import"@girs/gio-2.0";export{m as EXTBlendMinMax,g as EXTColorBufferFloat,v as EXTColorBufferHalfFloat,b as EXTTextureFilterAnisotropic,K as HTMLCanvasElement,n as OESElementIndexUint,i as OESStandardDerivatives,o as OESTextureFloat,c as OESTextureFloatLinear,S as OESTextureHalfFloat,u as STACKGLDestroyContext,f as STACKGLResizeDrawingBuffer,G as WebGL2RenderingContext,L as WebGLActiveInfo,q as WebGLBridge,T as WebGLBuffer,e as WebGLContextAttributes,R as WebGLContextBase,F as WebGLDrawingBufferWrapper,A as WebGLFramebuffer,j as WebGLProgram,B as WebGLQuery,M as WebGLRenderbuffer,z as WebGLRenderingContext,V as WebGLSampler,N as WebGLShader,I as WebGLShaderPrecisionFormat,H as WebGLSync,P as WebGLTexture,w as WebGLTextureUnit,U as WebGLTransformFeedback,t as WebGLUniformLocation,E as WebGLVertexArrayGlobalAttribute,D as WebGLVertexArrayGlobalState,W as WebGLVertexArrayObject,O as WebGLVertexArrayObjectAttribute,k as WebGLVertexArrayObjectState,h as getEXTBlendMinMax,_ as getEXTColorBufferFloat,y as getEXTColorBufferHalfFloat,x as getEXTTextureFilterAnisotropic,r as getOESElementIndexUint,a as getOESStandardDerivatives,s as getOESTextureFloat,l as getOESTextureFloatLinear,C as getOESTextureHalfFloat,d as getSTACKGLDestroyContext,p as getSTACKGLResizeDrawingBuffer};
@@ -0,0 +1 @@
1
+ import"./_virtual/_rolldown/runtime.js";import{WebGLRenderingContext as e}from"./webgl-rendering-context.js";import{WebGL2RenderingContext as t}from"./webgl2-rendering-context.js";function defineGlobalIfMissing(e,t){globalThis[e]===void 0&&Object.defineProperty(globalThis,e,{value:t,writable:!0,configurable:!0})}defineGlobalIfMissing(`WebGLRenderingContext`,e),defineGlobalIfMissing(`WebGL2RenderingContext`,t);
@@ -0,0 +1 @@
1
+ import{__name as e}from"./_virtual/_rolldown/runtime.js";import{describe as t,expect as n,it as r,on as i}from"@gjsify/unit";import{WebGL2RenderingContext as a,WebGLContextBase as o,WebGLRenderingContext as s}from"@gjsify/webgl";import"@gjsify/webgl/register";var c=e(async()=>{await i(`Gjs`,async()=>{await t(`@gjsify/webgl/register — owned globals`,async()=>{await r(`installs WebGLRenderingContext on globalThis`,async()=>{let e=globalThis;n(typeof e.WebGLRenderingContext).toBe(`function`),n(e.WebGLRenderingContext).toBe(s)}),await r(`installs WebGL2RenderingContext on globalThis`,async()=>{let e=globalThis;n(typeof e.WebGL2RenderingContext).toBe(`function`),n(e.WebGL2RenderingContext).toBe(a)}),await r(`installs two distinct constructors over the shared context base`,async()=>{let e=globalThis,t=e.WebGLRenderingContext,r=e.WebGL2RenderingContext;n(t).not.toBe(r),n(Object.getPrototypeOf(t.prototype)).toBe(o.prototype),n(Object.getPrototypeOf(r.prototype)).toBe(o.prototype)})}),await t(`@gjsify/webgl/register — idempotency`,async()=>{for(let e of[`WebGLRenderingContext`,`WebGL2RenderingContext`])await r(`${e} is installed writable + configurable`,async()=>{let t=Object.getOwnPropertyDescriptor(globalThis,e);n(t).toBeDefined(),n(t?.writable).toBe(!0),n(t?.configurable).toBe(!0)}),await r(`re-defining ${e} does not throw`,async()=>{let t=Object.getOwnPropertyDescriptor(globalThis,e),r=!1;try{Object.defineProperty(globalThis,e,t)}catch{r=!0}n(r).toBe(!1)})})})},`default`);export{c as default};
package/lib/esm/test.js CHANGED
@@ -1 +1 @@
1
- import"./_virtual/_rolldown/runtime.js";import e from"./webgl1.spec.js";import t from"./webgl2.spec.js";import{run as n}from"@gjsify/unit";n({testSuite:async()=>{await e(),await t()}});
1
+ import"./_virtual/_rolldown/runtime.js";import e from"./register.spec.js";import t from"./webgl1.spec.js";import n from"./webgl2.spec.js";import{run as r}from"@gjsify/unit";r({testSuite:async()=>{await t(),await n()},registerSuite:e});
@@ -1 +1 @@
1
- import"./_virtual/_rolldown/runtime.js";import{HTMLCanvasElement as e}from"./html-canvas-element.js";import{notifyElementResize as t}from"@gjsify/dom-elements";import n from"gi://GObject";import r from"gi://GLib?version=2.0";import i from"gi://Gtk?version=4.0";import{attachEventControllers as a}from"@gjsify/event-bridge";import{Event as o}from"@gjsify/dom-events";const s=n.registerClass({GTypeName:`GjsifyWebGLBridge`},class WebGLBridge extends i.GLArea{constructor(n){super(n),this._canvas=null,this._readyCallbacks=[],this._resizeCallbacks=[],this._renderTag=null,this._tickCallbackId=null,this._frameCallback=null,this._lastFrameCallback=null,this._lastFrameTime=0,this._replaying=!1,this._frameCallbackId=0,this._nextFrameId=1,this._timeOrigin=r.get_monotonic_time(),this.set_use_es(!0),this.set_required_version(3,2),this.set_has_depth_buffer(!0),this.set_has_stencil_buffer(!0),a(this,()=>this._canvas,{captureKeys:!0}),this._tickCallbackId=this.add_tick_callback((e,t)=>(this._frameCallback!==null&&this.queue_render(),r.SOURCE_CONTINUE));let i=this.connect(`render`,()=>{this.disconnect(i),this.make_current(),this._canvas=new e(this);{let e=globalThis;e.document?.body&&e.document.body.appendChild(this._canvas)}this._canvas.getContext(`webgl2`);let t=this._canvas.getContext(`webgl`);if(t){for(let e of this._readyCallbacks)e(this._canvas,t);this._readyCallbacks=[]}return this._renderTag=this.connect(`render`,e=>{let t=(r.get_monotonic_time()-this._timeOrigin)/1e3;if(this._frameCallback!==null){globalThis.__GJSIFY_DEBUG_RAF===!0&&console.log(`[rAF] frame callback fires t=${t.toFixed(1)}`);let e=this._frameCallback;this._frameCallback=null,this._frameCallbackId=0,this._lastFrameCallback=e,this._lastFrameTime=t,e(t)}else if(this._lastFrameCallback!==null){this._replaying=!0;try{this._lastFrameCallback(this._lastFrameTime)}finally{this._replaying=!1}}return!0}),!0});this.connect(`resize`,()=>{let e=this.get_allocated_width(),n=this.get_allocated_height();this._canvas&&(this._canvas.dispatchEvent(new o(`resize`)),t(this._canvas,e,n));for(let t of this._resizeCallbacks)t(e,n);this._frameCallback&&this.requestAnimationFrame(this._frameCallback)}),this.connect(`unrealize`,()=>{this._renderTag!==null&&(this.disconnect(this._renderTag),this._renderTag=null),this._tickCallbackId!==null&&(this.remove_tick_callback(this._tickCallbackId),this._tickCallbackId=null),this._frameCallback=null,this._lastFrameCallback=null,this._lastFrameTime=0,this._replaying=!1,this._canvas=null})}get canvas(){return this._canvas}onReady(e){if(this._canvas){let t=this._canvas.getContext(`webgl`);if(t){e(this._canvas,t);return}}this._readyCallbacks.push(e)}onWebGLReady(e){this.onReady(e)}onResize(e){this._resizeCallbacks.push(e)}requestAnimationFrame(e){let t=this._nextFrameId++;return this._replaying?t:(this._frameCallback=e,this._frameCallbackId=t,this.queue_render(),t)}cancelAnimationFrame(e){e!==0&&e===this._frameCallbackId&&(this._frameCallback=null,this._frameCallbackId=0,this._lastFrameCallback=null,this._lastFrameTime=0)}installGlobals(){let e=globalThis;e.requestAnimationFrame=e=>this.requestAnimationFrame(e),e.cancelAnimationFrame=e=>this.cancelAnimationFrame(e);let t=this._timeOrigin;e.performance={now:()=>(r.get_monotonic_time()-t)/1e3,timeOrigin:Date.now()}}});export{s as WebGLBridge};
1
+ import"./_virtual/_rolldown/runtime.js";import{WebGLRenderingContext as e}from"./webgl-rendering-context.js";import{WebGL2RenderingContext as t}from"./webgl2-rendering-context.js";import{HTMLCanvasElement as n}from"./html-canvas-element.js";import{notifyElementResize as r}from"@gjsify/dom-elements";import i from"gi://GObject";import a from"gi://GLib?version=2.0";import o from"gi://Gtk?version=4.0";import{attachEventControllers as s}from"@gjsify/event-bridge";import{Event as c}from"@gjsify/dom-events";const l=i.registerClass({GTypeName:`GjsifyWebGLBridge`},class WebGLBridge extends o.GLArea{constructor(e){super(e),this._canvas=null,this._readyCallbacks=[],this._resizeCallbacks=[],this._renderTag=null,this._tickCallbackId=null,this._frameCallback=null,this._lastFrameCallback=null,this._lastFrameTime=0,this._replaying=!1,this._frameCallbackId=0,this._nextFrameId=1,this._timeOrigin=a.get_monotonic_time(),this.set_use_es(!0),this.set_required_version(3,2),this.set_has_depth_buffer(!0),this.set_has_stencil_buffer(!0),s(this,()=>this._canvas,{captureKeys:!0}),this._tickCallbackId=this.add_tick_callback((e,t)=>(this._frameCallback!==null&&this.queue_render(),a.SOURCE_CONTINUE));let t=this.connect(`render`,()=>{this.disconnect(t),this.make_current(),this._canvas=new n(this);{let e=globalThis;e.document?.body&&e.document.body.appendChild(this._canvas)}this._canvas.getContext(`webgl2`);let e=this._canvas.getContext(`webgl`);if(e){for(let t of this._readyCallbacks)t(this._canvas,e);this._readyCallbacks=[]}return this._renderTag=this.connect(`render`,e=>{let t=(a.get_monotonic_time()-this._timeOrigin)/1e3;if(this._frameCallback!==null){globalThis.__GJSIFY_DEBUG_RAF===!0&&console.log(`[rAF] frame callback fires t=${t.toFixed(1)}`);let e=this._frameCallback;this._frameCallback=null,this._frameCallbackId=0,this._lastFrameCallback=e,this._lastFrameTime=t,e(t)}else if(this._lastFrameCallback!==null){this._replaying=!0;try{this._lastFrameCallback(this._lastFrameTime)}finally{this._replaying=!1}}return!0}),!0});this.connect(`resize`,()=>{let e=this.get_allocated_width(),t=this.get_allocated_height();this._canvas&&(this._canvas.dispatchEvent(new c(`resize`)),r(this._canvas,e,t));for(let n of this._resizeCallbacks)n(e,t);this._frameCallback&&this.requestAnimationFrame(this._frameCallback)}),this.connect(`unrealize`,()=>{this._renderTag!==null&&(this.disconnect(this._renderTag),this._renderTag=null),this._tickCallbackId!==null&&(this.remove_tick_callback(this._tickCallbackId),this._tickCallbackId=null),this._frameCallback=null,this._lastFrameCallback=null,this._lastFrameTime=0,this._replaying=!1,this._canvas=null})}get canvas(){return this._canvas}onReady(e){if(this._canvas){let t=this._canvas.getContext(`webgl`);if(t){e(this._canvas,t);return}}this._readyCallbacks.push(e)}onWebGLReady(e){this.onReady(e)}onResize(e){this._resizeCallbacks.push(e)}requestAnimationFrame(e){let t=this._nextFrameId++;return this._replaying?t:(this._frameCallback=e,this._frameCallbackId=t,this.queue_render(),t)}cancelAnimationFrame(e){e!==0&&e===this._frameCallbackId&&(this._frameCallback=null,this._frameCallbackId=0,this._lastFrameCallback=null,this._lastFrameTime=0)}installGlobals(){let n=globalThis;n.requestAnimationFrame=e=>this.requestAnimationFrame(e),n.cancelAnimationFrame=e=>this.cancelAnimationFrame(e),n.WebGLRenderingContext=e,n.WebGL2RenderingContext=t;let r=this._timeOrigin;n.performance={now:()=>(a.get_monotonic_time()-r)/1e3,timeOrigin:Date.now()}}});export{l as WebGLBridge};
@@ -0,0 +1 @@
1
+ export {};
@@ -10,7 +10,8 @@ type WebGLReadyCallback = (canvas: globalThis.HTMLCanvasElement, gl: globalThis.
10
10
  * - Creates an `HTMLCanvasElement` wrapping the GLArea on first render
11
11
  * - Fires `onReady()` callbacks with (canvas, gl) once the context is available
12
12
  * - Provides `requestAnimationFrame()` backed by GTK frame clock (vsync) + render signal
13
- * - `installGlobals()` sets `globalThis.requestAnimationFrame` and `globalThis.performance`
13
+ * - `installGlobals()` sets `globalThis.{requestAnimationFrame, cancelAnimationFrame,
14
+ * performance, WebGLRenderingContext, WebGL2RenderingContext}`
14
15
  *
15
16
  * Usage:
16
17
  * ```ts
@@ -85,8 +86,18 @@ export declare const WebGLBridge: {
85
86
  */
86
87
  cancelAnimationFrame(id: number): void;
87
88
  /**
88
- * Sets browser globals (`requestAnimationFrame`, `performance`) so that
89
- * browser-targeted code (e.g. Three.js) works unchanged on GJS.
89
+ * Sets the browser globals this bridge owns — `requestAnimationFrame`,
90
+ * `cancelAnimationFrame`, `performance` and the two WebGL context
91
+ * constructors — so that browser-targeted code (e.g. Three.js) works
92
+ * unchanged on GJS.
93
+ *
94
+ * `WebGLRenderingContext` / `WebGL2RenderingContext` are installed
95
+ * UNCONDITIONALLY here: per ADR 0012 rule 5 a bridge's `installGlobals()`
96
+ * and its `/register` install the same set, `installGlobals()` being the
97
+ * explicit imperative path (`@gjsify/webgl/register` keeps the
98
+ * if-undefined guard instead). They used to reach `globalThis` for free
99
+ * as a side effect of importing the `@gjsify/webgl` barrel; moving that
100
+ * write into `register.ts` must not shrink what this method does.
90
101
  */
91
102
  installGlobals(): void;
92
103
  get allowed_apis(): Gdk.GLAPI;
@@ -570,8 +581,18 @@ export declare const WebGLBridge: {
570
581
  */
571
582
  cancelAnimationFrame(id: number): void;
572
583
  /**
573
- * Sets browser globals (`requestAnimationFrame`, `performance`) so that
574
- * browser-targeted code (e.g. Three.js) works unchanged on GJS.
584
+ * Sets the browser globals this bridge owns — `requestAnimationFrame`,
585
+ * `cancelAnimationFrame`, `performance` and the two WebGL context
586
+ * constructors — so that browser-targeted code (e.g. Three.js) works
587
+ * unchanged on GJS.
588
+ *
589
+ * `WebGLRenderingContext` / `WebGL2RenderingContext` are installed
590
+ * UNCONDITIONALLY here: per ADR 0012 rule 5 a bridge's `installGlobals()`
591
+ * and its `/register` install the same set, `installGlobals()` being the
592
+ * explicit imperative path (`@gjsify/webgl/register` keeps the
593
+ * if-undefined guard instead). They used to reach `globalThis` for free
594
+ * as a side effect of importing the `@gjsify/webgl` barrel; moving that
595
+ * write into `register.ts` must not shrink what this method does.
575
596
  */
576
597
  installGlobals(): void;
577
598
  get allowed_apis(): Gdk.GLAPI;
@@ -1055,8 +1076,18 @@ export declare const WebGLBridge: {
1055
1076
  */
1056
1077
  cancelAnimationFrame(id: number): void;
1057
1078
  /**
1058
- * Sets browser globals (`requestAnimationFrame`, `performance`) so that
1059
- * browser-targeted code (e.g. Three.js) works unchanged on GJS.
1079
+ * Sets the browser globals this bridge owns — `requestAnimationFrame`,
1080
+ * `cancelAnimationFrame`, `performance` and the two WebGL context
1081
+ * constructors — so that browser-targeted code (e.g. Three.js) works
1082
+ * unchanged on GJS.
1083
+ *
1084
+ * `WebGLRenderingContext` / `WebGL2RenderingContext` are installed
1085
+ * UNCONDITIONALLY here: per ADR 0012 rule 5 a bridge's `installGlobals()`
1086
+ * and its `/register` install the same set, `installGlobals()` being the
1087
+ * explicit imperative path (`@gjsify/webgl/register` keeps the
1088
+ * if-undefined guard instead). They used to reach `globalThis` for free
1089
+ * as a side effect of importing the `@gjsify/webgl` barrel; moving that
1090
+ * write into `register.ts` must not shrink what this method does.
1060
1091
  */
1061
1092
  installGlobals(): void;
1062
1093
  get allowed_apis(): Gdk.GLAPI;
@@ -1540,8 +1571,18 @@ export declare const WebGLBridge: {
1540
1571
  */
1541
1572
  cancelAnimationFrame(id: number): void;
1542
1573
  /**
1543
- * Sets browser globals (`requestAnimationFrame`, `performance`) so that
1544
- * browser-targeted code (e.g. Three.js) works unchanged on GJS.
1574
+ * Sets the browser globals this bridge owns — `requestAnimationFrame`,
1575
+ * `cancelAnimationFrame`, `performance` and the two WebGL context
1576
+ * constructors — so that browser-targeted code (e.g. Three.js) works
1577
+ * unchanged on GJS.
1578
+ *
1579
+ * `WebGLRenderingContext` / `WebGL2RenderingContext` are installed
1580
+ * UNCONDITIONALLY here: per ADR 0012 rule 5 a bridge's `installGlobals()`
1581
+ * and its `/register` install the same set, `installGlobals()` being the
1582
+ * explicit imperative path (`@gjsify/webgl/register` keeps the
1583
+ * if-undefined guard instead). They used to reach `globalThis` for free
1584
+ * as a side effect of importing the `@gjsify/webgl` barrel; moving that
1585
+ * write into `register.ts` must not shrink what this method does.
1545
1586
  */
1546
1587
  installGlobals(): void;
1547
1588
  get allowed_apis(): Gdk.GLAPI;
@@ -2025,8 +2066,18 @@ export declare const WebGLBridge: {
2025
2066
  */
2026
2067
  cancelAnimationFrame(id: number): void;
2027
2068
  /**
2028
- * Sets browser globals (`requestAnimationFrame`, `performance`) so that
2029
- * browser-targeted code (e.g. Three.js) works unchanged on GJS.
2069
+ * Sets the browser globals this bridge owns — `requestAnimationFrame`,
2070
+ * `cancelAnimationFrame`, `performance` and the two WebGL context
2071
+ * constructors — so that browser-targeted code (e.g. Three.js) works
2072
+ * unchanged on GJS.
2073
+ *
2074
+ * `WebGLRenderingContext` / `WebGL2RenderingContext` are installed
2075
+ * UNCONDITIONALLY here: per ADR 0012 rule 5 a bridge's `installGlobals()`
2076
+ * and its `/register` install the same set, `installGlobals()` being the
2077
+ * explicit imperative path (`@gjsify/webgl/register` keeps the
2078
+ * if-undefined guard instead). They used to reach `globalThis` for free
2079
+ * as a side effect of importing the `@gjsify/webgl` barrel; moving that
2080
+ * write into `register.ts` must not shrink what this method does.
2030
2081
  */
2031
2082
  installGlobals(): void;
2032
2083
  get allowed_apis(): Gdk.GLAPI;
@@ -2510,8 +2561,18 @@ export declare const WebGLBridge: {
2510
2561
  */
2511
2562
  cancelAnimationFrame(id: number): void;
2512
2563
  /**
2513
- * Sets browser globals (`requestAnimationFrame`, `performance`) so that
2514
- * browser-targeted code (e.g. Three.js) works unchanged on GJS.
2564
+ * Sets the browser globals this bridge owns — `requestAnimationFrame`,
2565
+ * `cancelAnimationFrame`, `performance` and the two WebGL context
2566
+ * constructors — so that browser-targeted code (e.g. Three.js) works
2567
+ * unchanged on GJS.
2568
+ *
2569
+ * `WebGLRenderingContext` / `WebGL2RenderingContext` are installed
2570
+ * UNCONDITIONALLY here: per ADR 0012 rule 5 a bridge's `installGlobals()`
2571
+ * and its `/register` install the same set, `installGlobals()` being the
2572
+ * explicit imperative path (`@gjsify/webgl/register` keeps the
2573
+ * if-undefined guard instead). They used to reach `globalThis` for free
2574
+ * as a side effect of importing the `@gjsify/webgl` barrel; moving that
2575
+ * write into `register.ts` must not shrink what this method does.
2515
2576
  */
2516
2577
  installGlobals(): void;
2517
2578
  get allowed_apis(): Gdk.GLAPI;
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@gjsify/webgl",
3
- "version": "0.22.0",
3
+ "version": "0.23.0",
4
4
  "description": "WebGL module for Gjs",
5
5
  "module": "lib/esm/index.js",
6
6
  "types": "lib/types/index.d.ts",
@@ -9,13 +9,27 @@
9
9
  ".": {
10
10
  "types": "./lib/types/index.d.ts",
11
11
  "default": "./lib/esm/index.js"
12
+ },
13
+ "./register": {
14
+ "types": "./lib/types/register.d.ts",
15
+ "default": "./lib/esm/register.js"
12
16
  }
13
17
  },
18
+ "sideEffects": [
19
+ "./lib/esm/register.js"
20
+ ],
14
21
  "files": [
15
22
  "lib",
16
23
  "prebuilds"
17
24
  ],
18
25
  "gjsify": {
26
+ "platforms": [
27
+ "linux-x86_64",
28
+ "linux-aarch64",
29
+ "linux-ppc64",
30
+ "linux-s390x",
31
+ "linux-riscv64"
32
+ ],
19
33
  "prebuilds": "prebuilds",
20
34
  "runtimes": {
21
35
  "gjs": "polyfill",
@@ -34,7 +48,7 @@
34
48
  "build:gjsify": "gjsify build --library 'src/ts/**/*.{ts,js}'",
35
49
  "build:meson": "gjsify run init:meson && meson compile -C build",
36
50
  "build:types": "gjsify tsc",
37
- "build:prebuilds": "gjsify run build:meson && mkdir -p prebuilds/linux-x86_64 && cp build/libgwebgl.so build/Gwebgl-0.1.typelib prebuilds/linux-x86_64/",
51
+ "build:prebuilds": "gjsify run build:meson && node ../../../scripts/stage-prebuild.mjs .",
38
52
  "build:test": "gjsify build src/ts/test.ts --app gjs --outfile test.gjs.js",
39
53
  "build:conformance": "gjsify build src/ts/conformance-test.ts --app gjs --outfile conformance.gjs.js",
40
54
  "test": "gjsify run build:gjsify && gjsify run build:test && gjsify run test:gjs",
@@ -46,8 +60,8 @@
46
60
  "WebGL"
47
61
  ],
48
62
  "devDependencies": {
49
- "@gjsify/cli": "^0.22.0",
50
- "@gjsify/unit": "^0.22.0",
63
+ "@gjsify/cli": "^0.23.0",
64
+ "@gjsify/unit": "^0.23.0",
51
65
  "@types/bit-twiddle": "^1.0.3",
52
66
  "@types/node": "^25.9.2",
53
67
  "typescript": "^6.0.3"
@@ -57,10 +71,10 @@
57
71
  "@girs/gjs": "^4.1.0",
58
72
  "@girs/gtk-4.0": "^4.1.0",
59
73
  "@girs/gwebgl-0.1": "0.1.0-4.0.0-rc.5",
60
- "@gjsify/dom-elements": "^0.22.0",
61
- "@gjsify/dom-events": "^0.22.0",
62
- "@gjsify/event-bridge": "^0.22.0",
63
- "@gjsify/utils": "^0.22.0",
74
+ "@gjsify/dom-elements": "^0.23.0",
75
+ "@gjsify/dom-events": "^0.23.0",
76
+ "@gjsify/event-bridge": "^0.23.0",
77
+ "@gjsify/utils": "^0.23.0",
64
78
  "bit-twiddle": "^1.0.2",
65
79
  "glsl-tokenizer": "^2.1.5"
66
80
  },