@lightningjs/renderer 3.0.0-beta8 → 3.0.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.
Files changed (566) hide show
  1. package/LICENSE +202 -202
  2. package/NOTICE +3 -3
  3. package/README.md +230 -147
  4. package/dist/exports/canvas.d.ts +1 -1
  5. package/dist/exports/canvas.js +1 -1
  6. package/dist/exports/canvas.js.map +1 -1
  7. package/dist/exports/index.d.ts +5 -6
  8. package/dist/exports/index.js +3 -5
  9. package/dist/exports/index.js.map +1 -1
  10. package/dist/exports/platform.d.ts +7 -0
  11. package/dist/exports/platform.js +27 -0
  12. package/dist/exports/platform.js.map +1 -0
  13. package/dist/exports/webgl.d.ts +2 -1
  14. package/dist/exports/webgl.js +2 -1
  15. package/dist/exports/webgl.js.map +1 -1
  16. package/dist/src/common/CommonTypes.d.ts +15 -3
  17. package/dist/src/core/AutosizeManager.d.ts +29 -0
  18. package/dist/src/core/AutosizeManager.js +169 -0
  19. package/dist/src/core/AutosizeManager.js.map +1 -0
  20. package/dist/src/core/Autosizer.d.ts +35 -0
  21. package/dist/src/core/Autosizer.js +196 -0
  22. package/dist/src/core/Autosizer.js.map +1 -0
  23. package/dist/src/core/CoreNode.d.ts +106 -58
  24. package/dist/src/core/CoreNode.js +530 -282
  25. package/dist/src/core/CoreNode.js.map +1 -1
  26. package/dist/src/core/CoreTextNode.d.ts +73 -88
  27. package/dist/src/core/CoreTextNode.js +375 -236
  28. package/dist/src/core/CoreTextNode.js.map +1 -1
  29. package/dist/src/core/CoreTextureManager.d.ts +23 -26
  30. package/dist/src/core/CoreTextureManager.js +60 -166
  31. package/dist/src/core/CoreTextureManager.js.map +1 -1
  32. package/dist/src/core/Stage.d.ts +63 -9
  33. package/dist/src/core/Stage.js +233 -133
  34. package/dist/src/core/Stage.js.map +1 -1
  35. package/dist/src/core/TextureError.d.ts +11 -0
  36. package/dist/src/core/TextureError.js +37 -0
  37. package/dist/src/core/TextureError.js.map +1 -0
  38. package/dist/src/core/TextureMemoryManager.d.ts +3 -5
  39. package/dist/src/core/TextureMemoryManager.js +84 -94
  40. package/dist/src/core/TextureMemoryManager.js.map +1 -1
  41. package/dist/src/core/animations/Animation.d.ts +21 -0
  42. package/dist/src/core/animations/Animation.js +194 -0
  43. package/dist/src/core/animations/Animation.js.map +1 -0
  44. package/dist/src/core/animations/CoreAnimation.d.ts +3 -3
  45. package/dist/src/core/animations/CoreAnimation.js +3 -3
  46. package/dist/src/core/animations/CoreAnimation.js.map +1 -1
  47. package/dist/src/core/animations/CoreAnimationController.d.ts +1 -1
  48. package/dist/src/core/animations/CoreAnimationController.js +8 -5
  49. package/dist/src/core/animations/CoreAnimationController.js.map +1 -1
  50. package/dist/src/core/animations/Playback.d.ts +64 -0
  51. package/dist/src/core/animations/Playback.js +169 -0
  52. package/dist/src/core/animations/Playback.js.map +1 -0
  53. package/dist/src/core/animations/Transition.d.ts +27 -0
  54. package/dist/src/core/animations/Transition.js +52 -0
  55. package/dist/src/core/animations/Transition.js.map +1 -0
  56. package/dist/src/core/animations/utils.d.ts +2 -0
  57. package/dist/src/core/animations/utils.js +136 -0
  58. package/dist/src/core/animations/utils.js.map +1 -0
  59. package/dist/src/core/lib/ImageWorker.d.ts +2 -2
  60. package/dist/src/core/lib/ImageWorker.js +30 -11
  61. package/dist/src/core/lib/ImageWorker.js.map +1 -1
  62. package/dist/src/core/lib/WebGlContextWrapper.d.ts +41 -3
  63. package/dist/src/core/lib/WebGlContextWrapper.js +105 -28
  64. package/dist/src/core/lib/WebGlContextWrapper.js.map +1 -1
  65. package/dist/src/core/lib/collectionUtils.d.ts +4 -0
  66. package/dist/src/core/lib/collectionUtils.js +72 -0
  67. package/dist/src/core/lib/collectionUtils.js.map +1 -0
  68. package/dist/src/core/lib/colorCache.d.ts +1 -0
  69. package/dist/src/core/lib/colorCache.js +19 -0
  70. package/dist/src/core/lib/colorCache.js.map +1 -0
  71. package/dist/src/core/lib/colorParser.d.ts +21 -0
  72. package/dist/src/core/lib/colorParser.js +72 -0
  73. package/dist/src/core/lib/colorParser.js.map +1 -0
  74. package/dist/src/core/lib/textureCompression.d.ts +14 -2
  75. package/dist/src/core/lib/textureCompression.js +320 -67
  76. package/dist/src/core/lib/textureCompression.js.map +1 -1
  77. package/dist/src/core/lib/utils.d.ts +6 -6
  78. package/dist/src/core/lib/utils.js +21 -65
  79. package/dist/src/core/lib/utils.js.map +1 -1
  80. package/dist/src/core/platform.d.ts +10 -0
  81. package/dist/src/core/platform.js +81 -0
  82. package/dist/src/core/platform.js.map +1 -0
  83. package/dist/src/core/platforms/GlContextWrapper.d.ts +136 -0
  84. package/{src/core/text-rendering/TextRenderingUtils.ts → dist/src/core/platforms/GlContextWrapper.js} +32 -36
  85. package/dist/src/core/platforms/GlContextWrapper.js.map +1 -0
  86. package/dist/src/core/platforms/Platform.d.ts +78 -12
  87. package/dist/src/core/platforms/Platform.js +18 -0
  88. package/dist/src/core/platforms/Platform.js.map +1 -1
  89. package/dist/src/core/platforms/web/WebGlContextWrapper.d.ts +776 -0
  90. package/dist/src/core/platforms/web/WebGlContextWrapper.js +1208 -0
  91. package/dist/src/core/platforms/web/WebGlContextWrapper.js.map +1 -0
  92. package/dist/src/core/platforms/web/WebPlatform.d.ts +17 -2
  93. package/dist/src/core/platforms/web/WebPlatform.js +158 -13
  94. package/dist/src/core/platforms/web/WebPlatform.js.map +1 -1
  95. package/dist/src/core/platforms/web/WebPlatformChrome50.d.ts +19 -0
  96. package/dist/src/core/platforms/web/WebPlatformChrome50.js +54 -0
  97. package/dist/src/core/platforms/web/WebPlatformChrome50.js.map +1 -0
  98. package/dist/src/core/platforms/web/WebPlatformLegacy.d.ts +20 -0
  99. package/dist/src/core/platforms/web/WebPlatformLegacy.js +105 -0
  100. package/dist/src/core/platforms/web/WebPlatformLegacy.js.map +1 -0
  101. package/dist/src/core/platforms/web/WebPlatformNext.d.ts +21 -0
  102. package/dist/src/core/platforms/web/WebPlatformNext.js +52 -0
  103. package/dist/src/core/platforms/web/WebPlatformNext.js.map +1 -0
  104. package/dist/src/core/platforms/web/lib/ImageWorker.d.ts +21 -0
  105. package/dist/src/core/platforms/web/lib/ImageWorker.js +136 -0
  106. package/dist/src/core/platforms/web/lib/ImageWorker.js.map +1 -0
  107. package/dist/src/core/platforms/web/lib/ImageWorkerDefault.d.ts +6 -0
  108. package/dist/src/core/platforms/web/lib/ImageWorkerDefault.js +92 -0
  109. package/dist/src/core/platforms/web/lib/ImageWorkerDefault.js.map +1 -0
  110. package/dist/src/core/platforms/web/lib/ImageWorkerLegacy.d.ts +1 -0
  111. package/dist/src/core/platforms/web/lib/ImageWorkerLegacy.js +63 -0
  112. package/dist/src/core/platforms/web/lib/ImageWorkerLegacy.js.map +1 -0
  113. package/dist/src/core/platforms/web/lib/ImageWorkerNoOptions.d.ts +7 -0
  114. package/dist/src/core/platforms/web/lib/ImageWorkerNoOptions.js +75 -0
  115. package/dist/src/core/platforms/web/lib/ImageWorkerNoOptions.js.map +1 -0
  116. package/dist/src/core/platforms/web/lib/createImageBitmap.d.ts +1 -0
  117. package/dist/src/core/platforms/web/lib/createImageBitmap.js +27 -0
  118. package/dist/src/core/platforms/web/lib/createImageBitmap.js.map +1 -0
  119. package/dist/src/core/platforms/web/lib/textureCompression.d.ts +26 -0
  120. package/dist/src/core/platforms/web/lib/textureCompression.js +301 -0
  121. package/dist/src/core/platforms/web/lib/textureCompression.js.map +1 -0
  122. package/dist/src/core/platforms/web/lib/textureSvg.d.ts +7 -0
  123. package/dist/src/core/platforms/web/lib/textureSvg.js +51 -0
  124. package/dist/src/core/platforms/web/lib/textureSvg.js.map +1 -0
  125. package/dist/src/core/platforms/web/lib/utils.d.ts +5 -0
  126. package/dist/src/core/platforms/web/lib/utils.js +86 -0
  127. package/dist/src/core/platforms/web/lib/utils.js.map +1 -0
  128. package/dist/src/core/renderers/CoreContextTexture.d.ts +2 -1
  129. package/dist/src/core/renderers/CoreContextTexture.js.map +1 -1
  130. package/dist/src/core/renderers/CoreRenderer.d.ts +4 -40
  131. package/dist/src/core/renderers/CoreRenderer.js +3 -4
  132. package/dist/src/core/renderers/CoreRenderer.js.map +1 -1
  133. package/dist/src/core/renderers/CoreShader.d.ts +9 -0
  134. package/{src/core/text-rendering/renderers/SdfTextRenderer/internal/constants.ts → dist/src/core/renderers/CoreShader.js} +28 -32
  135. package/dist/src/core/renderers/CoreShader.js.map +1 -0
  136. package/dist/src/core/renderers/CoreShaderNode.d.ts +10 -0
  137. package/dist/src/core/renderers/CoreShaderNode.js +19 -2
  138. package/dist/src/core/renderers/CoreShaderNode.js.map +1 -1
  139. package/dist/src/core/renderers/canvas/CanvasCoreRenderer.d.ts +33 -0
  140. package/dist/src/core/renderers/canvas/CanvasCoreRenderer.js +250 -0
  141. package/dist/src/core/renderers/canvas/CanvasCoreRenderer.js.map +1 -0
  142. package/dist/src/core/renderers/canvas/CanvasCoreTexture.d.ts +17 -0
  143. package/dist/src/core/renderers/canvas/CanvasCoreTexture.js +125 -0
  144. package/dist/src/core/renderers/canvas/CanvasCoreTexture.js.map +1 -0
  145. package/dist/src/core/renderers/canvas/CanvasRenderer.d.ts +5 -6
  146. package/dist/src/core/renderers/canvas/CanvasRenderer.js +67 -91
  147. package/dist/src/core/renderers/canvas/CanvasRenderer.js.map +1 -1
  148. package/dist/src/core/renderers/canvas/CanvasShaderNode.d.ts +1 -2
  149. package/dist/src/core/renderers/canvas/CanvasShaderNode.js +5 -4
  150. package/dist/src/core/renderers/canvas/CanvasShaderNode.js.map +1 -1
  151. package/dist/src/core/renderers/canvas/CanvasTexture.d.ts +3 -2
  152. package/dist/src/core/renderers/canvas/CanvasTexture.js +17 -13
  153. package/dist/src/core/renderers/canvas/CanvasTexture.js.map +1 -1
  154. package/dist/src/core/renderers/canvas/internal/C2DShaderUtils.d.ts +13 -0
  155. package/dist/src/core/renderers/canvas/internal/C2DShaderUtils.js +113 -192
  156. package/dist/src/core/renderers/canvas/internal/C2DShaderUtils.js.map +1 -1
  157. package/dist/src/core/renderers/canvas/internal/ColorUtils.d.ts +0 -2
  158. package/dist/src/core/renderers/canvas/internal/ColorUtils.js +0 -14
  159. package/dist/src/core/renderers/canvas/internal/ColorUtils.js.map +1 -1
  160. package/dist/src/core/renderers/canvas/shaders/UnsupportedShader.d.ts +10 -0
  161. package/{src/core/text-rendering/renderers/SdfTextRenderer/internal/util.ts → dist/src/core/renderers/canvas/shaders/UnsupportedShader.js} +43 -40
  162. package/dist/src/core/renderers/canvas/shaders/UnsupportedShader.js.map +1 -0
  163. package/dist/src/core/renderers/webgl/SdfRenderOp.d.ts +33 -0
  164. package/dist/src/core/renderers/webgl/SdfRenderOp.js +98 -0
  165. package/dist/src/core/renderers/webgl/SdfRenderOp.js.map +1 -0
  166. package/dist/src/core/renderers/webgl/WebGlCoreCtxRenderTexture.d.ts +12 -0
  167. package/dist/src/core/renderers/webgl/WebGlCoreCtxRenderTexture.js +58 -0
  168. package/dist/src/core/renderers/webgl/WebGlCoreCtxRenderTexture.js.map +1 -0
  169. package/dist/src/core/renderers/webgl/WebGlCoreCtxSubTexture.d.ts +9 -0
  170. package/dist/src/core/renderers/webgl/WebGlCoreCtxSubTexture.js +38 -0
  171. package/dist/src/core/renderers/webgl/WebGlCoreCtxSubTexture.js.map +1 -0
  172. package/dist/src/core/renderers/webgl/WebGlCoreCtxTexture.d.ts +69 -0
  173. package/dist/src/core/renderers/webgl/WebGlCoreCtxTexture.js +272 -0
  174. package/dist/src/core/renderers/webgl/WebGlCoreCtxTexture.js.map +1 -0
  175. package/dist/src/core/renderers/webgl/WebGlCoreRenderOp.d.ts +34 -0
  176. package/dist/src/core/renderers/webgl/WebGlCoreRenderOp.js +114 -0
  177. package/dist/src/core/renderers/webgl/WebGlCoreRenderOp.js.map +1 -0
  178. package/dist/src/core/renderers/webgl/WebGlCoreRenderer.d.ts +133 -0
  179. package/dist/src/core/renderers/webgl/WebGlCoreRenderer.js +649 -0
  180. package/dist/src/core/renderers/webgl/WebGlCoreRenderer.js.map +1 -0
  181. package/dist/src/core/renderers/webgl/WebGlCoreShader.d.ts +78 -0
  182. package/dist/src/core/renderers/webgl/WebGlCoreShader.js +202 -0
  183. package/dist/src/core/renderers/webgl/WebGlCoreShader.js.map +1 -0
  184. package/dist/src/core/renderers/webgl/WebGlCtxRenderTexture.d.ts +4 -2
  185. package/dist/src/core/renderers/webgl/WebGlCtxRenderTexture.js +14 -6
  186. package/dist/src/core/renderers/webgl/WebGlCtxRenderTexture.js.map +1 -1
  187. package/dist/src/core/renderers/webgl/WebGlCtxSubTexture.d.ts +15 -2
  188. package/dist/src/core/renderers/webgl/WebGlCtxSubTexture.js +34 -5
  189. package/dist/src/core/renderers/webgl/WebGlCtxSubTexture.js.map +1 -1
  190. package/dist/src/core/renderers/webgl/WebGlCtxTexture.d.ts +19 -9
  191. package/dist/src/core/renderers/webgl/WebGlCtxTexture.js +101 -49
  192. package/dist/src/core/renderers/webgl/WebGlCtxTexture.js.map +1 -1
  193. package/dist/src/core/renderers/webgl/WebGlRenderOp.d.ts +3 -2
  194. package/dist/src/core/renderers/webgl/WebGlRenderOp.js +14 -5
  195. package/dist/src/core/renderers/webgl/WebGlRenderOp.js.map +1 -1
  196. package/dist/src/core/renderers/webgl/WebGlRenderer.d.ts +11 -23
  197. package/dist/src/core/renderers/webgl/WebGlRenderer.js +122 -133
  198. package/dist/src/core/renderers/webgl/WebGlRenderer.js.map +1 -1
  199. package/dist/src/core/renderers/webgl/WebGlShaderNode.d.ts +4 -6
  200. package/dist/src/core/renderers/webgl/WebGlShaderNode.js +3 -3
  201. package/dist/src/core/renderers/webgl/WebGlShaderNode.js.map +1 -1
  202. package/dist/src/core/renderers/webgl/WebGlShaderProgram.d.ts +11 -9
  203. package/dist/src/core/renderers/webgl/WebGlShaderProgram.js +83 -46
  204. package/dist/src/core/renderers/webgl/WebGlShaderProgram.js.map +1 -1
  205. package/dist/src/core/renderers/webgl/internal/RendererUtils.d.ts +4 -4
  206. package/dist/src/core/renderers/webgl/internal/RendererUtils.js.map +1 -1
  207. package/dist/src/core/renderers/webgl/internal/ShaderUtils.d.ts +3 -3
  208. package/dist/src/core/renderers/webgl/internal/ShaderUtils.js +38 -37
  209. package/dist/src/core/renderers/webgl/internal/ShaderUtils.js.map +1 -1
  210. package/dist/src/core/renderers/webgl/shaders/DefaultShader.d.ts +9 -0
  211. package/dist/src/core/renderers/webgl/shaders/DefaultShader.js +84 -0
  212. package/dist/src/core/renderers/webgl/shaders/DefaultShader.js.map +1 -0
  213. package/dist/src/core/renderers/webgl/shaders/DefaultShaderBatched.d.ts +10 -0
  214. package/dist/src/core/renderers/webgl/shaders/DefaultShaderBatched.js +108 -0
  215. package/dist/src/core/renderers/webgl/shaders/DefaultShaderBatched.js.map +1 -0
  216. package/dist/src/core/renderers/webgl/shaders/DynamicShader.d.ts +29 -0
  217. package/dist/src/core/renderers/webgl/shaders/DynamicShader.js +408 -0
  218. package/dist/src/core/renderers/webgl/shaders/DynamicShader.js.map +1 -0
  219. package/dist/src/core/renderers/webgl/shaders/RoundedRectangle.d.ts +28 -0
  220. package/dist/src/core/renderers/webgl/shaders/RoundedRectangle.js +126 -0
  221. package/dist/src/core/renderers/webgl/shaders/RoundedRectangle.js.map +1 -0
  222. package/dist/src/core/renderers/webgl/shaders/SdfShader.d.ts +47 -0
  223. package/dist/src/core/renderers/webgl/shaders/SdfShader.js +148 -0
  224. package/dist/src/core/renderers/webgl/shaders/SdfShader.js.map +1 -0
  225. package/dist/src/core/renderers/webgl/shaders/effects/BorderBottomEffect.d.ts +31 -0
  226. package/dist/src/core/renderers/webgl/shaders/effects/BorderBottomEffect.js +71 -0
  227. package/dist/src/core/renderers/webgl/shaders/effects/BorderBottomEffect.js.map +1 -0
  228. package/dist/src/core/renderers/webgl/shaders/effects/BorderEffect.d.ts +30 -0
  229. package/dist/src/core/renderers/webgl/shaders/effects/BorderEffect.js +58 -0
  230. package/dist/src/core/renderers/webgl/shaders/effects/BorderEffect.js.map +1 -0
  231. package/dist/src/core/renderers/webgl/shaders/effects/BorderLeftEffect.d.ts +31 -0
  232. package/dist/src/core/renderers/webgl/shaders/effects/BorderLeftEffect.js +71 -0
  233. package/dist/src/core/renderers/webgl/shaders/effects/BorderLeftEffect.js.map +1 -0
  234. package/dist/src/core/renderers/webgl/shaders/effects/BorderRightEffect.d.ts +31 -0
  235. package/dist/src/core/renderers/webgl/shaders/effects/BorderRightEffect.js +71 -0
  236. package/dist/src/core/renderers/webgl/shaders/effects/BorderRightEffect.js.map +1 -0
  237. package/dist/src/core/renderers/webgl/shaders/effects/BorderTopEffect.d.ts +31 -0
  238. package/dist/src/core/renderers/webgl/shaders/effects/BorderTopEffect.js +71 -0
  239. package/dist/src/core/renderers/webgl/shaders/effects/BorderTopEffect.js.map +1 -0
  240. package/dist/src/core/renderers/webgl/shaders/effects/EffectUtils.d.ts +9 -0
  241. package/dist/src/core/renderers/webgl/shaders/effects/EffectUtils.js +136 -0
  242. package/dist/src/core/renderers/webgl/shaders/effects/EffectUtils.js.map +1 -0
  243. package/dist/src/core/renderers/webgl/shaders/effects/FadeOutEffect.d.ts +36 -0
  244. package/dist/src/core/renderers/webgl/shaders/effects/FadeOutEffect.js +85 -0
  245. package/dist/src/core/renderers/webgl/shaders/effects/FadeOutEffect.js.map +1 -0
  246. package/dist/src/core/renderers/webgl/shaders/effects/GlitchEffect.d.ts +45 -0
  247. package/dist/src/core/renderers/webgl/shaders/effects/GlitchEffect.js +104 -0
  248. package/dist/src/core/renderers/webgl/shaders/effects/GlitchEffect.js.map +1 -0
  249. package/dist/src/core/renderers/webgl/shaders/effects/GrayscaleEffect.d.ts +22 -0
  250. package/dist/src/core/renderers/webgl/shaders/effects/GrayscaleEffect.js +45 -0
  251. package/dist/src/core/renderers/webgl/shaders/effects/GrayscaleEffect.js.map +1 -0
  252. package/dist/src/core/renderers/webgl/shaders/effects/HolePunchEffect.d.ts +58 -0
  253. package/dist/src/core/renderers/webgl/shaders/effects/HolePunchEffect.js +80 -0
  254. package/dist/src/core/renderers/webgl/shaders/effects/HolePunchEffect.js.map +1 -0
  255. package/dist/src/core/renderers/webgl/shaders/effects/LinearGradientEffect.d.ts +35 -0
  256. package/dist/src/core/renderers/webgl/shaders/effects/LinearGradientEffect.js +134 -0
  257. package/dist/src/core/renderers/webgl/shaders/effects/LinearGradientEffect.js.map +1 -0
  258. package/dist/src/core/renderers/webgl/shaders/effects/RadialGradientEffect.d.ts +40 -0
  259. package/dist/src/core/renderers/webgl/shaders/effects/RadialGradientEffect.js +143 -0
  260. package/dist/src/core/renderers/webgl/shaders/effects/RadialGradientEffect.js.map +1 -0
  261. package/dist/src/core/renderers/webgl/shaders/effects/RadialProgressEffect.d.ts +61 -0
  262. package/dist/src/core/renderers/webgl/shaders/effects/RadialProgressEffect.js +127 -0
  263. package/dist/src/core/renderers/webgl/shaders/effects/RadialProgressEffect.js.map +1 -0
  264. package/dist/src/core/renderers/webgl/shaders/effects/RadiusEffect.d.ts +40 -0
  265. package/dist/src/core/renderers/webgl/shaders/effects/RadiusEffect.js +71 -0
  266. package/dist/src/core/renderers/webgl/shaders/effects/RadiusEffect.js.map +1 -0
  267. package/dist/src/core/renderers/webgl/shaders/effects/ShaderEffect.d.ts +115 -0
  268. package/dist/src/core/renderers/webgl/shaders/effects/ShaderEffect.js +61 -0
  269. package/dist/src/core/renderers/webgl/shaders/effects/ShaderEffect.js.map +1 -0
  270. package/dist/src/core/shaders/canvas/Border.d.ts +8 -2
  271. package/dist/src/core/shaders/canvas/Border.js +64 -25
  272. package/dist/src/core/shaders/canvas/Border.js.map +1 -1
  273. package/dist/src/core/shaders/canvas/HolePunch.js +4 -3
  274. package/dist/src/core/shaders/canvas/HolePunch.js.map +1 -1
  275. package/dist/src/core/shaders/canvas/LinearGradient.js +7 -5
  276. package/dist/src/core/shaders/canvas/LinearGradient.js.map +1 -1
  277. package/dist/src/core/shaders/canvas/RadialGradient.js +12 -10
  278. package/dist/src/core/shaders/canvas/RadialGradient.js.map +1 -1
  279. package/dist/src/core/shaders/canvas/Rounded.js +3 -3
  280. package/dist/src/core/shaders/canvas/Rounded.js.map +1 -1
  281. package/dist/src/core/shaders/canvas/RoundedWithBorder.d.ts +6 -3
  282. package/dist/src/core/shaders/canvas/RoundedWithBorder.js +41 -11
  283. package/dist/src/core/shaders/canvas/RoundedWithBorder.js.map +1 -1
  284. package/dist/src/core/shaders/canvas/RoundedWithBorderAndShadow.d.ts +2 -3
  285. package/dist/src/core/shaders/canvas/RoundedWithBorderAndShadow.js +46 -9
  286. package/dist/src/core/shaders/canvas/RoundedWithBorderAndShadow.js.map +1 -1
  287. package/dist/src/core/shaders/canvas/RoundedWithShadow.js +6 -5
  288. package/dist/src/core/shaders/canvas/RoundedWithShadow.js.map +1 -1
  289. package/dist/src/core/shaders/canvas/Shadow.js +4 -2
  290. package/dist/src/core/shaders/canvas/Shadow.js.map +1 -1
  291. package/dist/src/core/shaders/canvas/utils/render.d.ts +1 -1
  292. package/dist/src/core/shaders/canvas/utils/render.js +31 -18
  293. package/dist/src/core/shaders/canvas/utils/render.js.map +1 -1
  294. package/dist/src/core/shaders/templates/BorderTemplate.d.ts +11 -1
  295. package/dist/src/core/shaders/templates/BorderTemplate.js +30 -10
  296. package/dist/src/core/shaders/templates/BorderTemplate.js.map +1 -1
  297. package/dist/src/core/shaders/templates/HolePunchTemplate.d.ts +2 -2
  298. package/dist/src/core/shaders/templates/HolePunchTemplate.js +2 -2
  299. package/dist/src/core/shaders/templates/HolePunchTemplate.js.map +1 -1
  300. package/dist/src/core/shaders/templates/RadialGradientTemplate.d.ts +8 -6
  301. package/dist/src/core/shaders/templates/RadialGradientTemplate.js +2 -2
  302. package/dist/src/core/shaders/templates/RadialGradientTemplate.js.map +1 -1
  303. package/dist/src/core/shaders/webgl/Border.js +138 -84
  304. package/dist/src/core/shaders/webgl/Border.js.map +1 -1
  305. package/dist/src/core/shaders/webgl/Default.js +46 -47
  306. package/dist/src/core/shaders/webgl/Default.js.map +1 -1
  307. package/dist/src/core/shaders/webgl/DefaultBatched.js +61 -61
  308. package/dist/src/core/shaders/webgl/HolePunch.js +34 -34
  309. package/dist/src/core/shaders/webgl/HolePunch.js.map +1 -1
  310. package/dist/src/core/shaders/webgl/LinearGradient.js +60 -36
  311. package/dist/src/core/shaders/webgl/LinearGradient.js.map +1 -1
  312. package/dist/src/core/shaders/webgl/RadialGradient.js +60 -37
  313. package/dist/src/core/shaders/webgl/RadialGradient.js.map +1 -1
  314. package/dist/src/core/shaders/webgl/Rounded.js +74 -72
  315. package/dist/src/core/shaders/webgl/Rounded.js.map +1 -1
  316. package/dist/src/core/shaders/webgl/RoundedWithBorder.js +172 -113
  317. package/dist/src/core/shaders/webgl/RoundedWithBorder.js.map +1 -1
  318. package/dist/src/core/shaders/webgl/RoundedWithBorderAndShadow.js +191 -132
  319. package/dist/src/core/shaders/webgl/RoundedWithBorderAndShadow.js.map +1 -1
  320. package/dist/src/core/shaders/webgl/RoundedWithShadow.js +57 -55
  321. package/dist/src/core/shaders/webgl/RoundedWithShadow.js.map +1 -1
  322. package/dist/src/core/shaders/webgl/SdfShader.d.ts +0 -2
  323. package/dist/src/core/shaders/webgl/SdfShader.js +56 -66
  324. package/dist/src/core/shaders/webgl/SdfShader.js.map +1 -1
  325. package/dist/src/core/shaders/webgl/SdfShadowShader.d.ts +9 -0
  326. package/dist/src/core/shaders/webgl/SdfShadowShader.js +100 -0
  327. package/dist/src/core/shaders/webgl/SdfShadowShader.js.map +1 -0
  328. package/dist/src/core/shaders/webgl/Shadow.js +89 -83
  329. package/dist/src/core/shaders/webgl/Shadow.js.map +1 -1
  330. package/dist/src/core/text-rendering/CanvasFont.d.ts +14 -0
  331. package/dist/src/core/text-rendering/CanvasFont.js +111 -0
  332. package/dist/src/core/text-rendering/CanvasFont.js.map +1 -0
  333. package/dist/src/core/text-rendering/CanvasFontHandler.d.ts +59 -0
  334. package/dist/src/core/text-rendering/CanvasFontHandler.js +224 -0
  335. package/dist/src/core/text-rendering/CanvasFontHandler.js.map +1 -0
  336. package/dist/src/core/text-rendering/CanvasTextRenderer.d.ts +17 -0
  337. package/dist/src/core/text-rendering/CanvasTextRenderer.js +157 -0
  338. package/dist/src/core/text-rendering/CanvasTextRenderer.js.map +1 -0
  339. package/dist/src/core/text-rendering/CoreFont.d.ts +33 -0
  340. package/dist/src/core/text-rendering/CoreFont.js +48 -0
  341. package/dist/src/core/text-rendering/CoreFont.js.map +1 -0
  342. package/dist/src/core/text-rendering/FontManager.d.ts +11 -0
  343. package/dist/src/core/text-rendering/FontManager.js +42 -0
  344. package/dist/src/core/text-rendering/FontManager.js.map +1 -0
  345. package/dist/src/core/text-rendering/SdfFont.d.ts +29 -0
  346. package/dist/src/core/text-rendering/SdfFont.js +142 -0
  347. package/dist/src/core/text-rendering/SdfFont.js.map +1 -0
  348. package/dist/src/core/text-rendering/SdfFontHandler.d.ts +182 -0
  349. package/dist/src/core/text-rendering/SdfFontHandler.js +381 -0
  350. package/dist/src/core/text-rendering/SdfFontHandler.js.map +1 -0
  351. package/dist/src/core/text-rendering/SdfTextRenderer.d.ts +17 -0
  352. package/dist/src/core/text-rendering/SdfTextRenderer.js +301 -0
  353. package/dist/src/core/text-rendering/SdfTextRenderer.js.map +1 -0
  354. package/dist/src/core/text-rendering/TextLayoutEngine.d.ts +18 -0
  355. package/dist/src/core/text-rendering/TextLayoutEngine.js +380 -0
  356. package/dist/src/core/text-rendering/TextLayoutEngine.js.map +1 -0
  357. package/dist/src/core/text-rendering/TextRenderer.d.ts +383 -0
  358. package/{src/core/text-rendering/renderers/SdfTextRenderer/internal/getUnicodeCodepoints.ts → dist/src/core/text-rendering/TextRenderer.js} +20 -38
  359. package/dist/src/core/text-rendering/TextRenderer.js.map +1 -0
  360. package/dist/src/core/text-rendering/TextTextureRendererUtils.js.map +1 -1
  361. package/dist/src/core/text-rendering/Utils.d.ts +30 -0
  362. package/dist/src/core/text-rendering/Utils.js +84 -0
  363. package/dist/src/core/text-rendering/Utils.js.map +1 -0
  364. package/dist/src/core/text-rendering/font-face-types/SdfTrFontFace/SdfTrFontFace.js +2 -2
  365. package/dist/src/core/text-rendering/font-face-types/SdfTrFontFace/SdfTrFontFace.js.map +1 -1
  366. package/dist/src/core/text-rendering/renderers/CanvasTextRenderer.js +0 -5
  367. package/dist/src/core/text-rendering/renderers/CanvasTextRenderer.js.map +1 -1
  368. package/dist/src/core/text-rendering/renderers/LightningTextTextureRenderer.d.ts +1 -7
  369. package/dist/src/core/text-rendering/renderers/LightningTextTextureRenderer.js +2 -50
  370. package/dist/src/core/text-rendering/renderers/LightningTextTextureRenderer.js.map +1 -1
  371. package/dist/src/core/text-rendering/renderers/SdfTextRenderer/SdfTextRenderer.d.ts +3 -2
  372. package/dist/src/core/text-rendering/renderers/SdfTextRenderer/SdfTextRenderer.js +87 -46
  373. package/dist/src/core/text-rendering/renderers/SdfTextRenderer/SdfTextRenderer.js.map +1 -1
  374. package/dist/src/core/text-rendering/renderers/SdfTextRenderer/internal/layoutText.d.ts +1 -1
  375. package/dist/src/core/text-rendering/renderers/SdfTextRenderer/internal/layoutText.js +8 -66
  376. package/dist/src/core/text-rendering/renderers/SdfTextRenderer/internal/layoutText.js.map +1 -1
  377. package/dist/src/core/text-rendering/renderers/TextRenderer.d.ts +4 -14
  378. package/dist/src/core/text-rendering/renderers/TextRenderer.js +0 -3
  379. package/dist/src/core/text-rendering/renderers/TextRenderer.js.map +1 -1
  380. package/dist/src/core/textures/ColorTexture.d.ts +1 -1
  381. package/dist/src/core/textures/ColorTexture.js +3 -4
  382. package/dist/src/core/textures/ColorTexture.js.map +1 -1
  383. package/dist/src/core/textures/ImageTexture.d.ts +33 -14
  384. package/dist/src/core/textures/ImageTexture.js +46 -125
  385. package/dist/src/core/textures/ImageTexture.js.map +1 -1
  386. package/dist/src/core/textures/NoiseTexture.d.ts +3 -3
  387. package/dist/src/core/textures/NoiseTexture.js +8 -8
  388. package/dist/src/core/textures/NoiseTexture.js.map +1 -1
  389. package/dist/src/core/textures/RenderTexture.d.ts +7 -7
  390. package/dist/src/core/textures/RenderTexture.js +12 -12
  391. package/dist/src/core/textures/RenderTexture.js.map +1 -1
  392. package/dist/src/core/textures/SubTexture.d.ts +6 -8
  393. package/dist/src/core/textures/SubTexture.js +22 -40
  394. package/dist/src/core/textures/SubTexture.js.map +1 -1
  395. package/dist/src/core/textures/Texture.d.ts +74 -11
  396. package/dist/src/core/textures/Texture.js +136 -18
  397. package/dist/src/core/textures/Texture.js.map +1 -1
  398. package/dist/src/core/utils.d.ts +2 -1
  399. package/dist/src/core/utils.js +1 -1
  400. package/dist/src/core/utils.js.map +1 -1
  401. package/dist/src/main-api/DynamicShaderController.d.ts +29 -0
  402. package/dist/src/main-api/DynamicShaderController.js +58 -0
  403. package/dist/src/main-api/DynamicShaderController.js.map +1 -0
  404. package/dist/src/main-api/Inspector.d.ts +129 -1
  405. package/dist/src/main-api/Inspector.js +462 -23
  406. package/dist/src/main-api/Inspector.js.map +1 -1
  407. package/dist/src/main-api/Renderer.d.ts +223 -41
  408. package/dist/src/main-api/Renderer.js +107 -62
  409. package/dist/src/main-api/Renderer.js.map +1 -1
  410. package/dist/src/main-api/ShaderController.d.ts +31 -0
  411. package/dist/src/main-api/ShaderController.js +37 -0
  412. package/dist/src/main-api/ShaderController.js.map +1 -0
  413. package/dist/src/utils.d.ts +0 -2
  414. package/dist/src/utils.js +0 -36
  415. package/dist/src/utils.js.map +1 -1
  416. package/dist/tsconfig.dist.tsbuildinfo +1 -1
  417. package/dist/tsconfig.tsbuildinfo +1 -0
  418. package/exports/canvas-shaders.ts +28 -28
  419. package/exports/canvas.ts +45 -45
  420. package/exports/index.ts +90 -90
  421. package/exports/inspector.ts +24 -24
  422. package/exports/platform.ts +31 -0
  423. package/exports/utils.ts +50 -50
  424. package/exports/webgl-shaders.ts +28 -28
  425. package/exports/webgl.ts +52 -50
  426. package/package.json +16 -15
  427. package/src/common/CommonTypes.ts +163 -146
  428. package/src/common/EventEmitter.ts +77 -77
  429. package/src/common/IAnimationController.ts +92 -92
  430. package/src/common/IEventEmitter.ts +28 -28
  431. package/src/core/Autosizer.ts +224 -0
  432. package/src/core/CoreNode.test.ts +365 -202
  433. package/src/core/CoreNode.ts +2785 -2483
  434. package/src/core/CoreShaderManager.ts +188 -188
  435. package/src/core/CoreTextNode.test.ts +311 -0
  436. package/src/core/CoreTextNode.ts +598 -451
  437. package/src/core/CoreTextureManager.ts +484 -608
  438. package/src/core/Stage.ts +927 -800
  439. package/src/core/TextureError.ts +46 -0
  440. package/src/core/TextureMemoryManager.ts +418 -435
  441. package/src/core/animations/AnimationManager.ts +38 -38
  442. package/src/core/animations/CoreAnimation.ts +290 -291
  443. package/src/core/animations/CoreAnimationController.ts +169 -164
  444. package/src/core/lib/ContextSpy.ts +41 -41
  445. package/src/core/lib/Matrix3d.ts +244 -244
  446. package/src/core/lib/RenderCoords.ts +71 -71
  447. package/src/core/lib/collectionUtils.ts +83 -0
  448. package/src/core/lib/colorCache.ts +20 -0
  449. package/src/core/{renderers/canvas/internal/ColorUtils.ts → lib/colorParser.ts} +85 -85
  450. package/src/core/lib/utils.ts +337 -390
  451. package/src/core/platforms/GlContextWrapper.ts +291 -0
  452. package/src/core/platforms/Platform.ts +176 -77
  453. package/src/core/{lib → platforms/web}/WebGlContextWrapper.ts +1547 -1374
  454. package/src/core/platforms/web/WebPlatform.ts +306 -84
  455. package/src/core/platforms/web/WebPlatformChrome50.ts +63 -0
  456. package/src/core/platforms/web/WebPlatformLegacy.ts +150 -0
  457. package/src/core/platforms/web/WebPlatformNext.ts +57 -0
  458. package/src/core/platforms/web/lib/ImageWorker.ts +192 -0
  459. package/src/core/platforms/web/lib/ImageWorkerDefault.ts +117 -0
  460. package/src/core/platforms/web/lib/ImageWorkerLegacy.ts +87 -0
  461. package/src/core/platforms/web/lib/ImageWorkerNoOptions.ts +99 -0
  462. package/src/core/platforms/web/lib/createImageBitmap.ts +40 -0
  463. package/src/core/platforms/web/lib/textureCompression.ts +391 -0
  464. package/src/core/{lib → platforms/web/lib}/textureSvg.ts +66 -78
  465. package/src/core/platforms/web/lib/utils.ts +105 -0
  466. package/src/core/renderers/CoreContextTexture.ts +44 -43
  467. package/src/core/renderers/CoreRenderOp.ts +22 -22
  468. package/src/core/renderers/CoreRenderer.ts +71 -110
  469. package/src/core/renderers/CoreShaderNode.ts +202 -175
  470. package/src/core/renderers/CoreShaderProgram.ts +23 -23
  471. package/src/core/renderers/canvas/CanvasRenderer.ts +258 -302
  472. package/src/core/renderers/canvas/CanvasShaderNode.ts +95 -96
  473. package/src/core/renderers/canvas/CanvasTexture.ts +160 -156
  474. package/src/core/renderers/webgl/SdfRenderOp.ts +106 -0
  475. package/src/core/renderers/webgl/WebGlCtxRenderTexture.ts +89 -86
  476. package/src/core/renderers/webgl/WebGlCtxSubTexture.ts +95 -50
  477. package/src/core/renderers/webgl/WebGlCtxTexture.ts +350 -298
  478. package/src/core/renderers/webgl/WebGlRenderer.ts +726 -747
  479. package/src/core/renderers/webgl/WebGlShaderNode.ts +430 -435
  480. package/src/core/renderers/webgl/WebGlShaderProgram.ts +362 -318
  481. package/src/core/renderers/webgl/internal/BufferCollection.ts +54 -54
  482. package/src/core/renderers/webgl/internal/RendererUtils.ts +151 -155
  483. package/src/core/renderers/webgl/internal/ShaderUtils.ts +283 -281
  484. package/src/core/renderers/webgl/internal/WebGlUtils.ts +35 -35
  485. package/src/core/shaders/canvas/Border.ts +132 -78
  486. package/src/core/shaders/canvas/HolePunch.ts +56 -62
  487. package/src/core/shaders/canvas/LinearGradient.ts +73 -71
  488. package/src/core/shaders/canvas/RadialGradient.ts +96 -99
  489. package/src/core/shaders/canvas/Rounded.ts +55 -55
  490. package/src/core/shaders/canvas/RoundedWithBorder.ts +122 -74
  491. package/src/core/shaders/canvas/RoundedWithBorderAndShadow.ts +136 -90
  492. package/src/core/shaders/canvas/RoundedWithShadow.ts +71 -70
  493. package/src/core/shaders/canvas/Shadow.ts +54 -52
  494. package/src/core/shaders/canvas/utils/render.ts +160 -151
  495. package/src/core/shaders/templates/BorderTemplate.ts +145 -115
  496. package/src/core/shaders/templates/HolePunchTemplate.ts +82 -82
  497. package/src/core/shaders/templates/LinearGradientTemplate.ts +71 -71
  498. package/src/core/shaders/templates/RadialGradientTemplate.ts +83 -81
  499. package/src/core/shaders/templates/RoundedTemplate.ts +98 -98
  500. package/src/core/shaders/templates/RoundedWithBorderAndShadowTemplate.ts +38 -38
  501. package/src/core/shaders/templates/RoundedWithBorderTemplate.ts +35 -35
  502. package/src/core/shaders/templates/RoundedWithShadowTemplate.ts +35 -35
  503. package/src/core/shaders/templates/ShadowTemplate.ts +106 -106
  504. package/src/core/shaders/utils.ts +46 -46
  505. package/src/core/shaders/webgl/Border.ts +169 -116
  506. package/src/core/shaders/webgl/Default.ts +88 -89
  507. package/src/core/shaders/webgl/DefaultBatched.ts +129 -129
  508. package/src/core/shaders/webgl/HolePunch.ts +75 -75
  509. package/src/core/shaders/webgl/LinearGradient.ts +106 -82
  510. package/src/core/shaders/webgl/RadialGradient.ts +108 -85
  511. package/src/core/shaders/webgl/Rounded.ts +115 -117
  512. package/src/core/shaders/webgl/RoundedWithBorder.ts +210 -155
  513. package/src/core/shaders/webgl/RoundedWithBorderAndShadow.ts +234 -175
  514. package/src/core/shaders/webgl/RoundedWithShadow.ts +96 -98
  515. package/src/core/shaders/webgl/SdfShader.ts +122 -134
  516. package/src/core/shaders/webgl/Shadow.ts +121 -115
  517. package/src/core/text-rendering/CanvasFontHandler.ts +304 -0
  518. package/src/core/text-rendering/CanvasTextRenderer.ts +255 -0
  519. package/src/core/text-rendering/SdfFontHandler.ts +584 -0
  520. package/src/core/text-rendering/SdfTextRenderer.ts +403 -0
  521. package/src/core/text-rendering/TextLayoutEngine.ts +672 -0
  522. package/src/core/text-rendering/TextRenderer.ts +444 -0
  523. package/src/core/text-rendering/Utils.ts +99 -0
  524. package/src/core/text-rendering/tests/TextLayoutEngine.test.ts +453 -0
  525. package/src/core/textures/ColorTexture.ts +104 -102
  526. package/src/core/textures/ImageTexture.ts +292 -418
  527. package/src/core/textures/NoiseTexture.ts +106 -104
  528. package/src/core/textures/RenderTexture.ts +87 -85
  529. package/src/core/textures/SubTexture.ts +184 -205
  530. package/src/core/textures/Texture.ts +524 -372
  531. package/src/core/utils.ts +229 -227
  532. package/src/env.d.ts +7 -7
  533. package/src/main-api/INode.ts +100 -100
  534. package/src/main-api/Inspector.ts +1278 -569
  535. package/src/main-api/Renderer.ts +1030 -818
  536. package/src/main-api/utils.ts +45 -45
  537. package/src/utils.ts +220 -267
  538. package/COPYING +0 -1
  539. package/src/core/lib/ImageWorker.ts +0 -286
  540. package/src/core/lib/textureCompression.ts +0 -152
  541. package/src/core/lib/validateImageBitmap.ts +0 -87
  542. package/src/core/renderers/canvas/internal/C2DShaderUtils.ts +0 -220
  543. package/src/core/renderers/webgl/WebGlRenderOp.ts +0 -161
  544. package/src/core/text-rendering/TextTextureRendererUtils.ts +0 -263
  545. package/src/core/text-rendering/TrFontManager.ts +0 -183
  546. package/src/core/text-rendering/font-face-types/SdfTrFontFace/SdfTrFontFace.ts +0 -176
  547. package/src/core/text-rendering/font-face-types/SdfTrFontFace/internal/FontShaper.ts +0 -139
  548. package/src/core/text-rendering/font-face-types/SdfTrFontFace/internal/SdfFontShaper.test.ts +0 -173
  549. package/src/core/text-rendering/font-face-types/SdfTrFontFace/internal/SdfFontShaper.ts +0 -171
  550. package/src/core/text-rendering/font-face-types/TrFontFace.ts +0 -187
  551. package/src/core/text-rendering/font-face-types/WebTrFontFace.ts +0 -94
  552. package/src/core/text-rendering/font-face-types/utils.ts +0 -39
  553. package/src/core/text-rendering/renderers/CanvasTextRenderer.ts +0 -514
  554. package/src/core/text-rendering/renderers/LightningTextTextureRenderer.ts +0 -863
  555. package/src/core/text-rendering/renderers/SdfTextRenderer/SdfTextRenderer.ts +0 -793
  556. package/src/core/text-rendering/renderers/SdfTextRenderer/internal/PeekableGenerator.test.ts +0 -48
  557. package/src/core/text-rendering/renderers/SdfTextRenderer/internal/PeekableGenerator.ts +0 -66
  558. package/src/core/text-rendering/renderers/SdfTextRenderer/internal/SpecialCodepoints.ts +0 -52
  559. package/src/core/text-rendering/renderers/SdfTextRenderer/internal/getStartConditions.ts +0 -117
  560. package/src/core/text-rendering/renderers/SdfTextRenderer/internal/getUnicodeCodepoints.test.ts +0 -133
  561. package/src/core/text-rendering/renderers/SdfTextRenderer/internal/layoutText.ts +0 -497
  562. package/src/core/text-rendering/renderers/SdfTextRenderer/internal/measureText.test.ts +0 -49
  563. package/src/core/text-rendering/renderers/SdfTextRenderer/internal/measureText.ts +0 -52
  564. package/src/core/text-rendering/renderers/SdfTextRenderer/internal/setRenderWindow.test.ts +0 -205
  565. package/src/core/text-rendering/renderers/SdfTextRenderer/internal/setRenderWindow.ts +0 -93
  566. package/src/core/text-rendering/renderers/TextRenderer.ts +0 -567
@@ -1,818 +1,1030 @@
1
- /*
2
- * If not stated otherwise in this file or this component's LICENSE file the
3
- * following copyright and licenses apply:
4
- *
5
- * Copyright 2023 Comcast Cable Communications Management, LLC.
6
- *
7
- * Licensed under the Apache License, Version 2.0 (the License);
8
- * you may not use this file except in compliance with the License.
9
- * You may obtain a copy of the License at
10
- *
11
- * http://www.apache.org/licenses/LICENSE-2.0
12
- *
13
- * Unless required by applicable law or agreed to in writing, software
14
- * distributed under the License is distributed on an "AS IS" BASIS,
15
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
16
- * See the License for the specific language governing permissions and
17
- * limitations under the License.
18
- */
19
-
20
- import type { ExtractProps, TextureMap } from '../core/CoreTextureManager.js';
21
- import { EventEmitter } from '../common/EventEmitter.js';
22
- import { isProductionEnvironment } from '../utils.js';
23
- import { Stage, type StageOptions } from '../core/Stage.js';
24
- import { CoreNode, type CoreNodeProps } from '../core/CoreNode.js';
25
- import { type CoreTextNodeProps } from '../core/CoreTextNode.js';
26
- import type { INode, INodeProps, ITextNode, ITextNodeProps } from './INode.js';
27
- import type { TextureMemoryManagerSettings } from '../core/TextureMemoryManager.js';
28
- import type { CanvasTextRenderer } from '../core/text-rendering/renderers/CanvasTextRenderer.js';
29
- import type { SdfTextRenderer } from '../core/text-rendering/renderers/SdfTextRenderer/SdfTextRenderer.js';
30
- import type { CanvasRenderer } from '../core/renderers/canvas/CanvasRenderer.js';
31
- import type { WebGlRenderer } from '../core/renderers/webgl/WebGlRenderer.js';
32
- import type { Inspector } from './Inspector.js';
33
- import type { CoreShaderNode } from '../core/renderers/CoreShaderNode.js';
34
- import type {
35
- ExtractShaderProps,
36
- OptionalShaderProps,
37
- ShaderMap,
38
- } from '../core/CoreShaderManager.js';
39
- import { WebPlatform } from '../core/platforms/web/WebPlatform.js';
40
- import { Platform } from '../core/platforms/Platform.js';
41
-
42
- /**
43
- * Settings for the Renderer that can be updated during runtime.
44
- */
45
- export interface RendererRuntimeSettings {
46
- /**
47
- * Authored logical pixel width of the application
48
- *
49
- * @defaultValue `1920`
50
- */
51
- appWidth: number;
52
-
53
- /**
54
- * Authored logical pixel height of the application
55
- *
56
- * @defaultValue `1080`
57
- */
58
- appHeight: number;
59
-
60
- /**
61
- * Texture Memory Manager Settings
62
- */
63
- textureMemory: Partial<TextureMemoryManagerSettings>;
64
-
65
- /**
66
- * Bounds margin to extend the boundary in which a Node is added as Quad.
67
- */
68
- boundsMargin: number | [number, number, number, number];
69
-
70
- /**
71
- * Factor to convert app-authored logical coorindates to device logical coordinates
72
- *
73
- * @remarks
74
- * This value allows auto-scaling to support larger/small resolutions than the
75
- * app was authored for.
76
- *
77
- * If the app was authored for 1920x1080 and this value is 2, the app's canvas
78
- * will be rendered at 3840x2160 logical pixels.
79
- *
80
- * Likewise, if the app was authored for 1920x1080 and this value is 0.66667,
81
- * the app's canvas will be rendered at 1280x720 logical pixels.
82
- *
83
- * @defaultValue `1`
84
- */
85
- deviceLogicalPixelRatio: number;
86
-
87
- /**
88
- * Factor to convert device logical coordinates to device physical coordinates
89
- *
90
- * @remarks
91
- * This value allows auto-scaling to support devices with different pixel densities.
92
- *
93
- * This controls the number of physical pixels that are used to render each logical
94
- * pixel. For example, if the device has a pixel density of 2, each logical pixel
95
- * will be rendered using 2x2 physical pixels.
96
- *
97
- * By default, it will be set to `window.devicePixelRatio` which is the pixel
98
- * density of the device the app is running on reported by the browser.
99
- *
100
- * @defaultValue `window.devicePixelRatio`
101
- */
102
- devicePhysicalPixelRatio: number;
103
-
104
- /**
105
- * RGBA encoded number of the background to use
106
- *
107
- * @defaultValue `0x00000000`
108
- */
109
- clearColor: number;
110
-
111
- /**
112
- * Interval in milliseconds to receive FPS updates
113
- *
114
- * @remarks
115
- * If set to `0`, FPS updates will be disabled.
116
- *
117
- * @defaultValue `0` (disabled)
118
- */
119
- fpsUpdateInterval: number;
120
-
121
- /**
122
- * DOM Inspector
123
- *
124
- * @remarks
125
- * The inspector will replicate the state of the Nodes created
126
- * in the renderer and allow inspection of the state of the nodes.
127
- *
128
- */
129
- inspector: typeof Inspector | false;
130
-
131
- /**
132
- * Texture Processing Limit (in milliseconds)
133
- *
134
- * @remarks
135
- * The maximum amount of time the renderer is allowed to process textures in a
136
- * single frame. If the processing time exceeds this limit, the renderer will
137
- * skip processing the remaining textures and continue rendering the frame.
138
- *
139
- * @defaultValue `10`
140
- */
141
- textureProcessingTimeLimit: number;
142
- }
143
-
144
- /**
145
- * Configuration settings for {@link RendererMain}
146
- */
147
- export type RendererMainSettings = RendererRuntimeSettings & {
148
- /**
149
- * Include context call (i.e. WebGL) information in FPS updates
150
- *
151
- * @remarks
152
- * When enabled the number of calls to each context method over the
153
- * `fpsUpdateInterval` will be included in the FPS update payload's
154
- * `contextSpyData` property.
155
- *
156
- * Enabling the context spy has a serious impact on performance so only use it
157
- * when you need to extract context call information.
158
- *
159
- * @defaultValue `false` (disabled)
160
- */
161
- enableContextSpy: boolean;
162
-
163
- /**
164
- * Number or Image Workers to use
165
- *
166
- * @remarks
167
- * On devices with multiple cores, this can be used to improve image loading
168
- * as well as reduce the impact of image loading on the main thread.
169
- * Set to 0 to disable image workers.
170
- *
171
- * @defaultValue `2`
172
- */
173
- numImageWorkers: number;
174
-
175
- /**
176
- * Renderer Engine
177
- *
178
- * @remarks
179
- * The renderer engine to use. Spawns a WebGL or Canvas renderer.
180
- * WebGL is more performant and supports more features. Canvas is
181
- * supported on most platforms.
182
- *
183
- * Note: When using CanvasCoreRenderer you can only use
184
- * CanvasTextRenderer. The WebGLCoreRenderer supports
185
- * both CanvasTextRenderer and SdfTextRenderer for Text Rendering.
186
- *
187
- */
188
- renderEngine: typeof CanvasRenderer | typeof WebGlRenderer;
189
-
190
- /**
191
- * Quad buffer size in bytes
192
- *
193
- * @defaultValue 4 * 1024 * 1024
194
- */
195
- quadBufferSize: number;
196
-
197
- /**
198
- * Font Engines
199
- *
200
- * @remarks
201
- * The font engines to use for text rendering. CanvasTextRenderer is supported
202
- * on all platforms. SdfTextRenderer is a more performant renderer.
203
- * When using `renderEngine=CanvasCoreRenderer` you can only use `CanvasTextRenderer`.
204
- * The `renderEngine=WebGLCoreRenderer` supports both `CanvasTextRenderer` and `SdfTextRenderer`.
205
- *
206
- * This setting is used to enable tree shaking of unused font engines. Please
207
- * import your font engine(s) as follows:
208
- * ```
209
- * import { CanvasTextRenderer } from '@lightning/renderer/canvas';
210
- * import { SdfTextRenderer } from '@lightning/renderer/webgl';
211
- * ```
212
- *
213
- * If both CanvasTextRenderer and SdfTextRenderer are provided, the first renderer
214
- * provided will be asked first if it can render the font. If it cannot render the
215
- * font, the next renderer will be asked. If no renderer can render the font, the
216
- * text will not be rendered.
217
- *
218
- * **Note** that if you have fonts available in both engines the second font engine
219
- * will not be used. This is because the first font engine will always be asked first.
220
- *
221
- * @defaultValue '[]'
222
- *
223
- *
224
- */
225
- fontEngines: (typeof SdfTextRenderer | typeof CanvasTextRenderer)[];
226
-
227
- /**
228
- * Force WebGL2
229
- *
230
- * @remarks
231
- * Force the renderer to use WebGL2. This can be used to force the renderer to
232
- * use WebGL2 even if the browser supports WebGL1.
233
- *
234
- * @defaultValue `false`
235
- */
236
- forceWebGL2: boolean;
237
-
238
- /**
239
- * Enable strictBounds
240
- *
241
- * @remarks
242
- * Enable strict bounds for the renderer. This will ensure that the renderer
243
- * will not render outside the bounds of the canvas.
244
- *
245
- * @defaultValue `true`
246
- */
247
- strictBounds: boolean;
248
-
249
- /**
250
- * Canvas object to use for rendering
251
- *
252
- * @remarks
253
- * This is used to render the scene graph. If not provided, a new canvas
254
- * element will be created and appended to the target element.
255
- */
256
- canvas: HTMLCanvasElement;
257
-
258
- /**
259
- * createImageBitmap support for the runtime
260
- *
261
- * @remarks
262
- * This is used to determine if and which version of the createImageBitmap API
263
- * is supported by the runtime. This is used to determine if the renderer can
264
- * use createImageBitmap to load images.
265
- *
266
- * Options supported
267
- * - Auto - Automatically determine the supported version
268
- * - Basic - Supports createImageBitmap(image)
269
- * - Options - Supports createImageBitmap(image, options)
270
- * - Full - Supports createImageBitmap(image, sx, sy, sw, sh, options)
271
- *
272
- * Note with auto detection, the renderer will attempt to use the most advanced
273
- * version of the API available. If the API is not available, the renderer will
274
- * fall back to the next available version.
275
- *
276
- * This will affect startup performance as the renderer will need to determine
277
- * the supported version of the API.
278
- *
279
- * @defaultValue `full`
280
- */
281
- createImageBitmapSupport: 'auto' | 'basic' | 'options' | 'full';
282
-
283
- /**
284
- * Provide an alternative platform abstraction layer
285
- *
286
- * @remarks
287
- * By default the Lightning 3 renderer will load a webplatform, assuming it runs
288
- * inside a web browsr. However for special cases there might be a need to provide
289
- * an abstracted platform layer to run on non-web or non-standard JS engines
290
- *
291
- * @defaultValue `null`
292
- */
293
- platform: typeof Platform | null;
294
- };
295
-
296
- /**
297
- * The Renderer Main API
298
- *
299
- * @remarks
300
- * This is the primary class used to configure and operate the Renderer.
301
- *
302
- * It is used to create and destroy Nodes, as well as Texture and Shader
303
- * references.
304
- *
305
- * Example:
306
- * ```ts
307
- * import { RendererMain, MainCoreDriver } from '@lightningjs/renderer';
308
- *
309
- * // Initialize the Renderer
310
- * const renderer = new RendererMain(
311
- * {
312
- * appWidth: 1920,
313
- * appHeight: 1080
314
- * },
315
- * 'app',
316
- * new MainCoreDriver(),
317
- * );
318
- * ```
319
- *
320
- * ## Events
321
- * - `fpsUpdate`
322
- * - Emitted every `fpsUpdateInterval` milliseconds with the current FPS
323
- * - `frameTick`
324
- * - Emitted every frame tick
325
- * - `quadsUpdate`
326
- * - Emitted when number of quads rendered is updated
327
- * - `idle`
328
- * - Emitted when the renderer is idle (no changes to the scene
329
- * graph/animations running)
330
- * - `criticalCleanup`
331
- * - Emitted when the Texture Memory Manager Cleanup process is triggered
332
- * - Payload: { memUsed: number, criticalThreshold: number }
333
- * - `memUsed` - The amount of memory (in bytes) used by textures before the
334
- * cleanup process
335
- * - `criticalThreshold` - The critical threshold (in bytes)
336
- * - `criticalCleanupFailed`
337
- * - Emitted when the Texture Memory Manager Cleanup process is unable to free
338
- * up enough texture memory to reach below the critical threshold.
339
- * This can happen when there is not enough non-renderable textures to
340
- * free up.
341
- * - Payload (object with keys):
342
- * - `memUsed` - The amount of memory (in bytes) used by textures after
343
- * the cleanup process
344
- * - `criticalThreshold` - The critical threshold (in bytes)
345
- */
346
- export class RendererMain extends EventEmitter {
347
- readonly root: INode;
348
- readonly canvas: HTMLCanvasElement;
349
- readonly stage: Stage;
350
- private inspector: Inspector | null = null;
351
-
352
- /**
353
- * Constructs a new Renderer instance
354
- *
355
- * @param settings Renderer settings
356
- * @param target Element ID or HTMLElement to insert the canvas into
357
- * @param driver Core Driver to use
358
- */
359
- constructor(
360
- settings: Partial<RendererMainSettings>,
361
- target: string | HTMLElement,
362
- ) {
363
- super();
364
-
365
- const resolvedTxSettings = this.resolveTxSettings(
366
- settings.textureMemory || {},
367
- );
368
-
369
- settings = {
370
- appWidth: settings.appWidth || 1920,
371
- appHeight: settings.appHeight || 1080,
372
- textureMemory: resolvedTxSettings,
373
- boundsMargin: settings.boundsMargin || 0,
374
- deviceLogicalPixelRatio: settings.deviceLogicalPixelRatio || 1,
375
- devicePhysicalPixelRatio:
376
- settings.devicePhysicalPixelRatio || window.devicePixelRatio,
377
- clearColor: settings.clearColor ?? 0x00000000,
378
- fpsUpdateInterval: settings.fpsUpdateInterval || 0,
379
- numImageWorkers:
380
- settings.numImageWorkers !== undefined ? settings.numImageWorkers : 2,
381
- enableContextSpy: settings.enableContextSpy ?? false,
382
- forceWebGL2: settings.forceWebGL2 ?? false,
383
- inspector: settings.inspector ?? false,
384
- renderEngine: settings.renderEngine,
385
- quadBufferSize: settings.quadBufferSize ?? 4 * 1024 * 1024,
386
- fontEngines: settings.fontEngines ?? [],
387
- strictBounds: settings.strictBounds ?? true,
388
- textureProcessingTimeLimit: settings.textureProcessingTimeLimit || 10,
389
- canvas: settings.canvas || document.createElement('canvas'),
390
- createImageBitmapSupport: settings.createImageBitmapSupport || 'full',
391
- platform: settings.platform || null,
392
- };
393
-
394
- const {
395
- appWidth,
396
- appHeight,
397
- deviceLogicalPixelRatio,
398
- devicePhysicalPixelRatio,
399
- inspector,
400
- canvas,
401
- } = settings as RendererMainSettings;
402
-
403
- let platform;
404
- if (
405
- settings.platform !== undefined &&
406
- settings.platform !== null &&
407
- settings.platform.prototype instanceof Platform === true
408
- ) {
409
- // @ts-ignore - if Platform is a valid class, it will be used
410
- platform = new settings.platform();
411
- } else {
412
- platform = new WebPlatform();
413
- }
414
-
415
- const deviceLogicalWidth = appWidth * deviceLogicalPixelRatio;
416
- const deviceLogicalHeight = appHeight * deviceLogicalPixelRatio;
417
-
418
- this.canvas = canvas;
419
- canvas.width = deviceLogicalWidth * devicePhysicalPixelRatio;
420
- canvas.height = deviceLogicalHeight * devicePhysicalPixelRatio;
421
-
422
- canvas.style.width = `${deviceLogicalWidth}px`;
423
- canvas.style.height = `${deviceLogicalHeight}px`;
424
-
425
- // Initialize the stage
426
- this.stage = new Stage({
427
- appWidth,
428
- appHeight,
429
- boundsMargin: settings.boundsMargin!,
430
- clearColor: settings.clearColor!,
431
- canvas: this.canvas,
432
- deviceLogicalPixelRatio,
433
- devicePhysicalPixelRatio,
434
- enableContextSpy: settings.enableContextSpy!,
435
- forceWebGL2: settings.forceWebGL2!,
436
- fpsUpdateInterval: settings.fpsUpdateInterval!,
437
- numImageWorkers: settings.numImageWorkers!,
438
- renderEngine: settings.renderEngine!,
439
- textureMemory: resolvedTxSettings,
440
- eventBus: this,
441
- quadBufferSize: settings.quadBufferSize!,
442
- fontEngines: settings.fontEngines!,
443
- inspector: settings.inspector !== null,
444
- strictBounds: settings.strictBounds!,
445
- textureProcessingTimeLimit: settings.textureProcessingTimeLimit!,
446
- createImageBitmapSupport: settings.createImageBitmapSupport!,
447
- platform,
448
- });
449
-
450
- // Extract the root node
451
- this.root = this.stage.root as unknown as INode;
452
-
453
- // Get the target element and attach the canvas to it
454
- let targetEl: HTMLElement | null;
455
- if (typeof target === 'string') {
456
- targetEl = document.getElementById(target);
457
- } else {
458
- targetEl = target;
459
- }
460
-
461
- if (!targetEl) {
462
- throw new Error('Could not find target element');
463
- }
464
-
465
- targetEl.appendChild(canvas);
466
-
467
- // Initialize inspector (if enabled)
468
- if (inspector && isProductionEnvironment === false) {
469
- this.inspector = new inspector(canvas, settings as RendererMainSettings);
470
- }
471
- }
472
-
473
- /**
474
- * Resolves the Texture Memory Manager values
475
- *
476
- * @param props
477
- * @returns
478
- */
479
- private resolveTxSettings(
480
- textureMemory: Partial<TextureMemoryManagerSettings>,
481
- ): TextureMemoryManagerSettings {
482
- const currentTxSettings =
483
- (this.stage && this.stage.options.textureMemory) || {};
484
-
485
- return {
486
- criticalThreshold:
487
- textureMemory?.criticalThreshold ??
488
- currentTxSettings?.criticalThreshold ??
489
- 124e6,
490
- targetThresholdLevel:
491
- textureMemory?.targetThresholdLevel ??
492
- currentTxSettings?.targetThresholdLevel ??
493
- 0.5,
494
- cleanupInterval:
495
- textureMemory?.cleanupInterval ??
496
- currentTxSettings?.cleanupInterval ??
497
- 5000,
498
- debugLogging:
499
- textureMemory?.debugLogging ?? currentTxSettings?.debugLogging ?? false,
500
- baselineMemoryAllocation:
501
- textureMemory?.baselineMemoryAllocation ??
502
- currentTxSettings?.baselineMemoryAllocation ??
503
- 26e6,
504
- doNotExceedCriticalThreshold:
505
- textureMemory?.doNotExceedCriticalThreshold ??
506
- currentTxSettings?.doNotExceedCriticalThreshold ??
507
- false,
508
- };
509
- }
510
-
511
- /**
512
- * Create a new scene graph node
513
- *
514
- * @remarks
515
- * A node is the main graphical building block of the Renderer scene graph. It
516
- * can be a container for other nodes, or it can be a leaf node that renders a
517
- * solid color, gradient, image, or specific texture, using a specific shader.
518
- *
519
- * To create a text node, see {@link createTextNode}.
520
- *
521
- * See {@link CoreNode} for more details.
522
- *
523
- * @param props
524
- * @returns
525
- */
526
- createNode<ShNode extends CoreShaderNode<any>>(
527
- props: Partial<INodeProps<ShNode>>,
528
- ): INode<ShNode> {
529
- const node = this.stage.createNode(props as Partial<CoreNodeProps>);
530
-
531
- if (this.inspector) {
532
- return this.inspector.createNode(node) as unknown as INode<ShNode>;
533
- }
534
-
535
- return node as unknown as INode<ShNode>;
536
- }
537
-
538
- /**
539
- * Create a new scene graph text node
540
- *
541
- * @remarks
542
- * A text node is the second graphical building block of the Renderer scene
543
- * graph. It renders text using a specific text renderer that is automatically
544
- * chosen based on the font requested and what type of fonts are installed
545
- * into an app.
546
- *
547
- * See {@link ITextNode} for more details.
548
- *
549
- * @param props
550
- * @returns
551
- */
552
- createTextNode(props: Partial<ITextNodeProps>): ITextNode {
553
- const textNode = this.stage.createTextNode(props as CoreTextNodeProps);
554
-
555
- if (this.inspector) {
556
- return this.inspector.createTextNode(textNode) as unknown as ITextNode;
557
- }
558
-
559
- return textNode as unknown as ITextNode;
560
- }
561
-
562
- /**
563
- * Destroy a node
564
- *
565
- * @remarks
566
- * This method destroys a node
567
- *
568
- * @param node
569
- * @returns
570
- */
571
- destroyNode(node: INode) {
572
- if (this.inspector) {
573
- this.inspector.destroyNode(node.id);
574
- }
575
-
576
- return node.destroy();
577
- }
578
-
579
- /**
580
- * Create a new texture reference
581
- *
582
- * @remarks
583
- * This method creates a new reference to a texture. The texture is not
584
- * loaded until it is used on a node.
585
- *
586
- * It can be assigned to a node's `texture` property, or it can be used
587
- * when creating a SubTexture.
588
- *
589
- * @param textureType
590
- * @param props
591
- * @param options
592
- * @returns
593
- */
594
- createTexture<TxType extends keyof TextureMap>(
595
- textureType: TxType,
596
- props: ExtractProps<TextureMap[TxType]>,
597
- ): InstanceType<TextureMap[TxType]> {
598
- return this.stage.txManager.createTexture(textureType, props);
599
- }
600
-
601
- /**
602
- * Create a new shader controller for a shader type
603
- *
604
- * @remarks
605
- * This method creates a new Shader Controller for a specific shader type.
606
- *
607
- * If the shader has not been loaded yet, it will be loaded. Otherwise, the
608
- * existing shader will be reused.
609
- *
610
- * It can be assigned to a Node's `shader` property.
611
- *
612
- * @param shaderType
613
- * @param props
614
- * @returns
615
- */
616
- createShader<ShType extends keyof ShaderMap>(
617
- shType: ShType,
618
- props?: OptionalShaderProps<ShType>,
619
- ) {
620
- return this.stage.shManager.createShader(shType, props) as CoreShaderNode<
621
- NonNullable<ExtractShaderProps<ShType>>
622
- >;
623
- }
624
-
625
- /**
626
- * Get a Node by its ID
627
- *
628
- * @param id
629
- * @returns
630
- */
631
- getNodeById(id: number): CoreNode | null {
632
- const root = this.stage?.root;
633
- if (!root) {
634
- return null;
635
- }
636
-
637
- const findNode = (node: CoreNode): CoreNode | null => {
638
- if (node.id === id) {
639
- return node;
640
- }
641
-
642
- for (const child of node.children) {
643
- const found = findNode(child);
644
- if (found) {
645
- return found;
646
- }
647
- }
648
-
649
- return null;
650
- };
651
-
652
- return findNode(root);
653
- }
654
-
655
- toggleFreeze() {
656
- throw new Error('Not implemented');
657
- }
658
-
659
- advanceFrame() {
660
- throw new Error('Not implemented');
661
- }
662
-
663
- getBufferInfo() {
664
- return this.stage.renderer.getBufferInfo();
665
- }
666
-
667
- /**
668
- * Re-render the current frame without advancing any running animations.
669
- *
670
- * @remarks
671
- * Any state changes will be reflected in the re-rendered frame. Useful for
672
- * debugging.
673
- *
674
- * May not do anything if the render loop is running on a separate worker.
675
- */
676
- rerender() {
677
- this.stage.requestRender();
678
- }
679
-
680
- /**
681
- * Cleanup textures that are not being used
682
- *
683
- * @param aggressive - If true, will cleanup all textures, regardless of render status
684
- *
685
- * @remarks
686
- * This can be used to free up GFX memory used by textures that are no longer
687
- * being displayed.
688
- *
689
- * This routine is also called automatically when the memory used by textures
690
- * exceeds the critical threshold on frame generation **OR** when the renderer
691
- * is idle and the memory used by textures exceeds the target threshold.
692
- *
693
- * **NOTE**: This is a heavy operation and should be used sparingly.
694
- * **NOTE2**: This will not cleanup textures that are currently being displayed.
695
- * **NOTE3**: This will not cleanup textures that are marked as `preventCleanup`.
696
- * **NOTE4**: This has nothing to do with the garbage collection of JavaScript.
697
- */
698
- cleanup(aggressive: boolean = false) {
699
- this.stage.cleanup(aggressive);
700
- }
701
-
702
- /**
703
- * Sets the clear color for the stage.
704
- *
705
- * @param color - The color to set as the clear color.
706
- */
707
- setClearColor(color: number) {
708
- this.stage.setClearColor(color);
709
- }
710
-
711
- /**
712
- * Set options for the renderer
713
- *
714
- * @param options
715
- */
716
- setOptions(options: Partial<RendererRuntimeSettings>) {
717
- const stage = this.stage;
718
- if (options.textureMemory !== undefined) {
719
- const textureMemory = (options.textureMemory = this.resolveTxSettings(
720
- options.textureMemory,
721
- ));
722
- stage.txMemManager.updateSettings(textureMemory);
723
- stage.txMemManager.cleanup();
724
- }
725
-
726
- if (options.boundsMargin !== undefined) {
727
- let bm = options.boundsMargin!;
728
- options.boundsMargin = Array.isArray(bm) ? bm : [bm, bm, bm, bm];
729
- }
730
-
731
- const stageOptions = stage.options;
732
- for (let key in options) {
733
- stageOptions[key] = options[key]!;
734
- }
735
-
736
- if (options.inspector !== undefined && !isProductionEnvironment) {
737
- if (options.inspector === false) {
738
- this.inspector?.destroy();
739
- this.inspector = null;
740
- } else if (
741
- this.inspector === null ||
742
- this.inspector.constructor !== options.inspector
743
- ) {
744
- this.inspector = new options.inspector(
745
- this.canvas,
746
- stage.options as unknown as RendererMainSettings,
747
- );
748
- this.inspector?.createNodes(this.root as unknown as CoreNode);
749
- }
750
- }
751
-
752
- let needDimensionsUpdate = false;
753
-
754
- if (
755
- options.deviceLogicalPixelRatio ||
756
- options.devicePhysicalPixelRatio !== undefined
757
- ) {
758
- this.stage.pixelRatio =
759
- stageOptions.devicePhysicalPixelRatio *
760
- stageOptions.deviceLogicalPixelRatio;
761
- this.inspector?.updateViewport(
762
- stageOptions.appWidth,
763
- stageOptions.appHeight,
764
- stageOptions.deviceLogicalPixelRatio,
765
- );
766
- needDimensionsUpdate = true;
767
- }
768
-
769
- if (options.appWidth !== undefined || options.appHeight !== undefined) {
770
- this.inspector?.updateViewport(
771
- stageOptions.appWidth,
772
- stageOptions.appHeight,
773
- stageOptions.deviceLogicalPixelRatio,
774
- );
775
- needDimensionsUpdate = true;
776
- }
777
-
778
- if (options.boundsMargin !== undefined) {
779
- this.stage.setBoundsMargin(options.boundsMargin);
780
- }
781
-
782
- if (options.clearColor !== undefined) {
783
- this.stage.setClearColor(options.clearColor);
784
- }
785
-
786
- if (needDimensionsUpdate) {
787
- this.updateAppDimensions();
788
- }
789
- }
790
-
791
- private updateAppDimensions() {
792
- const {
793
- appWidth,
794
- appHeight,
795
- deviceLogicalPixelRatio,
796
- devicePhysicalPixelRatio,
797
- } = this.stage.options;
798
-
799
- const deviceLogicalWidth = appWidth * deviceLogicalPixelRatio;
800
- const deviceLogicalHeight = appHeight * deviceLogicalPixelRatio;
801
-
802
- this.canvas.width = deviceLogicalWidth * devicePhysicalPixelRatio;
803
- this.canvas.height = deviceLogicalHeight * devicePhysicalPixelRatio;
804
-
805
- this.canvas.style.width = `${deviceLogicalWidth}px`;
806
- this.canvas.style.height = `${deviceLogicalHeight}px`;
807
-
808
- this.stage.renderer.updateViewport();
809
-
810
- this.root.width = appWidth;
811
- this.root.height = appHeight;
812
- this.stage.updateViewportBounds();
813
- }
814
-
815
- get settings(): Readonly<StageOptions> {
816
- return this.stage.options;
817
- }
818
- }
1
+ /*
2
+ * If not stated otherwise in this file or this component's LICENSE file the
3
+ * following copyright and licenses apply:
4
+ *
5
+ * Copyright 2023 Comcast Cable Communications Management, LLC.
6
+ *
7
+ * Licensed under the Apache License, Version 2.0 (the License);
8
+ * you may not use this file except in compliance with the License.
9
+ * You may obtain a copy of the License at
10
+ *
11
+ * http://www.apache.org/licenses/LICENSE-2.0
12
+ *
13
+ * Unless required by applicable law or agreed to in writing, software
14
+ * distributed under the License is distributed on an "AS IS" BASIS,
15
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
16
+ * See the License for the specific language governing permissions and
17
+ * limitations under the License.
18
+ */
19
+
20
+ import type { ExtractProps, TextureMap } from '../core/CoreTextureManager.js';
21
+ import { EventEmitter } from '../common/EventEmitter.js';
22
+ import { assertTruthy, isProductionEnvironment } from '../utils.js';
23
+ import { Stage, type StageOptions } from '../core/Stage.js';
24
+ import { CoreNode, type CoreNodeProps } from '../core/CoreNode.js';
25
+ import { type CoreTextNodeProps } from '../core/CoreTextNode.js';
26
+ import type { INode, INodeProps, ITextNode, ITextNodeProps } from './INode.js';
27
+ import type { TextureMemoryManagerSettings } from '../core/TextureMemoryManager.js';
28
+ import type { TextRenderer } from '../core/text-rendering/TextRenderer.js';
29
+ import type { CanvasRenderer } from '../core/renderers/canvas/CanvasRenderer.js';
30
+ import type { WebGlRenderer } from '../core/renderers/webgl/WebGlRenderer.js';
31
+ import type { Inspector, InspectorOptions } from './Inspector.js';
32
+ import type { CoreShaderNode } from '../core/renderers/CoreShaderNode.js';
33
+ import type {
34
+ ExtractShaderProps,
35
+ OptionalShaderProps,
36
+ ShaderMap,
37
+ } from '../core/CoreShaderManager.js';
38
+ import { WebPlatform } from '../core/platforms/web/WebPlatform.js';
39
+ import { Platform } from '../core/platforms/Platform.js';
40
+
41
+ /**
42
+ * FPS Update Event Data
43
+ *
44
+ * @category Events
45
+ * @example
46
+ * ```typescript
47
+ * renderer.on('fpsUpdate', (data) => {
48
+ * console.log(`Current FPS: ${data.fps}`);
49
+ * if (data.contextSpyData) {
50
+ * console.log('WebGL calls:', data.contextSpyData);
51
+ * }
52
+ * });
53
+ * ```
54
+ */
55
+ export interface RendererMainFpsUpdateEvent {
56
+ /** Current frames per second */
57
+ fps: number;
58
+ /** Context spy data (if enabled) - contains WebGL call statistics */
59
+ contextSpyData?: unknown;
60
+ }
61
+
62
+ /**
63
+ * Frame Tick Event Data
64
+ *
65
+ * @category Events
66
+ * @example
67
+ * ```typescript
68
+ * renderer.on('frameTick', (data) => {
69
+ * console.log(`Frame time: ${data.time}ms, delta: ${data.delta}ms`);
70
+ * });
71
+ * ```
72
+ */
73
+ export interface RendererMainFrameTickEvent {
74
+ /** Current timestamp */
75
+ time: number;
76
+ /** Time delta since last frame */
77
+ delta: number;
78
+ }
79
+
80
+ /**
81
+ * Quads Update Event Data
82
+ *
83
+ * @category Events
84
+ * @example
85
+ * ```typescript
86
+ * renderer.on('quadsUpdate', (data) => {
87
+ * console.log(`Rendered quads: ${data.quads}`);
88
+ * });
89
+ * ```
90
+ */
91
+ export interface RendererMainQuadsUpdateEvent {
92
+ /** Number of rendered quads */
93
+ quads: number;
94
+ }
95
+
96
+ /**
97
+ * Idle Event Data
98
+ *
99
+ * @category Events
100
+ * @remarks
101
+ * This event is emitted when the renderer has no scene updates to process.
102
+ * The event has no payload - use this for performance optimizations during idle periods.
103
+ *
104
+ * @example
105
+ * ```typescript
106
+ * renderer.on('idle', () => {
107
+ * // Renderer is idle - perfect time for cleanup, analytics, etc.
108
+ * console.log('Renderer is idle - no scene changes');
109
+ *
110
+ * // Example: Perform background tasks
111
+ * performBackgroundCleanup();
112
+ * sendAnalytics();
113
+ * });
114
+ * ```
115
+ */
116
+ export interface RendererMainIdleEvent {
117
+ /** This event has no payload - listen without parameters */
118
+ readonly __eventHasNoPayload?: never;
119
+ }
120
+
121
+ /**
122
+ * Critical Cleanup Event Data
123
+ *
124
+ * @category Events
125
+ * @example
126
+ * ```typescript
127
+ * renderer.on('criticalCleanup', (data) => {
128
+ * console.log(`Memory cleanup triggered!`);
129
+ * console.log(`Memory used: ${data.memUsed} bytes`);
130
+ * console.log(`Critical threshold: ${data.criticalThreshold} bytes`);
131
+ * });
132
+ * ```
133
+ */
134
+ export interface RendererMainCriticalCleanupEvent {
135
+ /** Memory used before cleanup (bytes) */
136
+ memUsed: number;
137
+ /** Critical threshold (bytes) */
138
+ criticalThreshold: number;
139
+ }
140
+
141
+ /**
142
+ * Critical Cleanup Failed Event Data
143
+ *
144
+ * @category Events
145
+ * @example
146
+ * ```typescript
147
+ * renderer.on('criticalCleanupFailed', (data) => {
148
+ * console.warn(`Memory cleanup failed!`);
149
+ * console.log(`Memory still used: ${data.memUsed} bytes`);
150
+ * console.log(`Critical threshold: ${data.criticalThreshold} bytes`);
151
+ * // Consider reducing texture usage or forcing cleanup
152
+ * });
153
+ * ```
154
+ */
155
+ export interface RendererMainCriticalCleanupFailedEvent {
156
+ /** Memory used after cleanup (bytes) */
157
+ memUsed: number;
158
+ /** Critical threshold (bytes) */
159
+ criticalThreshold: number;
160
+ }
161
+
162
+ /**
163
+ * Settings for the Renderer that can be updated during runtime.
164
+ */
165
+ export interface RendererRuntimeSettings {
166
+ /**
167
+ * Authored logical pixel width of the application
168
+ *
169
+ * @defaultValue `1920`
170
+ */
171
+ appWidth: number;
172
+
173
+ /**
174
+ * Authored logical pixel height of the application
175
+ *
176
+ * @defaultValue `1080`
177
+ */
178
+ appHeight: number;
179
+
180
+ /**
181
+ * Texture Memory Manager Settings
182
+ */
183
+ textureMemory: Partial<TextureMemoryManagerSettings>;
184
+
185
+ /**
186
+ * Bounds margin to extend the boundary in which a Node is added as Quad.
187
+ */
188
+ boundsMargin: number | [number, number, number, number];
189
+
190
+ /**
191
+ * Factor to convert app-authored logical coorindates to device logical coordinates
192
+ *
193
+ * @remarks
194
+ * This value allows auto-scaling to support larger/small resolutions than the
195
+ * app was authored for.
196
+ *
197
+ * If the app was authored for 1920x1080 and this value is 2, the app's canvas
198
+ * will be rendered at 3840x2160 logical pixels.
199
+ *
200
+ * Likewise, if the app was authored for 1920x1080 and this value is 0.66667,
201
+ * the app's canvas will be rendered at 1280x720 logical pixels.
202
+ *
203
+ * @defaultValue `1`
204
+ */
205
+ deviceLogicalPixelRatio: number;
206
+
207
+ /**
208
+ * Factor to convert device logical coordinates to device physical coordinates
209
+ *
210
+ * @remarks
211
+ * This value allows auto-scaling to support devices with different pixel densities.
212
+ *
213
+ * This controls the number of physical pixels that are used to render each logical
214
+ * pixel. For example, if the device has a pixel density of 2, each logical pixel
215
+ * will be rendered using 2x2 physical pixels.
216
+ *
217
+ * By default, it will be set to `window.devicePixelRatio` which is the pixel
218
+ * density of the device the app is running on reported by the browser.
219
+ *
220
+ * @defaultValue `window.devicePixelRatio`
221
+ */
222
+ devicePhysicalPixelRatio: number;
223
+
224
+ /**
225
+ * RGBA encoded number of the background to use
226
+ *
227
+ * @defaultValue `0x00000000`
228
+ */
229
+ clearColor: number;
230
+
231
+ /**
232
+ * Interval in milliseconds to receive FPS updates
233
+ *
234
+ * @remarks
235
+ * If set to `0`, FPS updates will be disabled.
236
+ *
237
+ * @defaultValue `0` (disabled)
238
+ */
239
+ fpsUpdateInterval: number;
240
+
241
+ /**
242
+ * Clears the render buffer on reset
243
+ *
244
+ * @remarks
245
+ * If false, the renderer will not clear the buffer before rendering a new frame.
246
+ * This is useful if you want to preserve the previous frame.
247
+ *
248
+ * @defaultValue `true`
249
+ */
250
+ enableClear: boolean;
251
+
252
+ /**
253
+ * DOM Inspector
254
+ *
255
+ * @remarks
256
+ * The inspector will replicate the state of the Nodes created
257
+ * in the renderer and allow inspection of the state of the nodes.
258
+ *
259
+ */
260
+ inspector: typeof Inspector | false;
261
+
262
+ /**
263
+ * Inspector Options
264
+ *
265
+ * @remarks
266
+ * Configuration options for the Inspector's performance monitoring features.
267
+ * Only used when inspector is enabled.
268
+ */
269
+ inspectorOptions?: Partial<InspectorOptions>;
270
+
271
+ /**
272
+ * Texture Processing Limit (in milliseconds)
273
+ *
274
+ * @remarks
275
+ * The maximum amount of time the renderer is allowed to process textures in a
276
+ * single frame. If the processing time exceeds this limit, the renderer will
277
+ * skip processing the remaining textures and continue rendering the frame.
278
+ *
279
+ * @defaultValue `10`
280
+ */
281
+ textureProcessingTimeLimit: number;
282
+
283
+ /**
284
+ * Target FPS for the global render loop
285
+ *
286
+ * @remarks
287
+ * Controls the maximum frame rate of the entire rendering system.
288
+ * When set to 0, no throttling is applied (use display refresh rate).
289
+ * When set to a positive number, the global requestAnimationFrame loop
290
+ * will be throttled to this target FPS, affecting all animations and rendering.
291
+ *
292
+ * This provides global performance control for the entire application,
293
+ * useful for managing performance on lower-end devices.
294
+ *
295
+ * @defaultValue `0` (no throttling, use display refresh rate)
296
+ */
297
+ targetFPS: number;
298
+ }
299
+
300
+ /**
301
+ * Configuration settings for {@link RendererMain}
302
+ */
303
+ export type RendererMainSettings = RendererRuntimeSettings & {
304
+ /**
305
+ * Include context call (i.e. WebGL) information in FPS updates
306
+ *
307
+ * @remarks
308
+ * When enabled the number of calls to each context method over the
309
+ * `fpsUpdateInterval` will be included in the FPS update payload's
310
+ * `contextSpyData` property.
311
+ *
312
+ * Enabling the context spy has a serious impact on performance so only use it
313
+ * when you need to extract context call information.
314
+ *
315
+ * @defaultValue `false` (disabled)
316
+ */
317
+ enableContextSpy: boolean;
318
+
319
+ /**
320
+ * Number or Image Workers to use
321
+ *
322
+ * @remarks
323
+ * On devices with multiple cores, this can be used to improve image loading
324
+ * as well as reduce the impact of image loading on the main thread.
325
+ * Set to 0 to disable image workers.
326
+ *
327
+ * @defaultValue `2`
328
+ */
329
+ numImageWorkers: number;
330
+
331
+ /**
332
+ * Renderer Engine
333
+ *
334
+ * @remarks
335
+ * The renderer engine to use. Spawns a WebGL or Canvas renderer.
336
+ * WebGL is more performant and supports more features. Canvas is
337
+ * supported on most platforms.
338
+ *
339
+ * Note: When using CanvasCoreRenderer you can only use
340
+ * CanvasTextRenderer. The WebGLCoreRenderer supports
341
+ * both CanvasTextRenderer and SdfTextRenderer for Text Rendering.
342
+ *
343
+ */
344
+ renderEngine: typeof CanvasRenderer | typeof WebGlRenderer;
345
+
346
+ /**
347
+ * Quad buffer size in bytes
348
+ *
349
+ * @defaultValue 4 * 1024 * 1024
350
+ */
351
+ quadBufferSize: number;
352
+
353
+ /**
354
+ * Font Engines
355
+ *
356
+ * @remarks
357
+ * The font engines to use for text rendering. CanvasTextRenderer is supported
358
+ * on all platforms. SdfTextRenderer is a more performant renderer.
359
+ * When using `renderEngine=CanvasCoreRenderer` you can only use `CanvasTextRenderer`.
360
+ * The `renderEngine=WebGLCoreRenderer` supports both `CanvasTextRenderer` and `SdfTextRenderer`.
361
+ *
362
+ * This setting is used to enable tree shaking of unused font engines. Please
363
+ * import your font engine(s) as follows:
364
+ * ```
365
+ * import { CanvasTextRenderer } from '@lightning/renderer/canvas';
366
+ * import { SdfTextRenderer } from '@lightning/renderer/webgl';
367
+ * ```
368
+ *
369
+ * If both CanvasTextRenderer and SdfTextRenderer are provided, the first renderer
370
+ * provided will be asked first if it can render the font. If it cannot render the
371
+ * font, the next renderer will be asked. If no renderer can render the font, the
372
+ * text will not be rendered.
373
+ *
374
+ * **Note** that if you have fonts available in both engines the second font engine
375
+ * will not be used. This is because the first font engine will always be asked first.
376
+ *
377
+ * @defaultValue '[]'
378
+ *
379
+ *
380
+ */
381
+ fontEngines: TextRenderer[];
382
+
383
+ /**
384
+ * Force WebGL2
385
+ *
386
+ * @remarks
387
+ * Force the renderer to use WebGL2. This can be used to force the renderer to
388
+ * use WebGL2 even if the browser supports WebGL1.
389
+ *
390
+ * @defaultValue `false`
391
+ */
392
+ forceWebGL2: boolean;
393
+
394
+ /**
395
+ * Canvas object to use for rendering
396
+ *
397
+ * @remarks
398
+ * This is used to render the scene graph. If not provided, a new canvas
399
+ * element will be created and appended to the target element.
400
+ */
401
+ canvas: HTMLCanvasElement;
402
+
403
+ /**
404
+ * createImageBitmap support for the runtime
405
+ *
406
+ * @remarks
407
+ * This is used to determine if and which version of the createImageBitmap API
408
+ * is supported by the runtime. This is used to determine if the renderer can
409
+ * use createImageBitmap to load images.
410
+ *
411
+ * Options supported
412
+ * - Auto - Automatically determine the supported version
413
+ * - Basic - Supports createImageBitmap(image)
414
+ * - Options - Supports createImageBitmap(image, options)
415
+ * - Full - Supports createImageBitmap(image, sx, sy, sw, sh, options)
416
+ *
417
+ * Note with auto detection, the renderer will attempt to use the most advanced
418
+ * version of the API available. If the API is not available, the renderer will
419
+ * fall back to the next available version.
420
+ *
421
+ * This will affect startup performance as the renderer will need to determine
422
+ * the supported version of the API.
423
+ *
424
+ * @defaultValue `full`
425
+ */
426
+ createImageBitmapSupport: 'auto' | 'basic' | 'options' | 'full';
427
+
428
+ /**
429
+ * Provide an alternative platform abstraction layer
430
+ *
431
+ * @remarks
432
+ * By default the Lightning 3 renderer will load a webplatform, assuming it runs
433
+ * inside a web browsr. However for special cases there might be a need to provide
434
+ * an abstracted platform layer to run on non-web or non-standard JS engines
435
+ *
436
+ * @defaultValue `null`
437
+ */
438
+ platform: typeof Platform | null;
439
+
440
+ /**
441
+ * Number of times to retry loading a failed texture
442
+ *
443
+ * @remarks
444
+ * When a texture fails to load, Lightning will retry up to this many times
445
+ * before permanently giving up. Each retry will clear the texture ownership
446
+ * and then re-establish it to trigger a new load attempt.
447
+ *
448
+ * Set to null to disable retries. Set to 0 to always try once and never retry.
449
+ * This is typically only used on ImageTexture instances.
450
+ *
451
+ */
452
+ maxRetryCount?: number;
453
+ };
454
+
455
+ /**
456
+ * The Renderer Main API
457
+ *
458
+ * @remarks
459
+ * This is the primary class used to configure and operate the Renderer.
460
+ *
461
+ * It is used to create and destroy Nodes, as well as Texture and Shader
462
+ * references.
463
+ *
464
+ * Example:
465
+ * ```ts
466
+ * import { RendererMain, MainCoreDriver } from '@lightningjs/renderer';
467
+ *
468
+ * // Initialize the Renderer
469
+ * const renderer = new RendererMain(
470
+ * {
471
+ * appWidth: 1920,
472
+ * appHeight: 1080
473
+ * },
474
+ * 'app',
475
+ * new MainCoreDriver(),
476
+ * );
477
+ * ```
478
+ *
479
+ * ## Event Handling
480
+ *
481
+ * Listen to events using the standard EventEmitter API:
482
+ * ```typescript
483
+ * renderer.on('fpsUpdate', (data: RendererMainFpsUpdateEvent) => {
484
+ * console.log(`FPS: ${data.fps}`);
485
+ * });
486
+ *
487
+ * renderer.on('idle', (data: RendererMainIdleEvent) => {
488
+ * // Renderer is idle - no scene changes
489
+ * });
490
+ * ```
491
+ *
492
+ * @see {@link RendererMainFpsUpdateEvent}
493
+ * @see {@link RendererMainFrameTickEvent}
494
+ * @see {@link RendererMainQuadsUpdateEvent}
495
+ * @see {@link RendererMainIdleEvent}
496
+ * @see {@link RendererMainCriticalCleanupEvent}
497
+ * @see {@link RendererMainCriticalCleanupFailedEvent}
498
+ *
499
+ * @fires RendererMain#fpsUpdate
500
+ * @fires RendererMain#frameTick
501
+ * @fires RendererMain#quadsUpdate
502
+ * @fires RendererMain#idle
503
+ * @fires RendererMain#criticalCleanup
504
+ * @fires RendererMain#criticalCleanupFailed
505
+ */
506
+ export class RendererMain extends EventEmitter {
507
+ readonly root: INode;
508
+ readonly canvas: HTMLCanvasElement;
509
+ readonly stage: Stage;
510
+ private inspector: Inspector | null = null;
511
+
512
+ /**
513
+ * Constructs a new Renderer instance
514
+ *
515
+ * @param settings Renderer settings
516
+ * @param target Element ID or HTMLElement to insert the canvas into
517
+ * @param driver Core Driver to use
518
+ */
519
+ constructor(
520
+ settings: Partial<RendererMainSettings>,
521
+ target?: string | HTMLElement,
522
+ ) {
523
+ super();
524
+
525
+ const resolvedTxSettings = this.resolveTxSettings(
526
+ settings.textureMemory || {},
527
+ );
528
+
529
+ settings = {
530
+ appWidth: settings.appWidth || 1920,
531
+ appHeight: settings.appHeight || 1080,
532
+ textureMemory: resolvedTxSettings,
533
+ boundsMargin: settings.boundsMargin || 0,
534
+ deviceLogicalPixelRatio: settings.deviceLogicalPixelRatio || 1,
535
+ devicePhysicalPixelRatio:
536
+ settings.devicePhysicalPixelRatio || window.devicePixelRatio || 1,
537
+ clearColor: settings.clearColor ?? 0x00000000,
538
+ fpsUpdateInterval: settings.fpsUpdateInterval || 0,
539
+ enableClear: settings.enableClear ?? true,
540
+ targetFPS: settings.targetFPS || 0,
541
+ numImageWorkers:
542
+ settings.numImageWorkers !== undefined ? settings.numImageWorkers : 2,
543
+ enableContextSpy: settings.enableContextSpy ?? false,
544
+ forceWebGL2: settings.forceWebGL2 ?? false,
545
+ inspector: settings.inspector ?? false,
546
+ inspectorOptions: settings.inspectorOptions ?? {},
547
+ renderEngine: settings.renderEngine,
548
+ quadBufferSize: settings.quadBufferSize ?? 4 * 1024 * 1024,
549
+ fontEngines: settings.fontEngines ?? [],
550
+ textureProcessingTimeLimit: settings.textureProcessingTimeLimit || 42,
551
+ canvas: settings.canvas,
552
+ createImageBitmapSupport: settings.createImageBitmapSupport || 'full',
553
+ platform: settings.platform || WebPlatform,
554
+ maxRetryCount: settings.maxRetryCount ?? 5,
555
+ };
556
+
557
+ const {
558
+ appWidth,
559
+ appHeight,
560
+ deviceLogicalPixelRatio,
561
+ devicePhysicalPixelRatio,
562
+ inspector,
563
+ } = settings as RendererMainSettings;
564
+
565
+ assertTruthy(
566
+ settings.platform,
567
+ 'A platform implementation must be provided in settings.platform',
568
+ );
569
+
570
+ // eslint-disable-next-line @typescript-eslint/no-unsafe-assignment, @typescript-eslint/no-unsafe-call
571
+ const platform = new (settings.platform as any)({
572
+ numImageWorkers: settings.numImageWorkers,
573
+ forceWebGL2: settings.forceWebGL2,
574
+ canvas: settings.canvas,
575
+ });
576
+
577
+ const deviceLogicalWidth = appWidth * deviceLogicalPixelRatio;
578
+ const deviceLogicalHeight = appHeight * deviceLogicalPixelRatio;
579
+
580
+ // eslint-disable-next-line @typescript-eslint/no-non-null-assertion, @typescript-eslint/no-unsafe-member-access
581
+ this.canvas = platform.canvas! as HTMLCanvasElement;
582
+ this.canvas.width = deviceLogicalWidth * devicePhysicalPixelRatio;
583
+ this.canvas.height = deviceLogicalHeight * devicePhysicalPixelRatio;
584
+
585
+ this.canvas.style.width = `${deviceLogicalWidth}px`;
586
+ this.canvas.style.height = `${deviceLogicalHeight}px`;
587
+
588
+ // Initialize the stage
589
+ this.stage = new Stage({
590
+ appWidth,
591
+ appHeight,
592
+ boundsMargin: settings.boundsMargin!,
593
+ clearColor: settings.clearColor!,
594
+ canvas: this.canvas,
595
+ deviceLogicalPixelRatio,
596
+ devicePhysicalPixelRatio,
597
+ enableContextSpy: settings.enableContextSpy!,
598
+ forceWebGL2: settings.forceWebGL2!,
599
+ fpsUpdateInterval: settings.fpsUpdateInterval!,
600
+ enableClear: settings.enableClear!,
601
+ numImageWorkers: settings.numImageWorkers!,
602
+ renderEngine: settings.renderEngine!,
603
+ textureMemory: resolvedTxSettings,
604
+ eventBus: this,
605
+ quadBufferSize: settings.quadBufferSize!,
606
+ fontEngines: settings.fontEngines!,
607
+ inspector: settings.inspector !== null,
608
+ targetFPS: settings.targetFPS!,
609
+ textureProcessingTimeLimit: settings.textureProcessingTimeLimit!,
610
+ createImageBitmapSupport: settings.createImageBitmapSupport!,
611
+ platform,
612
+ maxRetryCount: settings.maxRetryCount ?? 5,
613
+ });
614
+
615
+ // Extract the root node
616
+ this.root = this.stage.root as unknown as INode;
617
+
618
+ // Get the target element and attach the canvas to it
619
+ if (target) {
620
+ let targetEl: HTMLElement | null;
621
+ if (typeof target === 'string') {
622
+ targetEl = document.getElementById(target);
623
+ } else {
624
+ targetEl = target;
625
+ }
626
+
627
+ if (!targetEl) {
628
+ throw new Error('Could not find target element');
629
+ }
630
+
631
+ targetEl.appendChild(this.canvas);
632
+ } else if (settings.canvas !== this.canvas) {
633
+ throw new Error(
634
+ 'New canvas element could not be appended to undefined target',
635
+ );
636
+ }
637
+
638
+ // Initialize inspector (if enabled)
639
+ if (inspector && isProductionEnvironment === false) {
640
+ this.inspector = new inspector(
641
+ this.canvas,
642
+ settings as RendererMainSettings,
643
+ );
644
+ }
645
+ }
646
+
647
+ /**
648
+ * Resolves the Texture Memory Manager values
649
+ *
650
+ * @param props
651
+ * @returns
652
+ */
653
+ private resolveTxSettings(
654
+ textureMemory: Partial<TextureMemoryManagerSettings>,
655
+ ): TextureMemoryManagerSettings {
656
+ const currentTxSettings =
657
+ (this.stage && this.stage.options.textureMemory) || {};
658
+
659
+ return {
660
+ criticalThreshold:
661
+ textureMemory?.criticalThreshold ??
662
+ currentTxSettings?.criticalThreshold ??
663
+ 124e6,
664
+ targetThresholdLevel:
665
+ textureMemory?.targetThresholdLevel ??
666
+ currentTxSettings?.targetThresholdLevel ??
667
+ 0.5,
668
+ cleanupInterval:
669
+ textureMemory?.cleanupInterval ??
670
+ currentTxSettings?.cleanupInterval ??
671
+ 5000,
672
+ debugLogging:
673
+ textureMemory?.debugLogging ?? currentTxSettings?.debugLogging ?? false,
674
+ baselineMemoryAllocation:
675
+ textureMemory?.baselineMemoryAllocation ??
676
+ currentTxSettings?.baselineMemoryAllocation ??
677
+ 26e6,
678
+ doNotExceedCriticalThreshold:
679
+ textureMemory?.doNotExceedCriticalThreshold ??
680
+ currentTxSettings?.doNotExceedCriticalThreshold ??
681
+ false,
682
+ };
683
+ }
684
+
685
+ /**
686
+ * Create a new scene graph node
687
+ *
688
+ * @remarks
689
+ * A node is the main graphical building block of the Renderer scene graph. It
690
+ * can be a container for other nodes, or it can be a leaf node that renders a
691
+ * solid color, gradient, image, or specific texture, using a specific shader.
692
+ *
693
+ * To create a text node, see {@link createTextNode}.
694
+ *
695
+ * See {@link CoreNode} for more details.
696
+ *
697
+ * @param props
698
+ * @returns
699
+ */
700
+ createNode<ShNode extends CoreShaderNode<any>>(
701
+ props: Partial<INodeProps<ShNode>>,
702
+ ): INode<ShNode> {
703
+ const node = this.stage.createNode(props as Partial<CoreNodeProps>);
704
+
705
+ if (this.inspector) {
706
+ return this.inspector.createNode(node) as unknown as INode<ShNode>;
707
+ }
708
+
709
+ return node as unknown as INode<ShNode>;
710
+ }
711
+
712
+ /**
713
+ * Create a new scene graph text node
714
+ *
715
+ * @remarks
716
+ * A text node is the second graphical building block of the Renderer scene
717
+ * graph. It renders text using a specific text renderer that is automatically
718
+ * chosen based on the font requested and what type of fonts are installed
719
+ * into an app.
720
+ *
721
+ * See {@link ITextNode} for more details.
722
+ *
723
+ * @param props
724
+ * @returns
725
+ */
726
+ createTextNode(props: Partial<ITextNodeProps>): ITextNode {
727
+ const textNode = this.stage.createTextNode(props as CoreTextNodeProps);
728
+
729
+ if (this.inspector) {
730
+ return this.inspector.createTextNode(textNode) as unknown as ITextNode;
731
+ }
732
+
733
+ return textNode as unknown as ITextNode;
734
+ }
735
+
736
+ /**
737
+ * Destroy a node
738
+ *
739
+ * @remarks
740
+ * This method destroys a node
741
+ *
742
+ * @param node
743
+ * @returns
744
+ */
745
+ destroyNode(node: INode) {
746
+ if (this.inspector) {
747
+ this.inspector.destroyNode(node.id);
748
+ }
749
+
750
+ return node.destroy();
751
+ }
752
+
753
+ /**
754
+ * Create a new texture reference
755
+ *
756
+ * @remarks
757
+ * This method creates a new reference to a texture. The texture is not
758
+ * loaded until it is used on a node.
759
+ *
760
+ * It can be assigned to a node's `texture` property, or it can be used
761
+ * when creating a SubTexture.
762
+ *
763
+ * @param textureType
764
+ * @param props
765
+ * @param options
766
+ * @returns
767
+ */
768
+ createTexture<TxType extends keyof TextureMap>(
769
+ textureType: TxType,
770
+ props: ExtractProps<TextureMap[TxType]>,
771
+ ): InstanceType<TextureMap[TxType]> {
772
+ return this.stage.txManager.createTexture(textureType, props);
773
+ }
774
+
775
+ /**
776
+ * Create a new shader controller for a shader type
777
+ *
778
+ * @remarks
779
+ * This method creates a new Shader Controller for a specific shader type.
780
+ *
781
+ * If the shader has not been loaded yet, it will be loaded. Otherwise, the
782
+ * existing shader will be reused.
783
+ *
784
+ * It can be assigned to a Node's `shader` property.
785
+ *
786
+ * @param shaderType
787
+ * @param props
788
+ * @returns
789
+ */
790
+ createShader<ShType extends keyof ShaderMap>(
791
+ shType: ShType,
792
+ props?: OptionalShaderProps<ShType>,
793
+ ) {
794
+ return this.stage.shManager.createShader(shType, props) as CoreShaderNode<
795
+ NonNullable<ExtractShaderProps<ShType>>
796
+ >;
797
+ }
798
+
799
+ /**
800
+ * Get a Node by its ID
801
+ *
802
+ * @param id
803
+ * @returns
804
+ */
805
+ getNodeById(id: number): CoreNode | null {
806
+ const root = this.stage?.root;
807
+ if (!root) {
808
+ return null;
809
+ }
810
+
811
+ const findNode = (node: CoreNode): CoreNode | null => {
812
+ if (node.id === id) {
813
+ return node;
814
+ }
815
+
816
+ for (const child of node.children) {
817
+ const found = findNode(child);
818
+ if (found) {
819
+ return found;
820
+ }
821
+ }
822
+
823
+ return null;
824
+ };
825
+
826
+ return findNode(root);
827
+ }
828
+
829
+ toggleFreeze() {
830
+ throw new Error('Not implemented');
831
+ }
832
+
833
+ advanceFrame() {
834
+ throw new Error('Not implemented');
835
+ }
836
+
837
+ getBufferInfo() {
838
+ return this.stage.renderer.getBufferInfo();
839
+ }
840
+
841
+ /**
842
+ * Re-render the current frame without advancing any running animations.
843
+ *
844
+ * @remarks
845
+ * Any state changes will be reflected in the re-rendered frame. Useful for
846
+ * debugging.
847
+ *
848
+ * May not do anything if the render loop is running on a separate worker.
849
+ */
850
+ rerender() {
851
+ this.stage.requestRender();
852
+ }
853
+
854
+ /**
855
+ * Cleanup textures that are not being used
856
+ *
857
+ * @param aggressive - If true, will cleanup all textures, regardless of render status
858
+ *
859
+ * @remarks
860
+ * This can be used to free up GFX memory used by textures that are no longer
861
+ * being displayed.
862
+ *
863
+ * This routine is also called automatically when the memory used by textures
864
+ * exceeds the critical threshold on frame generation **OR** when the renderer
865
+ * is idle and the memory used by textures exceeds the target threshold.
866
+ *
867
+ * **NOTE**: This is a heavy operation and should be used sparingly.
868
+ * **NOTE2**: This will not cleanup textures that are currently being displayed.
869
+ * **NOTE3**: This will not cleanup textures that are marked as `preventCleanup`.
870
+ * **NOTE4**: This has nothing to do with the garbage collection of JavaScript.
871
+ */
872
+ cleanup() {
873
+ this.stage.cleanup();
874
+ }
875
+
876
+ /**
877
+ * Sets the clear color for the stage.
878
+ *
879
+ * @param color - The color to set as the clear color.
880
+ */
881
+ setClearColor(color: number) {
882
+ this.stage.setClearColor(color);
883
+ }
884
+
885
+ /**
886
+ * Set options for the renderer
887
+ *
888
+ * @param options
889
+ */
890
+ setOptions(options: Partial<RendererRuntimeSettings>) {
891
+ const stage = this.stage;
892
+ if (options.textureMemory !== undefined) {
893
+ const textureMemory = (options.textureMemory = this.resolveTxSettings(
894
+ options.textureMemory,
895
+ ));
896
+ stage.txMemManager.updateSettings(textureMemory);
897
+ stage.txMemManager.cleanup();
898
+ }
899
+
900
+ if (options.boundsMargin !== undefined) {
901
+ let bm = options.boundsMargin!;
902
+ options.boundsMargin = Array.isArray(bm) ? bm : [bm, bm, bm, bm];
903
+ }
904
+
905
+ const stageOptions = stage.options;
906
+ for (let key in options) {
907
+ stageOptions[key] = options[key]!;
908
+ }
909
+
910
+ if (options.inspector !== undefined && !isProductionEnvironment) {
911
+ if (options.inspector === false) {
912
+ this.inspector?.destroy();
913
+ this.inspector = null;
914
+ } else if (
915
+ this.inspector === null ||
916
+ this.inspector.constructor !== options.inspector
917
+ ) {
918
+ this.inspector = new options.inspector(
919
+ this.canvas,
920
+ stage.options as unknown as RendererMainSettings,
921
+ );
922
+ this.inspector?.createNodes(this.root as unknown as CoreNode);
923
+ }
924
+ }
925
+
926
+ let needDimensionsUpdate = false;
927
+
928
+ if (
929
+ options.deviceLogicalPixelRatio ||
930
+ options.devicePhysicalPixelRatio !== undefined
931
+ ) {
932
+ this.stage.pixelRatio =
933
+ stageOptions.devicePhysicalPixelRatio *
934
+ stageOptions.deviceLogicalPixelRatio;
935
+ this.inspector?.updateViewport(
936
+ stageOptions.appWidth,
937
+ stageOptions.appHeight,
938
+ stageOptions.deviceLogicalPixelRatio,
939
+ );
940
+ needDimensionsUpdate = true;
941
+ }
942
+
943
+ if (options.appWidth !== undefined || options.appHeight !== undefined) {
944
+ this.inspector?.updateViewport(
945
+ stageOptions.appWidth,
946
+ stageOptions.appHeight,
947
+ stageOptions.deviceLogicalPixelRatio,
948
+ );
949
+ needDimensionsUpdate = true;
950
+ }
951
+
952
+ if (options.boundsMargin !== undefined) {
953
+ this.stage.setBoundsMargin(options.boundsMargin);
954
+ }
955
+
956
+ if (options.clearColor !== undefined) {
957
+ this.stage.setClearColor(options.clearColor);
958
+ }
959
+
960
+ if (needDimensionsUpdate) {
961
+ this.updateAppDimensions();
962
+ }
963
+ }
964
+
965
+ private updateAppDimensions() {
966
+ const {
967
+ appWidth,
968
+ appHeight,
969
+ deviceLogicalPixelRatio,
970
+ devicePhysicalPixelRatio,
971
+ } = this.stage.options;
972
+
973
+ const deviceLogicalWidth = appWidth * deviceLogicalPixelRatio;
974
+ const deviceLogicalHeight = appHeight * deviceLogicalPixelRatio;
975
+
976
+ this.canvas.width = deviceLogicalWidth * devicePhysicalPixelRatio;
977
+ this.canvas.height = deviceLogicalHeight * devicePhysicalPixelRatio;
978
+
979
+ this.canvas.style.width = `${deviceLogicalWidth}px`;
980
+ this.canvas.style.height = `${deviceLogicalHeight}px`;
981
+
982
+ this.stage.renderer.updateViewport();
983
+
984
+ this.root.w = appWidth;
985
+ this.root.h = appHeight;
986
+ this.stage.updateViewportBounds();
987
+ }
988
+
989
+ get settings(): Readonly<StageOptions> {
990
+ return this.stage.options;
991
+ }
992
+
993
+ /**
994
+ * Gets the target FPS for the global render loop
995
+ *
996
+ * @returns The current target FPS (0 means no throttling)
997
+ *
998
+ * @remarks
999
+ * This controls the maximum frame rate of the entire rendering system.
1000
+ * When 0, the system runs at display refresh rate.
1001
+ */
1002
+ get targetFPS(): number {
1003
+ return this.stage.options.targetFPS || 0;
1004
+ }
1005
+
1006
+ /**
1007
+ * Sets the target FPS for the global render loop
1008
+ *
1009
+ * @param fps - The target FPS to set for the global render loop.
1010
+ * Set to 0 or a negative value to disable throttling.
1011
+ *
1012
+ * @remarks
1013
+ * This setting affects the entire rendering system immediately.
1014
+ * All animations, rendering, and frame updates will be throttled
1015
+ * to this target FPS. Provides global performance control.
1016
+ *
1017
+ * @example
1018
+ * ```typescript
1019
+ * // Set global target to 30fps for better performance
1020
+ * renderer.targetFPS = 30;
1021
+ *
1022
+ * // Disable global throttling (use display refresh rate)
1023
+ * renderer.targetFPS = 0;
1024
+ * ```
1025
+ */
1026
+ set targetFPS(fps: number) {
1027
+ this.stage.options.targetFPS = fps > 0 ? fps : 0;
1028
+ this.stage.updateTargetFrameTime();
1029
+ }
1030
+ }