├── .gitignore ├── .npmignore ├── LICENCE.txt ├── README.md ├── assets ├── CubeMesh.d.ts ├── CubeMesh.ts ├── PlaneMesh.ts ├── audio.wav ├── cube │ ├── negx.jpg │ ├── negy.jpg │ ├── negz.jpg │ ├── posx.jpg │ ├── posy.jpg │ ├── posz.jpg │ └── readme.txt ├── leaf.png ├── leaf2.png └── video.webm ├── dist ├── XGPU.js ├── XGPU.umd.cjs ├── documentation.json ├── index.d.ts ├── index.js ├── samples.jpg ├── xGPU │ ├── BuiltIns.d.ts │ ├── BuiltIns.js │ ├── EventDispatcher.d.ts │ ├── EventDispatcher.js │ ├── GPURenderer.d.ts │ ├── GPURenderer.js │ ├── GPUType.d.ts │ ├── GPUType.js │ ├── HighLevelParser.d.ts │ ├── HighLevelParser.js │ ├── IRenderer.d.ts │ ├── IRenderer.js │ ├── PrimitiveType.d.ts │ ├── PrimitiveType.js │ ├── TextureRenderer.d.ts │ ├── TextureRenderer.js │ ├── WebGPUProperties.d.ts │ ├── WebGPUProperties.js │ ├── XGPU.d.ts │ ├── XGPU.js │ ├── blendmodes │ │ ├── AlphaBlendMode.d.ts │ │ ├── AlphaBlendMode.js │ │ ├── BlendMode.d.ts │ │ └── BlendMode.js │ ├── pipelines │ │ ├── ComputePipeline.d.ts │ │ ├── ComputePipeline.js │ │ ├── Pipeline.d.ts │ │ ├── Pipeline.js │ │ ├── PipelinePlugin.d.ts │ │ ├── PipelinePlugin.js │ │ ├── RenderPipeline.d.ts │ │ ├── RenderPipeline.js │ │ ├── VertexShaderDebuggerPipeline.d.ts │ │ ├── VertexShaderDebuggerPipeline.js │ │ └── resources │ │ │ ├── DrawConfig.d.ts │ │ │ ├── DrawConfig.js │ │ │ ├── IndexBuffer.d.ts │ │ │ ├── IndexBuffer.js │ │ │ └── textures │ │ │ ├── DepthStencilTexture.d.ts │ │ │ ├── DepthStencilTexture.js │ │ │ ├── DepthTextureArray.d.ts │ │ │ ├── DepthTextureArray.js │ │ │ ├── MultiSampleTexture.d.ts │ │ │ ├── MultiSampleTexture.js │ │ │ ├── RenderPassTexture.d.ts │ │ │ ├── RenderPassTexture.js │ │ │ ├── Texture.d.ts │ │ │ └── Texture.js │ └── shader │ │ ├── Bindgroup.d.ts │ │ ├── Bindgroup.js │ │ ├── Bindgroups.d.ts │ │ ├── Bindgroups.js │ │ ├── ComputeShader.d.ts │ │ ├── ComputeShader.js │ │ ├── FragmentShader.d.ts │ │ ├── FragmentShader.js │ │ ├── ShaderType.d.ts │ │ ├── ShaderType.js │ │ ├── VertexShader.d.ts │ │ ├── VertexShader.js │ │ ├── resources │ │ ├── CubeMapTexture.d.ts │ │ ├── CubeMapTexture.js │ │ ├── CubeMapTextureArray.d.ts │ │ ├── CubeMapTextureArray.js │ │ ├── IShaderResource.d.ts │ │ ├── IShaderResource.js │ │ ├── ImageTexture.d.ts │ │ ├── ImageTexture.js │ │ ├── ImageTextureArray.d.ts │ │ ├── ImageTextureArray.js │ │ ├── ImageTextureIO.d.ts │ │ ├── ImageTextureIO.js │ │ ├── StageableBuffer.d.ts │ │ ├── StageableBuffer.js │ │ ├── TextureSampler.d.ts │ │ ├── TextureSampler.js │ │ ├── UniformBuffer.d.ts │ │ ├── UniformBuffer.js │ │ ├── UniformGroup.d.ts │ │ ├── UniformGroup.js │ │ ├── UniformGroupArray.d.ts │ │ ├── UniformGroupArray.js │ │ ├── VertexAttribute.d.ts │ │ ├── VertexAttribute.js │ │ ├── VertexBuffer.d.ts │ │ ├── VertexBuffer.js │ │ ├── VertexBufferIO.d.ts │ │ ├── VertexBufferIO.js │ │ ├── VideoTexture.d.ts │ │ ├── VideoTexture.js │ │ └── attributes │ │ │ ├── FloatBuffer.d.ts │ │ │ ├── FloatBuffer.js │ │ │ ├── IVec2Buffer.d.ts │ │ │ ├── IVec2Buffer.js │ │ │ ├── IVec3Buffer.d.ts │ │ │ ├── IVec3Buffer.js │ │ │ ├── IVec4Buffer.d.ts │ │ │ ├── IVec4Buffer.js │ │ │ ├── IntBuffer.d.ts │ │ │ ├── IntBuffer.js │ │ │ ├── UVec2Buffer.d.ts │ │ │ ├── UVec2Buffer.js │ │ │ ├── UVec3Buffer.d.ts │ │ │ ├── UVec3Buffer.js │ │ │ ├── UVec4Buffer.d.ts │ │ │ ├── UVec4Buffer.js │ │ │ ├── UintBuffer.d.ts │ │ │ ├── UintBuffer.js │ │ │ ├── Vec2Buffer.d.ts │ │ │ ├── Vec2Buffer.js │ │ │ ├── Vec3Buffer.d.ts │ │ │ ├── Vec3Buffer.js │ │ │ ├── Vec4Buffer.d.ts │ │ │ └── Vec4Buffer.js │ │ └── shaderParts │ │ ├── ShaderNode.d.ts │ │ ├── ShaderNode.js │ │ ├── ShaderStage.d.ts │ │ ├── ShaderStage.js │ │ ├── ShaderStruct.d.ts │ │ └── ShaderStruct.js └── xgpu_pipeline_resources.jpg ├── docs.json ├── githubPush.js ├── index.html ├── package-lock.json ├── package.json ├── public ├── samples.jpg └── xgpu_pipeline_resources.jpg ├── publish.js ├── readme_temp.md ├── set_xgpu_dev.js ├── set_xgpu_prod.js ├── src ├── index.ts ├── vite-env.d.ts └── xGPU │ ├── BuiltIns.ts │ ├── EventDispatcher.ts │ ├── GPURenderer.ts │ ├── GPUType.ts │ ├── HighLevelParser.ts │ ├── IRenderer.ts │ ├── PrimitiveType.ts │ ├── TextureRenderer.ts │ ├── WebGPUProperties.ts │ ├── XGPU.ts │ ├── blendmodes │ ├── AlphaBlendMode.ts │ └── BlendMode.ts │ ├── pipelines │ ├── ComputePipeline.ts │ ├── Pipeline.ts │ ├── PipelinePlugin.ts │ ├── RenderPipeline.ts │ ├── VertexShaderDebuggerPipeline.ts │ └── resources │ │ ├── DrawConfig.ts │ │ ├── IndexBuffer.ts │ │ └── textures │ │ ├── DepthStencilTexture.ts │ │ ├── DepthTextureArray.ts │ │ ├── MultiSampleTexture.ts │ │ ├── RenderPassTexture.ts │ │ └── Texture.ts │ └── shader │ ├── Bindgroup.ts │ ├── Bindgroups.ts │ ├── ComputeShader.ts │ ├── FragmentShader.ts │ ├── ShaderType.ts │ ├── VertexShader.ts │ ├── resources │ ├── CubeMapTexture.ts │ ├── CubeMapTextureArray.ts │ ├── IShaderResource.ts │ ├── ImageTexture.ts │ ├── ImageTextureArray.ts │ ├── ImageTextureIO.ts │ ├── StageableBuffer.ts │ ├── TextureSampler.ts │ ├── UniformBuffer.ts │ ├── UniformGroup.ts │ ├── UniformGroupArray.ts │ ├── VertexAttribute.ts │ ├── VertexBuffer.ts │ ├── VertexBufferIO.ts │ ├── VideoTexture.ts │ └── attributes │ │ ├── FloatBuffer.ts │ │ ├── IVec2Buffer.ts │ │ ├── IVec3Buffer.ts │ │ ├── IVec4Buffer.ts │ │ ├── IntBuffer.ts │ │ ├── UVec2Buffer.ts │ │ ├── UVec3Buffer.ts │ │ ├── UVec4Buffer.ts │ │ ├── UintBuffer.ts │ │ ├── Vec2Buffer.ts │ │ ├── Vec3Buffer.ts │ │ └── Vec4Buffer.ts │ └── shaderParts │ ├── ShaderNode.ts │ ├── ShaderStage.ts │ └── ShaderStruct.ts ├── todo.txt ├── tsconfig.json ├── tsconfig_build.json ├── typedoc.json ├── updateDoc.js ├── vite.config.js └── xgpu-0.9.23.tgz /.gitignore: -------------------------------------------------------------------------------- 1 | # Logs 2 | logs 3 | *.log 4 | npm-debug.log* 5 | yarn-debug.log* 6 | yarn-error.log* 7 | pnpm-debug.log* 8 | lerna-debug.log* 9 | 10 | 11 | assets 12 | node_modules 13 | dist-ssr 14 | *.local 15 | 16 | # Editor directories and files 17 | .vscode/* 18 | !.vscode/extensions.json 19 | .idea 20 | .DS_Store 21 | *.suo 22 | *.ntvs* 23 | *.njsproj 24 | *.sln 25 | *.sw? 26 | -------------------------------------------------------------------------------- /.npmignore: -------------------------------------------------------------------------------- 1 | # Logs 2 | logs 3 | *.log 4 | npm-debug.log* 5 | yarn-debug.log* 6 | yarn-error.log* 7 | pnpm-debug.log* 8 | lerna-debug.log* 9 | 10 | 11 | assets 12 | node_modules 13 | dist-ssr 14 | *.local 15 | 16 | # Editor directories and files 17 | .vscode/* 18 | !.vscode/extensions.json 19 | .idea 20 | .DS_Store 21 | *.suo 22 | *.ntvs* 23 | *.njsproj 24 | *.sln 25 | *.sw? 26 | -------------------------------------------------------------------------------- /LICENCE.txt: -------------------------------------------------------------------------------- 1 | The MIT License 2 | 3 | Copyright © 2023 XGPU.js Thomas Le Coz 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in 13 | all copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 21 | THE SOFTWARE. -------------------------------------------------------------------------------- /assets/CubeMesh.d.ts: -------------------------------------------------------------------------------- 1 | export declare const cubeVertexSize: number; 2 | export declare const cubePositionOffset = 0; 3 | export declare const cubeColorOffset: number; 4 | export declare const cubeUVOffset: number; 5 | export declare const cubeVertexCount = 36; 6 | export declare const cubeVertexArray: Float32Array; 7 | -------------------------------------------------------------------------------- /assets/CubeMesh.ts: -------------------------------------------------------------------------------- 1 | export const cubeVertexSize = 4 * 10; // Byte size of one cube vertex. 2 | export const cubePositionOffset = 0; 3 | export const cubeColorOffset = 4 * 4; // Byte offset of cube vertex color attribute. 4 | export const cubeUVOffset = 4 * 8; 5 | export const cubeVertexCount = 36; 6 | 7 | // prettier-ignore 8 | export const cubeVertexArray = new Float32Array([ 9 | // float4 position, float4 color, float2 uv, 10 | 1, -1, 1, 1, 1, 0, 1, 1, 1, 1, 11 | -1, -1, 1, 1, 0, 0, 1, 1, 0, 1, 12 | -1, -1, -1, 1, 0, 0, 0, 1, 0, 0, 13 | 1, -1, -1, 1, 1, 0, 0, 1, 1, 0, 14 | 1, -1, 1, 1, 1, 0, 1, 1, 1, 1, 15 | -1, -1, -1, 1, 0, 0, 0, 1, 0, 0, 16 | 17 | 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 18 | 1, -1, 1, 1, 1, 0, 1, 1, 0, 1, 19 | 1, -1, -1, 1, 1, 0, 0, 1, 0, 0, 20 | 1, 1, -1, 1, 1, 1, 0, 1, 1, 0, 21 | 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 22 | 1, -1, -1, 1, 1, 0, 0, 1, 0, 0, 23 | 24 | -1, 1, 1, 1, 0, 1, 1, 1, 1, 1, 25 | 1, 1, 1, 1, 1, 1, 1, 1, 0, 1, 26 | 1, 1, -1, 1, 1, 1, 0, 1, 0, 0, 27 | -1, 1, -1, 1, 0, 1, 0, 1, 1, 0, 28 | -1, 1, 1, 1, 0, 1, 1, 1, 1, 1, 29 | 1, 1, -1, 1, 1, 1, 0, 1, 0, 0, 30 | 31 | -1, -1, 1, 1, 0, 0, 1, 1, 1, 1, 32 | -1, 1, 1, 1, 0, 1, 1, 1, 0, 1, 33 | -1, 1, -1, 1, 0, 1, 0, 1, 0, 0, 34 | -1, -1, -1, 1, 0, 0, 0, 1, 1, 0, 35 | -1, -1, 1, 1, 0, 0, 1, 1, 1, 1, 36 | -1, 1, -1, 1, 0, 1, 0, 1, 0, 0, 37 | 38 | 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 39 | -1, 1, 1, 1, 0, 1, 1, 1, 0, 1, 40 | -1, -1, 1, 1, 0, 0, 1, 1, 0, 0, 41 | -1, -1, 1, 1, 0, 0, 1, 1, 0, 0, 42 | 1, -1, 1, 1, 1, 0, 1, 1, 1, 0, 43 | 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 44 | 45 | 1, -1, -1, 1, 1, 0, 0, 1, 1, 1, 46 | -1, -1, -1, 1, 0, 0, 0, 1, 0, 1, 47 | -1, 1, -1, 1, 0, 1, 0, 1, 0, 0, 48 | 1, 1, -1, 1, 1, 1, 0, 1, 1, 0, 49 | 1, -1, -1, 1, 1, 0, 0, 1, 1, 1, 50 | -1, 1, -1, 1, 0, 1, 0, 1, 0, 0, 51 | ]); 52 | -------------------------------------------------------------------------------- /assets/PlaneMesh.ts: -------------------------------------------------------------------------------- 1 | export const planeMesh = { 2 | position: [ 3 | [-0.5, -0.5, 0.0], 4 | [+0.5, -0.5, 0.0], 5 | [-0.5, +0.5, 0.0], 6 | [+0.5, +0.5, 0.0], 7 | ], 8 | normals: [ 9 | [0, 1, 0], 10 | [0, 1, 0], 11 | [0, 1, 0], 12 | [0, 1, 0] 13 | ], 14 | uvs: [ 15 | [0, 0], 16 | [1, 0], 17 | [0, 1], 18 | [1, 1], 19 | ], 20 | triangles: [ 21 | 0, 1, 2, 22 | 1, 3, 2 23 | ] 24 | } -------------------------------------------------------------------------------- /assets/audio.wav: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/tlecoz/XGPU/b2230801e3a9370f23b496986420a236eded31d3/assets/audio.wav -------------------------------------------------------------------------------- /assets/cube/negx.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/tlecoz/XGPU/b2230801e3a9370f23b496986420a236eded31d3/assets/cube/negx.jpg -------------------------------------------------------------------------------- /assets/cube/negy.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/tlecoz/XGPU/b2230801e3a9370f23b496986420a236eded31d3/assets/cube/negy.jpg -------------------------------------------------------------------------------- /assets/cube/negz.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/tlecoz/XGPU/b2230801e3a9370f23b496986420a236eded31d3/assets/cube/negz.jpg -------------------------------------------------------------------------------- /assets/cube/posx.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/tlecoz/XGPU/b2230801e3a9370f23b496986420a236eded31d3/assets/cube/posx.jpg -------------------------------------------------------------------------------- /assets/cube/posy.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/tlecoz/XGPU/b2230801e3a9370f23b496986420a236eded31d3/assets/cube/posy.jpg -------------------------------------------------------------------------------- /assets/cube/posz.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/tlecoz/XGPU/b2230801e3a9370f23b496986420a236eded31d3/assets/cube/posz.jpg -------------------------------------------------------------------------------- /assets/cube/readme.txt: -------------------------------------------------------------------------------- 1 | Author 2 | ====== 3 | 4 | This is the work of Emil Persson, aka Humus. 5 | http://www.humus.name 6 | humus@comhem.se 7 | 8 | 9 | 10 | Legal stuff 11 | =========== 12 | 13 | This work is free and may be used by anyone for any purpose 14 | and may be distributed freely to anyone using any distribution 15 | media or distribution method as long as this file is included. 16 | Distribution without this file is allowed if it's distributed 17 | with free non-commercial software; however, fair credit of the 18 | original author is expected. 19 | Any commercial distribution of this software requires the written 20 | approval of Emil Persson. 21 | -------------------------------------------------------------------------------- /assets/leaf.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/tlecoz/XGPU/b2230801e3a9370f23b496986420a236eded31d3/assets/leaf.png -------------------------------------------------------------------------------- /assets/leaf2.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/tlecoz/XGPU/b2230801e3a9370f23b496986420a236eded31d3/assets/leaf2.png -------------------------------------------------------------------------------- /assets/video.webm: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/tlecoz/XGPU/b2230801e3a9370f23b496986420a236eded31d3/assets/video.webm -------------------------------------------------------------------------------- /dist/index.d.ts: -------------------------------------------------------------------------------- 1 | export * from "./xGPU/XGPU"; 2 | export * from "./xGPU/EventDispatcher"; 3 | export * from "./xGPU/IRenderer"; 4 | export * from "./xGPU/GPURenderer"; 5 | export * from "./xGPU/TextureRenderer"; 6 | export * from "./xGPU/GPUType"; 7 | export * from "./xGPU/BuiltIns"; 8 | export * from "./xGPU/PrimitiveType"; 9 | export * from "./xGPU/blendmodes/AlphaBlendMode"; 10 | export * from "./xGPU/blendmodes/BlendMode"; 11 | export * from "./xGPU/pipelines/Pipeline"; 12 | export * from "./xGPU/pipelines/RenderPipeline"; 13 | export * from "./xGPU/pipelines/ComputePipeline"; 14 | export * from "./xGPU/pipelines/VertexShaderDebuggerPipeline"; 15 | export * from "./xGPU/pipelines/resources/IndexBuffer"; 16 | export * from "./xGPU/pipelines/resources/textures/Texture"; 17 | export * from "./xGPU/pipelines/resources/textures/DepthStencilTexture"; 18 | export * from "./xGPU/pipelines/resources/textures/MultiSampleTexture"; 19 | export * from "./xGPU/pipelines/PipelinePlugin"; 20 | export * from "./xGPU/shader/Bindgroup"; 21 | export * from "./xGPU/shader/Bindgroups"; 22 | export * from "./xGPU/shader/ComputeShader"; 23 | export * from "./xGPU/shader/FragmentShader"; 24 | export * from "./xGPU/shader/ShaderType"; 25 | export * from "./xGPU/shader/VertexShader"; 26 | export * from "./xGPU/shader/shaderParts/ShaderNode"; 27 | export * from "./xGPU/shader/shaderParts/ShaderStage"; 28 | export * from "./xGPU/shader/shaderParts/ShaderStruct"; 29 | export * from "./xGPU/shader/resources/IShaderResource"; 30 | export * from "./xGPU/shader/resources/CubeMapTexture"; 31 | export * from "./xGPU/shader/resources/ImageTexture"; 32 | export * from "./xGPU/shader/resources/ImageTextureArray"; 33 | export * from "./xGPU/pipelines/resources/textures/DepthTextureArray"; 34 | export * from "./xGPU/shader/resources/ImageTextureIO"; 35 | export * from "./xGPU/shader/resources/TextureSampler"; 36 | export * from "./xGPU/shader/resources/UniformBuffer"; 37 | export * from "./xGPU/shader/resources/UniformGroup"; 38 | export * from "./xGPU/shader/resources/UniformGroupArray"; 39 | export * from "./xGPU/shader/resources/VertexAttribute"; 40 | export * from "./xGPU/shader/resources/VertexBuffer"; 41 | export * from "./xGPU/shader/resources/VertexBufferIO"; 42 | export * from "./xGPU/shader/resources/VideoTexture"; 43 | export * from "./xGPU/pipelines/resources/textures/RenderPassTexture"; 44 | export * from "./xGPU/shader/resources/attributes/FloatBuffer"; 45 | export * from "./xGPU/shader/resources/attributes/Vec2Buffer"; 46 | export * from "./xGPU/shader/resources/attributes/Vec3Buffer"; 47 | export * from "./xGPU/shader/resources/attributes/Vec4Buffer"; 48 | export * from "./xGPU/shader/resources/attributes/IntBuffer"; 49 | export * from "./xGPU/shader/resources/attributes/IVec2Buffer"; 50 | export * from "./xGPU/shader/resources/attributes/IVec3Buffer"; 51 | export * from "./xGPU/shader/resources/attributes/IVec4Buffer"; 52 | export * from "./xGPU/shader/resources/attributes/UintBuffer"; 53 | export * from "./xGPU/shader/resources/attributes/UVec2Buffer"; 54 | export * from "./xGPU/shader/resources/attributes/UVec3Buffer"; 55 | export * from "./xGPU/shader/resources/attributes/UVec4Buffer"; 56 | export * from "./xGPU/HighLevelParser"; 57 | -------------------------------------------------------------------------------- /dist/index.js: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2023 Thomas Le Coz. All rights reserved. 2 | // This code is governed by an MIT license that can be found in the LICENSE file. 3 | export * from "./xGPU/XGPU"; 4 | export * from "./xGPU/EventDispatcher"; 5 | export * from "./xGPU/IRenderer"; 6 | export * from "./xGPU/GPURenderer"; 7 | //export * from "./xGPU/GPURendererV2" 8 | export * from "./xGPU/TextureRenderer"; 9 | export * from "./xGPU/GPUType"; 10 | export * from "./xGPU/BuiltIns"; 11 | export * from "./xGPU/PrimitiveType"; 12 | export * from "./xGPU/blendmodes/AlphaBlendMode"; 13 | export * from "./xGPU/blendmodes/BlendMode"; 14 | export * from "./xGPU/pipelines/Pipeline"; 15 | export * from "./xGPU/pipelines/RenderPipeline"; 16 | export * from "./xGPU/pipelines/ComputePipeline"; 17 | export * from "./xGPU/pipelines/VertexShaderDebuggerPipeline"; 18 | export * from "./xGPU/pipelines/resources/IndexBuffer"; 19 | export * from "./xGPU/pipelines/resources/textures/Texture"; 20 | export * from "./xGPU/pipelines/resources/textures/DepthStencilTexture"; 21 | export * from "./xGPU/pipelines/resources/textures/MultiSampleTexture"; 22 | export * from "./xGPU/pipelines/PipelinePlugin"; 23 | export * from "./xGPU/shader/Bindgroup"; 24 | export * from "./xGPU/shader/Bindgroups"; 25 | export * from "./xGPU/shader/ComputeShader"; 26 | export * from "./xGPU/shader/FragmentShader"; 27 | export * from "./xGPU/shader/ShaderType"; 28 | export * from "./xGPU/shader/VertexShader"; 29 | export * from "./xGPU/shader/shaderParts/ShaderNode"; 30 | export * from "./xGPU/shader/shaderParts/ShaderStage"; 31 | export * from "./xGPU/shader/shaderParts/ShaderStruct"; 32 | export * from "./xGPU/shader/resources/IShaderResource"; 33 | export * from "./xGPU/shader/resources/CubeMapTexture"; 34 | export * from "./xGPU/shader/resources/ImageTexture"; 35 | export * from "./xGPU/shader/resources/ImageTextureArray"; 36 | export * from "./xGPU/pipelines/resources/textures/DepthTextureArray"; 37 | export * from "./xGPU/shader/resources/ImageTextureIO"; 38 | export * from "./xGPU/shader/resources/TextureSampler"; 39 | export * from "./xGPU/shader/resources/UniformBuffer"; 40 | export * from "./xGPU/shader/resources/UniformGroup"; 41 | export * from "./xGPU/shader/resources/UniformGroupArray"; 42 | export * from "./xGPU/shader/resources/VertexAttribute"; 43 | export * from "./xGPU/shader/resources/VertexBuffer"; 44 | export * from "./xGPU/shader/resources/VertexBufferIO"; 45 | export * from "./xGPU/shader/resources/VideoTexture"; 46 | export * from "./xGPU/pipelines/resources/textures/RenderPassTexture"; 47 | export * from "./xGPU/shader/resources/attributes/FloatBuffer"; 48 | export * from "./xGPU/shader/resources/attributes/Vec2Buffer"; 49 | export * from "./xGPU/shader/resources/attributes/Vec3Buffer"; 50 | export * from "./xGPU/shader/resources/attributes/Vec4Buffer"; 51 | export * from "./xGPU/shader/resources/attributes/IntBuffer"; 52 | export * from "./xGPU/shader/resources/attributes/IVec2Buffer"; 53 | export * from "./xGPU/shader/resources/attributes/IVec3Buffer"; 54 | export * from "./xGPU/shader/resources/attributes/IVec4Buffer"; 55 | export * from "./xGPU/shader/resources/attributes/UintBuffer"; 56 | export * from "./xGPU/shader/resources/attributes/UVec2Buffer"; 57 | export * from "./xGPU/shader/resources/attributes/UVec3Buffer"; 58 | export * from "./xGPU/shader/resources/attributes/UVec4Buffer"; 59 | export * from "./xGPU/HighLevelParser"; 60 | -------------------------------------------------------------------------------- /dist/samples.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/tlecoz/XGPU/b2230801e3a9370f23b496986420a236eded31d3/dist/samples.jpg -------------------------------------------------------------------------------- /dist/xGPU/EventDispatcher.d.ts: -------------------------------------------------------------------------------- 1 | export declare class EventDispatcher { 2 | protected eventListeners: any; 3 | constructor(); 4 | addEventListener(eventName: string, callback: (data?: any) => void, removeListenerAfterDispatch?: boolean): void; 5 | removeEventListener(eventName: string, callback: (dispatcher: EventDispatcher, data?: any) => void): void; 6 | clearEvents(eventName: any): void; 7 | hasEventListener(eventName: any): boolean; 8 | dispatchEvent(eventName: string, eventData?: any): void; 9 | } 10 | -------------------------------------------------------------------------------- /dist/xGPU/EventDispatcher.js: -------------------------------------------------------------------------------- 1 | export class EventDispatcher { 2 | eventListeners = {}; 3 | constructor() { 4 | } 5 | addEventListener(eventName, callback, removeListenerAfterDispatch = false) { 6 | if (!this.eventListeners[eventName]) 7 | this.eventListeners[eventName] = []; 8 | if (removeListenerAfterDispatch) 9 | callback.removeAfter = true; 10 | this.eventListeners[eventName].push(callback); 11 | } 12 | removeEventListener(eventName, callback) { 13 | if (this.eventListeners[eventName]) { 14 | const id = this.eventListeners[eventName].indexOf(callback); 15 | if (id != -1) { 16 | this.eventListeners[eventName].splice(id, 1); 17 | } 18 | } 19 | } 20 | clearEvents(eventName) { 21 | this.addEventListener[eventName] = []; 22 | } 23 | hasEventListener(eventName) { return !!this.eventListeners[eventName]; } 24 | dispatchEvent(eventName, eventData) { 25 | if (this.eventListeners[eventName]) { 26 | const t = [...this.eventListeners[eventName]]; 27 | t.forEach(callback => { 28 | callback(eventData); 29 | if (callback.removeAfter) 30 | this.removeEventListener(eventName, callback); 31 | }); 32 | } 33 | } 34 | } 35 | -------------------------------------------------------------------------------- /dist/xGPU/GPURenderer.d.ts: -------------------------------------------------------------------------------- 1 | /// 2 | import { EventDispatcher } from "./EventDispatcher"; 3 | import { IRenderer } from "./IRenderer"; 4 | import { RenderPipeline } from "./pipelines/RenderPipeline"; 5 | export declare class GPURenderer extends EventDispatcher implements IRenderer { 6 | static ON_DRAW_END: string; 7 | protected domElement: HTMLCanvasElement; 8 | protected canvasView: GPUTextureView; 9 | protected ctx: GPUCanvasContext; 10 | protected currentWidth: number; 11 | protected currentHeight: number; 12 | protected dimensionChanged: boolean; 13 | protected deviceId: number; 14 | frameId: number; 15 | protected nbColorAttachment: number; 16 | renderPipelines: RenderPipeline[]; 17 | private static texturedQuadPipeline; 18 | protected texturedQuadPipeline: any; 19 | constructor(); 20 | resize(w: number, h: number): void; 21 | destroy(): void; 22 | protected gpuCtxConfiguration: any; 23 | initCanvas(canvas: HTMLCanvasElement, alphaMode?: "opaque" | "premultiplied"): Promise; 24 | get resized(): boolean; 25 | get firstPipeline(): RenderPipeline; 26 | get texture(): GPUTexture; 27 | get view(): GPUTextureView; 28 | get width(): number; 29 | get height(): number; 30 | get canvas(): HTMLCanvasElement; 31 | addPipeline(pipeline: RenderPipeline, offset?: number): RenderPipeline; 32 | removePipeline(pipeline: RenderPipeline): RenderPipeline; 33 | get nbPipeline(): number; 34 | get useSinglePipeline(): boolean; 35 | configure(textureUsage?: GPUTextureUsageFlags, alphaMode?: "opaque" | "premultiplied"): void; 36 | commandEncoder: GPUCommandEncoder; 37 | update(): Promise; 38 | } 39 | -------------------------------------------------------------------------------- /dist/xGPU/GPUType.d.ts: -------------------------------------------------------------------------------- 1 | export declare class GPUType { 2 | private _isVector; 3 | private _isMatrix; 4 | private _isArray; 5 | private _vecType; 6 | private _arrayLen; 7 | private _primitive; 8 | private _matrixColumns; 9 | private _matrixRows; 10 | private _alignOf; 11 | private _sizeOf; 12 | private _dataType; 13 | private _rawType; 14 | constructor(dataType: string); 15 | private renameDataType; 16 | get isPrimitive(): boolean; 17 | get isVector(): boolean; 18 | get isMatrix(): boolean; 19 | get isArray(): boolean; 20 | get isMatrixOfVectors(): boolean; 21 | get isArrayOfVectors(): boolean; 22 | get isArrayOfMatrixs(): boolean; 23 | get vectorType(): number; 24 | get arrayLength(): number; 25 | get matrixColumns(): number; 26 | get matrixRows(): number; 27 | get primitive(): "u32" | "i32" | "f32" | "f16"; 28 | get nbValues(): number; 29 | get byteSize(): number; 30 | get byteAlign(): number; 31 | set byteAlign(n: number); 32 | get dataType(): string; 33 | get rawType(): string; 34 | get byteValue(): number; 35 | private getMatrixBytesStructure; 36 | private getPrimitiveDataType; 37 | } 38 | -------------------------------------------------------------------------------- /dist/xGPU/HighLevelParser.d.ts: -------------------------------------------------------------------------------- 1 | import { DrawConfig } from "./pipelines/resources/DrawConfig"; 2 | export declare class HighLevelParser { 3 | constructor(); 4 | protected parseShaderBuiltins(descriptor: any): any; 5 | protected parseVertexBufferIOs(descriptor: any): any; 6 | protected parseImageTextureIOs(descriptor: any): any; 7 | protected parseVertexBuffers(descriptor: any): any; 8 | protected parseVertexAttributes(descriptor: any): any; 9 | protected parseUniformBuffers(descriptor: any): any; 10 | protected parseUniform(descriptor: any): any; 11 | protected parseImageTextureArray(descriptor: any): any; 12 | protected parseImageTexture(descriptor: any): any; 13 | protected parseTextureSampler(descriptor: any): any; 14 | protected parseVideoTexture(descriptor: any): any; 15 | protected parseCubeMapTexture(descriptor: any): any; 16 | protected parseDrawConfig(descriptor: any, drawConfig: DrawConfig): any; 17 | protected parseBindgroup(descriptor: any): any; 18 | protected firstPass(descriptor: any, target: "render" | "compute" | "bindgroup", drawConfig?: DrawConfig): any; 19 | protected parseHighLevelObj(descriptor: any): any; 20 | protected findAndFixRepetitionInDataStructure(o: any): any; 21 | protected targetIsBindgroup: boolean; 22 | protected parseBindgroupEntries(descriptor: any): any; 23 | private parseDebugValues; 24 | private parseVertexShaderDebug; 25 | parse(descriptor: any, target: "render" | "compute" | "bindgroup", drawConfig?: DrawConfig): any; 26 | private static instance; 27 | static parse(descriptor: any, target: "render" | "compute" | "bindgroup", drawConfig?: DrawConfig): any; 28 | } 29 | -------------------------------------------------------------------------------- /dist/xGPU/IRenderer.d.ts: -------------------------------------------------------------------------------- 1 | /// 2 | import { RenderPipeline } from "./pipelines/RenderPipeline"; 3 | export interface IRenderer { 4 | addPipeline(pipeline: RenderPipeline, offset?: number): void; 5 | resize(w: number, h: number): any; 6 | destroy(): void; 7 | update(): void; 8 | get renderPipelines(): RenderPipeline[]; 9 | get canvas(): HTMLCanvasElement; 10 | get resized(): boolean; 11 | get width(): number; 12 | get height(): number; 13 | get texture(): GPUTexture; 14 | get view(): GPUTextureView; 15 | get frameId(): number; 16 | get commandEncoder(): GPUCommandEncoder; 17 | } 18 | -------------------------------------------------------------------------------- /dist/xGPU/IRenderer.js: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2023 Thomas Le Coz. All rights reserved. 2 | // This code is governed by an MIT license that can be found in the LICENSE file. 3 | export {}; 4 | -------------------------------------------------------------------------------- /dist/xGPU/TextureRenderer.d.ts: -------------------------------------------------------------------------------- 1 | /// 2 | import { RenderPipeline } from "./pipelines/RenderPipeline"; 3 | import { Texture } from "./pipelines/resources/textures/Texture"; 4 | import { IRenderer } from "./IRenderer"; 5 | export declare class TextureRenderer implements IRenderer { 6 | protected textureObj: Texture; 7 | protected dimensionChanged: boolean; 8 | protected currentWidth: number; 9 | protected currentHeight: number; 10 | renderPipelines: RenderPipeline[]; 11 | protected useTextureInComputeShader: any; 12 | frameId: number; 13 | constructor(useTextureInComputeShader?: boolean); 14 | protected deviceId: number; 15 | init(w: number, h: number, usage?: number, sampleCount?: number): Promise; 16 | protected nbColorAttachment: number; 17 | addPipeline(pipeline: RenderPipeline, offset?: number): RenderPipeline; 18 | removePipeline(pipeline: RenderPipeline): RenderPipeline; 19 | resize(w: number, h: number): void; 20 | destroy(): void; 21 | commandEncoder: GPUCommandEncoder; 22 | update(): Promise; 23 | get resized(): boolean; 24 | get canvas(): HTMLCanvasElement; 25 | get width(): number; 26 | get height(): number; 27 | get texture(): GPUTexture; 28 | get view(): GPUTextureView; 29 | } 30 | -------------------------------------------------------------------------------- /dist/xGPU/WebGPUProperties.d.ts: -------------------------------------------------------------------------------- 1 | export declare class WebGPUProperties { 2 | private static build; 3 | private static resolve; 4 | private static getResult; 5 | private static ready; 6 | private static textureUsage; 7 | private static bufferUsage; 8 | private static shaderStage; 9 | static init(): Promise; 10 | private static _instance; 11 | constructor(); 12 | static getTextureUsageById(id: number): string; 13 | static getBufferUsageById(id: number): string; 14 | static getShaderStageById(id: number): string; 15 | } 16 | -------------------------------------------------------------------------------- /dist/xGPU/WebGPUProperties.js: -------------------------------------------------------------------------------- 1 | export class WebGPUProperties { 2 | static build(obj, currentId, currentNames) { 3 | let infoById = {}; 4 | let processedIds = new Set(); 5 | let stack = [{ id: currentId, names: currentNames }]; 6 | while (stack.length > 0) { 7 | let current = stack.pop(); 8 | let currentId = current.id; 9 | let currentNames = current.names; 10 | if (processedIds.has(currentId)) 11 | continue; 12 | for (let name in obj) { 13 | let id = obj[name]; 14 | let combinedId = currentId | id; 15 | let combinedNames = [...new Set(currentNames.concat(name))]; 16 | if (!(combinedId in infoById)) { 17 | infoById[combinedId] = combinedNames; 18 | stack.push({ id: combinedId, names: combinedNames }); 19 | } 20 | else { 21 | infoById[combinedId] = [...new Set(infoById[combinedId].concat(combinedNames))]; 22 | } 23 | } 24 | processedIds.add(currentId); 25 | } 26 | return infoById; 27 | } 28 | static resolve(obj, id) { 29 | if (id in obj) 30 | return obj[id].join("|"); 31 | return "undefined"; 32 | } 33 | static async getResult(WebGpuObject) { 34 | return new Promise((resolve) => { 35 | const result = this.build(WebGpuObject, 0, []); 36 | setTimeout(() => { 37 | //i make a pause to unblock the thread 38 | resolve(result); 39 | }, 1); 40 | }); 41 | } 42 | static ready = false; 43 | static textureUsage; 44 | static bufferUsage; 45 | static shaderStage; 46 | static async init() { 47 | if (!this._instance) 48 | new WebGPUProperties(); 49 | return new Promise(async (resolve) => { 50 | if (this.ready) 51 | resolve(); 52 | else { 53 | this.bufferUsage = await this.getResult(GPUBufferUsage); 54 | this.shaderStage = await this.getResult(GPUShaderStage); 55 | this.textureUsage = await this.getResult(GPUTextureUsage); 56 | this.ready = true; 57 | resolve(); 58 | } 59 | }); 60 | } 61 | static _instance; 62 | constructor() { 63 | if (WebGPUProperties._instance) { 64 | throw new Error("WebGPUProperties is not instanciable"); 65 | } 66 | WebGPUProperties._instance = this; 67 | } 68 | static getTextureUsageById(id) { 69 | return this.resolve(this.textureUsage, id); 70 | } 71 | static getBufferUsageById(id) { 72 | return this.resolve(this.bufferUsage, id); 73 | } 74 | static getShaderStageById(id) { 75 | return this.resolve(this.shaderStage, id); 76 | } 77 | } 78 | -------------------------------------------------------------------------------- /dist/xGPU/XGPU.d.ts: -------------------------------------------------------------------------------- 1 | /// 2 | import { Uniformable } from "./shader/resources/UniformGroup"; 3 | export type TransferableUniforms = { 4 | items: { 5 | name: string; 6 | type: string; 7 | values: any; 8 | groups?: any; 9 | items?: any; 10 | }; 11 | transferables: ArrayBuffer[]; 12 | }; 13 | export declare class XGPU { 14 | static showVertexShader: boolean; 15 | static showFragmentShader: boolean; 16 | static showComputeShader: boolean; 17 | static showVertexDebuggerShader: boolean; 18 | private static _ready; 19 | static get ready(): boolean; 20 | protected static gpuDevice: GPUDevice; 21 | static debugUsage(usage: number): string; 22 | static debugTextureUsage(usage: number): string; 23 | static debugShaderStage(n: number): string; 24 | constructor(); 25 | private static requestAdapterOptions; 26 | private static losingDevice; 27 | static deviceLost: boolean; 28 | private static deviceLostTime; 29 | static deviceId: number; 30 | static loseDevice(): void; 31 | static clear(): void; 32 | static get loseDeviceRecently(): boolean; 33 | static getTransferableUniforms(uniforms: { 34 | [key: string]: Uniformable; 35 | }): TransferableUniforms; 36 | static parseTransferableUniform(uniforms: TransferableUniforms): { 37 | [key: string]: Uniformable; 38 | }; 39 | static init(options?: { 40 | powerPreference?: "low-power" | "high-performance"; 41 | forceFallbackAdaoter?: boolean; 42 | }): Promise; 43 | static get device(): GPUDevice; 44 | private static _preferedCanvasFormat; 45 | static getPreferredCanvasFormat(): GPUTextureFormat; 46 | static setPreferredCanvasFormat(format: GPUTextureFormat): void; 47 | static destroy(): void; 48 | static createBindgroup(o: any): GPUBindGroup; 49 | static createBindgroupLayout(o: any): GPUBindGroupLayout; 50 | static createPipelineLayout(o: any): GPUPipelineLayout; 51 | static createRenderPipeline(o: any): GPURenderPipeline; 52 | static createComputePipeline(o: any): GPUComputePipeline; 53 | static createStagingBuffer(size: number): GPUBuffer; 54 | } 55 | -------------------------------------------------------------------------------- /dist/xGPU/blendmodes/AlphaBlendMode.d.ts: -------------------------------------------------------------------------------- 1 | import { BlendMode } from "./BlendMode"; 2 | export declare class AlphaBlendMode extends BlendMode { 3 | constructor(); 4 | } 5 | -------------------------------------------------------------------------------- /dist/xGPU/blendmodes/AlphaBlendMode.js: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2023 Thomas Le Coz. All rights reserved. 2 | // This code is governed by an MIT license that can be found in the LICENSE file. 3 | import { BlendMode } from "./BlendMode"; 4 | export class AlphaBlendMode extends BlendMode { 5 | constructor() { 6 | super(); 7 | this.color.operation = "add"; 8 | this.color.srcFactor = "src-alpha"; 9 | this.color.dstFactor = "one-minus-src-alpha"; 10 | this.alpha.operation = "add"; 11 | this.alpha.srcFactor = "src-alpha"; 12 | this.alpha.dstFactor = "one-minus-src-alpha"; 13 | } 14 | } 15 | -------------------------------------------------------------------------------- /dist/xGPU/blendmodes/BlendMode.d.ts: -------------------------------------------------------------------------------- 1 | export declare abstract class BlendMode { 2 | color: { 3 | operation: "add" | "subtract" | "reverse-subtract" | "min" | "max"; 4 | srcFactor: "zero" | "one" | "src" | "one-minus-src" | "src-alpha" | "one-minus-src-alpha" | "dst" | "one-minus-dst" | "one-minus-dst-alpha" | "src-alpha-saturated" | "constant" | "one-minus-constant"; 5 | dstFactor: "zero" | "one" | "src" | "one-minus-src" | "src-alpha" | "one-minus-src-alpha" | "dst" | "one-minus-dst" | "one-minus-dst-alpha" | "src-alpha-saturated" | "constant" | "one-minus-constant"; 6 | }; 7 | alpha: { 8 | operation: "add" | "subtract" | "reverse-subtract" | "min" | "max"; 9 | srcFactor: "zero" | "one" | "src" | "one-minus-src" | "src-alpha" | "one-minus-src-alpha" | "dst" | "one-minus-dst" | "one-minus-dst-alpha" | "src-alpha-saturated" | "constant" | "one-minus-constant"; 10 | dstFactor: "zero" | "one" | "src" | "one-minus-src" | "src-alpha" | "one-minus-src-alpha" | "dst" | "one-minus-dst" | "one-minus-dst-alpha" | "src-alpha-saturated" | "constant" | "one-minus-constant"; 11 | }; 12 | constructor(); 13 | } 14 | -------------------------------------------------------------------------------- /dist/xGPU/blendmodes/BlendMode.js: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2023 Thomas Le Coz. All rights reserved. 2 | // This code is governed by an MIT license that can be found in the LICENSE file. 3 | export class BlendMode { 4 | color = { operation: "add", srcFactor: "one", dstFactor: "zero" }; 5 | alpha = { operation: "add", srcFactor: "one", dstFactor: "zero" }; 6 | constructor() { 7 | } 8 | } 9 | -------------------------------------------------------------------------------- /dist/xGPU/pipelines/ComputePipeline.d.ts: -------------------------------------------------------------------------------- 1 | /// 2 | import { ComputeShader } from "../shader/ComputeShader"; 3 | import { ImageTextureIO } from "../shader/resources/ImageTextureIO"; 4 | import { VertexBuffer } from "../shader/resources/VertexBuffer"; 5 | import { VertexBufferIO } from "../shader/resources/VertexBufferIO"; 6 | import { Pipeline } from "./Pipeline"; 7 | import { ImageTexture } from "../shader/resources/ImageTexture"; 8 | export declare class ComputePipeline extends Pipeline { 9 | static ON_COMPUTE_SHADER_CODE_BUILT: string; 10 | static ON_COMPUTE_BEGIN: string; 11 | static ON_COMPUTE_END: string; 12 | static ON_GPU_PIPELINE_BUILT: string; 13 | static ON_INIT_FROM_OBJECT: string; 14 | static ON_DESTROY: string; 15 | static ON_DEVICE_LOST: string; 16 | static ON_UPDATE_RESOURCES: string; 17 | static ON_SUBMIT_QUEUE: string; 18 | computeShader: ComputeShader; 19 | protected gpuComputePipeline: GPUComputePipeline; 20 | workgroups: number[]; 21 | protected dispatchWorkgroup: number[]; 22 | protected bufferSize: number; 23 | protected textureSize: number[]; 24 | protected stagingBuffer: GPUBuffer; 25 | protected bufferIOs: VertexBuffer[]; 26 | protected textureIOs: ImageTexture[]; 27 | onComputeBegin: () => void; 28 | onComputeEnd: () => void; 29 | onShaderBuild: (shaderInfos: { 30 | code: string; 31 | }) => void; 32 | constructor(); 33 | set useRenderPipeline(b: boolean); 34 | initFromObject(descriptor: { 35 | bindgroups?: any; 36 | computeShader: { 37 | outputs?: any; 38 | main: string; 39 | inputs?: any; 40 | constants?: string; 41 | } | string | ComputeShader; 42 | [key: string]: unknown; 43 | }): { 44 | [key: string]: unknown; 45 | bindgroups?: any; 46 | computeShader: { 47 | outputs?: any; 48 | main: string; 49 | inputs?: any; 50 | constants?: string; 51 | } | string | ComputeShader; 52 | }; 53 | destroy(): void; 54 | setWorkgroups(x: number, y?: number, z?: number): void; 55 | setDispatchWorkgroup(x?: number, y?: number, z?: number): void; 56 | protected vertexBufferIOs: VertexBufferIO[]; 57 | protected imageTextureIOs: ImageTextureIO[]; 58 | protected resourceIOs: (VertexBufferIO | ImageTextureIO)[]; 59 | protected nbVertexMax: number; 60 | protected widthMax: number; 61 | protected heightMax: number; 62 | protected initResourceIOs(): void; 63 | protected deviceId: number; 64 | protected lastFrameTime: number; 65 | update(): void; 66 | protected setupDefaultWorkgroups(): void; 67 | protected rebuildingAfterDeviceLost: boolean; 68 | clearAfterDeviceLostAndRebuild(): void; 69 | buildGpuPipeline(): GPUComputePipeline; 70 | private firstFrame; 71 | private processingFirstFrame; 72 | private waitingFrame; 73 | nextFrame(): Promise; 74 | } 75 | -------------------------------------------------------------------------------- /dist/xGPU/pipelines/Pipeline.d.ts: -------------------------------------------------------------------------------- 1 | /// 2 | import { Bindgroup } from "../shader/Bindgroup"; 3 | import { Bindgroups } from "../shader/Bindgroups"; 4 | import { FragmentShader } from "../shader/FragmentShader"; 5 | import { IShaderResource } from "../shader/resources/IShaderResource"; 6 | import { VertexBuffer } from "../shader/resources/VertexBuffer"; 7 | import { ShaderStruct } from "../shader/shaderParts/ShaderStruct"; 8 | import { VertexShader } from "../shader/VertexShader"; 9 | import { PrimitiveFloatUniform, PrimitiveIntUniform, PrimitiveUintUniform } from "../PrimitiveType"; 10 | import { EventDispatcher } from "../EventDispatcher"; 11 | export declare class Pipeline extends EventDispatcher { 12 | description: any; 13 | nbVertex: number; 14 | bindGroups: Bindgroups; 15 | vertexBuffers: VertexBuffer[]; 16 | vertexShader: VertexShader; 17 | fragmentShader: FragmentShader; 18 | protected vertexBufferLayouts: Iterable; 19 | protected gpuBindgroups: GPUBindGroup[]; 20 | protected gpuBindGroupLayouts: GPUBindGroupLayout[]; 21 | protected gpuPipelineLayout: GPUPipelineLayout; 22 | type: "compute" | "compute_mixed" | "render"; 23 | constructor(); 24 | get isComputePipeline(): boolean; 25 | get isRenderPipeline(): boolean; 26 | get isMixedPipeline(): boolean; 27 | protected _resources: any; 28 | get resources(): any; 29 | debug: string; 30 | clearAfterDeviceLostAndRebuild(): void; 31 | initFromObject(obj: any): void; 32 | pipelineCount: number; 33 | static getResourceDefinition(resources: any): any; 34 | addBindgroup(group: Bindgroup): void; 35 | protected createVertexBufferLayout(): any; 36 | protected createShaderInput(shader: VertexShader, buffers: VertexBuffer[]): ShaderStruct; 37 | protected createLayouts(): void; 38 | protected initPipelineResources(pipeline: Pipeline): void; 39 | protected build(): void; 40 | update(o?: any): void; 41 | getResourceName(resource: any): string; 42 | createPipelineInstanceArray(resources: (PrimitiveFloatUniform | PrimitiveIntUniform | PrimitiveUintUniform | IShaderResource)[], nbInstance: number): any[]; 43 | } 44 | -------------------------------------------------------------------------------- /dist/xGPU/pipelines/PipelinePlugin.d.ts: -------------------------------------------------------------------------------- 1 | import { ShaderNode } from "../shader/shaderParts/ShaderNode"; 2 | import { Pipeline } from "./Pipeline"; 3 | export declare class PipelinePlugin { 4 | protected target: Pipeline; 5 | protected requiredNames: any; 6 | bindgroupResources: any; 7 | vertexShader: { 8 | outputs?: any; 9 | inputs?: any; 10 | constants?: string; 11 | main?: string | string[]; 12 | }; 13 | fragmentShader: { 14 | outputs?: any; 15 | inputs?: any; 16 | constants?: string; 17 | main?: string | string[]; 18 | }; 19 | constructor(target: Pipeline, required?: any); 20 | apply(vertexShaderNode?: ShaderNode, fragmentShaderNode?: ShaderNode): PipelinePlugin; 21 | } 22 | -------------------------------------------------------------------------------- /dist/xGPU/pipelines/PipelinePlugin.js: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2023 Thomas Le Coz. All rights reserved. 2 | // This code is governed by an MIT license that can be found in the LICENSE file. 3 | export class PipelinePlugin { 4 | target; 5 | requiredNames; 6 | bindgroupResources = {}; 7 | vertexShader = {}; 8 | fragmentShader = {}; 9 | constructor(target, required) { 10 | this.target = target; 11 | if (required) { 12 | this.requiredNames = {}; 13 | for (let z in required) { 14 | this.requiredNames[z] = target.getResourceName(required[z]); 15 | } 16 | } 17 | } 18 | apply(vertexShaderNode = null, fragmentShaderNode = null) { 19 | //if (!this.target.resources.bindgroups.plugins) this.target.resources.bindgroups.plugins = {}; 20 | //const plugins = this.target.resources.bindgroups.plugins; 21 | let plugins; 22 | for (let z in this.target.resources.bindgroups) { 23 | plugins = this.target.resources.bindgroups[z]; 24 | break; 25 | } 26 | for (let z in this.bindgroupResources) 27 | plugins[z] = this.bindgroupResources[z]; 28 | //------ VERTEX SHADER -------- 29 | let vs = this.target.resources.vertexShader; 30 | if (typeof vs === "string") 31 | vs = { main: vs }; 32 | if (this.vertexShader.outputs) { 33 | if (!vs.outputs) 34 | vs.outputs = {}; 35 | for (let z in this.vertexShader.outputs) { 36 | vs.outputs[z] = this.vertexShader.outputs[z]; 37 | } 38 | } 39 | if (this.vertexShader.inputs) { 40 | if (!vs.inputs) 41 | vs.inputs = {}; 42 | for (let z in this.vertexShader.inputs) { 43 | vs.inputs[z] = this.vertexShader.inputs[z]; 44 | } 45 | } 46 | if (this.vertexShader.constants) { 47 | if (!vs.constants) 48 | vs.constants = ""; 49 | vs.constants += this.vertexShader.constants; 50 | } 51 | if (this.vertexShader.main) { 52 | let main; 53 | if (typeof this.vertexShader.main === "string") 54 | main = this.vertexShader.main; 55 | else 56 | main = this.vertexShader.main.join("\n"); 57 | if (vertexShaderNode) 58 | vertexShaderNode.text = main; 59 | else { 60 | if (!vs.main) 61 | vs.main = ""; 62 | vs.main += main; 63 | } 64 | } 65 | this.target.resources.vertexShader = vs; 66 | //-------- FRAGMENT SHADER -------- 67 | let fs = this.target.resources.fragmentShader; 68 | if (typeof fs === "string") 69 | fs = { main: fs }; 70 | if (this.fragmentShader.outputs) { 71 | if (!fs.outputs) 72 | fs.outputs = {}; 73 | for (let z in this.fragmentShader.outputs) { 74 | fs.outputs[z] = this.fragmentShader.outputs[z]; 75 | } 76 | } 77 | if (this.fragmentShader.inputs) { 78 | if (!fs.inputs) 79 | fs.inputs = {}; 80 | for (let z in this.fragmentShader.inputs) { 81 | fs.inputs[z] = this.fragmentShader.inputs[z]; 82 | } 83 | } 84 | if (this.fragmentShader.constants) { 85 | if (!fs.constants) 86 | fs.constants = ""; 87 | fs.constants += this.fragmentShader.constants; 88 | } 89 | if (this.fragmentShader.main) { 90 | let main; 91 | if (typeof this.fragmentShader.main === "string") 92 | main = this.fragmentShader.main; 93 | else 94 | main = this.fragmentShader.main.join("\n"); 95 | if (fragmentShaderNode) 96 | fragmentShaderNode.text = main; 97 | else { 98 | if (!fs.main) 99 | fs.main = ""; 100 | fs.main += main; 101 | } 102 | } 103 | this.target.resources.fragmentShader = fs; 104 | this.target.initFromObject(this.target.resources); 105 | return this; 106 | } 107 | } 108 | -------------------------------------------------------------------------------- /dist/xGPU/pipelines/VertexShaderDebuggerPipeline.d.ts: -------------------------------------------------------------------------------- 1 | import { ComputePipeline } from "./ComputePipeline"; 2 | import { RenderPipeline } from "./RenderPipeline"; 3 | import { IndexBuffer } from "./resources/IndexBuffer"; 4 | import { UniformBuffer } from "../shader/resources/UniformBuffer"; 5 | import { VertexBuffer } from "../shader/resources/VertexBuffer"; 6 | import { VertexBufferIO } from "../shader/resources/VertexBufferIO"; 7 | export declare class VertexShaderDebuggerPipeline extends ComputePipeline { 8 | onLog: (o: { 9 | config: any; 10 | results: any[]; 11 | nbValueByFieldName: any; 12 | renderPipeline: RenderPipeline; 13 | dataTypeByFieldname: any; 14 | }) => void; 15 | protected config: any; 16 | constructor(); 17 | protected vertexShaderInputs: any; 18 | protected renderPipeline: RenderPipeline; 19 | protected computeShaderObj: any; 20 | protected resourceByType: any; 21 | protected initRenderPipeline(renderPipeline: RenderPipeline): void; 22 | protected indexBuffer: IndexBuffer; 23 | protected setupIndexBuffer(): void; 24 | protected results: any; 25 | protected resultBufferStructure: any; 26 | protected nbValueByFieldIndex: any; 27 | protected nbValueByFieldName: any; 28 | protected dataTypeByFieldname: any; 29 | protected fieldNames: string[]; 30 | protected fieldNewNames: string[]; 31 | protected fieldIndexByName: any; 32 | protected attributes: any; 33 | protected setupDataStructure(): void; 34 | protected vertexIdName: string; 35 | protected instanceIdName: string; 36 | protected setupVertexShaderBuiltIns(): void; 37 | protected renderUniformBuffers: { 38 | name: string; 39 | resource: UniformBuffer; 40 | }[]; 41 | protected setupUniformBuffers(): void; 42 | protected renderVertexBuffers: { 43 | name: string; 44 | resource: VertexBuffer; 45 | }[]; 46 | protected bufferNameByAttributeName: string[]; 47 | protected setupVertexBuffers(): void; 48 | protected vertexBufferIO: VertexBufferIO; 49 | protected setupComputeShaderVertexBufferIO(): void; 50 | private convertLetIntoVar; 51 | private removeVar; 52 | protected writeComputeShader(): string; 53 | protected firstPass: boolean; 54 | protected writeVertexShader(debugObject: any): string; 55 | private writeArrayTemplate; 56 | private temporaryIndex; 57 | private writeMatrixTemplate; 58 | protected buildComputeShader(): void; 59 | protected copyUniformsFromRenderToCompute(): void; 60 | init(renderPipeline: RenderPipeline, nbVertex: number): void; 61 | private createEmptyArray; 62 | private getObjectByType; 63 | private getNbValueByType; 64 | private getNewInstanceByType; 65 | } 66 | -------------------------------------------------------------------------------- /dist/xGPU/pipelines/resources/DrawConfig.d.ts: -------------------------------------------------------------------------------- 1 | /// 2 | import { RenderPipeline } from "../RenderPipeline"; 3 | import { IndexBuffer } from "./IndexBuffer"; 4 | export declare class DrawConfig { 5 | vertexCount: number; 6 | instanceCount: number; 7 | firstVertexId: number; 8 | firstInstanceId: number; 9 | baseVertex: number; 10 | indexBuffer: IndexBuffer; 11 | protected pipeline: RenderPipeline; 12 | protected setupDrawCompleted: boolean; 13 | constructor(renderPipeline: RenderPipeline); 14 | draw(renderPass: GPURenderPassEncoder): void; 15 | } 16 | -------------------------------------------------------------------------------- /dist/xGPU/pipelines/resources/DrawConfig.js: -------------------------------------------------------------------------------- 1 | export class DrawConfig { 2 | vertexCount = -1; 3 | instanceCount = 1; 4 | firstVertexId = 0; 5 | firstInstanceId = 0; 6 | baseVertex = 0; 7 | indexBuffer; 8 | pipeline; 9 | setupDrawCompleted = false; 10 | constructor(renderPipeline) { 11 | this.pipeline = renderPipeline; 12 | } 13 | draw(renderPass) { 14 | //console.log("DrawConfig.draw") 15 | if (this.indexBuffer) { 16 | //console.log(this.indexBuffer.nbPoint, this.instanceCount, this.firstVertexId, this.baseVertex, this.firstInstanceId) 17 | renderPass.setIndexBuffer(this.indexBuffer.gpuResource, this.indexBuffer.dataType, this.indexBuffer.offset, this.indexBuffer.getBufferSize()); 18 | renderPass.drawIndexed(this.indexBuffer.nbPoint, this.instanceCount, this.firstVertexId, this.baseVertex, this.firstInstanceId); 19 | } 20 | else { 21 | renderPass.draw(this.vertexCount, this.instanceCount, this.firstVertexId, this.firstInstanceId); 22 | } 23 | } 24 | } 25 | -------------------------------------------------------------------------------- /dist/xGPU/pipelines/resources/IndexBuffer.d.ts: -------------------------------------------------------------------------------- 1 | /// 2 | import { DrawConfig } from "./DrawConfig"; 3 | export type IndexBufferDescriptor = { 4 | nbPoint?: number; 5 | dataType?: "uint16" | "uint32"; 6 | datas?: Uint16Array | Uint32Array; 7 | offset?: number; 8 | }; 9 | export declare class IndexBuffer { 10 | gpuResource: GPUBuffer; 11 | descriptor: IndexBufferDescriptor; 12 | mustUpdateData: boolean; 13 | constructor(descriptor?: { 14 | nbPoint?: number; 15 | dataType?: "uint16" | "uint32"; 16 | datas?: Uint16Array | Uint32Array; 17 | offset?: number; 18 | }); 19 | destroyGpuResource(): void; 20 | createGpuResource(): void; 21 | getBufferSize(): number; 22 | get dataType(): GPUIndexFormat; 23 | get nbPoint(): number; 24 | set nbPoint(n: number); 25 | get offset(): number; 26 | set offset(n: number); 27 | private _datas; 28 | set datas(indices: Uint32Array | Uint16Array); 29 | updateDatas(indices: Uint32Array | Uint16Array, offset: number, len: number, extraBufferSize?: number): void; 30 | get datas(): Uint32Array | Uint16Array; 31 | update(): void; 32 | apply(renderPass: GPURenderPassEncoder, drawConfig: DrawConfig): void; 33 | } 34 | -------------------------------------------------------------------------------- /dist/xGPU/pipelines/resources/textures/DepthStencilTexture.d.ts: -------------------------------------------------------------------------------- 1 | /// 2 | import { IShaderResource } from "../../../shader/resources/IShaderResource"; 3 | import { Texture } from "./Texture"; 4 | export type DepthStencilTextureDescriptor = { 5 | size: GPUExtent3D; 6 | format?: "stencil8" | "depth16unorm" | "depth24plus" | "depth24plus-stencil8" | "depth32float"; 7 | }; 8 | export declare class DepthStencilTexture extends Texture implements IShaderResource { 9 | protected _isDepthTexture: boolean; 10 | private _description; 11 | get description(): { 12 | depthWriteEnabled: boolean; 13 | depthCompare: string; 14 | format: string; 15 | sampleCount?: number; 16 | }; 17 | private _attachment; 18 | get attachment(): any; 19 | constructor(descriptor: { 20 | size: GPUExtent3D; 21 | format?: "stencil8" | "depth16unorm" | "depth24plus" | "depth24plus-stencil8" | "depth32float"; 22 | usage?: GPUTextureUsageFlags; 23 | sampleCount?: number; 24 | }, depthStencilDescription?: { 25 | depthWriteEnabled: boolean; 26 | depthCompare: "never" | "less" | "equal" | "less-equal" | "greater" | "not-equal" | "greater-equal" | "always"; 27 | }, depthStencilAttachmentOptions?: any); 28 | get isDepthTexture(): boolean; 29 | mustBeTransfered: boolean; 30 | protected _visibility: GPUShaderStageFlags; 31 | setPipelineType(pipelineType: "compute" | "render" | "compute_mixed"): void; 32 | createBindGroupEntry(bindingId: number): { 33 | binding: number; 34 | resource: GPUTextureView; 35 | }; 36 | createBindGroupLayoutEntry(bindingId: number): { 37 | binding: number; 38 | visibility: number; 39 | texture: { 40 | sampleType: string; 41 | }; 42 | }; 43 | createDeclaration(varName: string, bindingId: number, groupId: number): string; 44 | createGpuResource(): void; 45 | destroyGpuResource(): void; 46 | resize(width: number, height: number): void; 47 | clone(): DepthStencilTexture; 48 | } 49 | -------------------------------------------------------------------------------- /dist/xGPU/pipelines/resources/textures/DepthStencilTexture.js: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2023 Thomas Le Coz. All rights reserved. 2 | // This code is governed by an MIT license that can be found in the LICENSE file. 3 | import { Texture } from "./Texture"; 4 | export class DepthStencilTexture extends Texture { 5 | /* 6 | When you apply a shadow to a renderPipeline , you actually create a ShadowPipeline that store information in the DepthStencilTexture. 7 | This texture is then used as IShaderResource in the renderPipeline. 8 | Because it can be an IShaderResource , we must implement the IShaderResource interface 9 | */ 10 | _isDepthTexture = false; 11 | _description; 12 | get description() { return this._description; } 13 | _attachment; 14 | get attachment() { return this._attachment; } 15 | ; 16 | constructor(descriptor, depthStencilDescription = null, depthStencilAttachmentOptions = null) { 17 | if (undefined === descriptor.format) 18 | descriptor.format = "depth24plus"; 19 | if (undefined === descriptor.sampleCount) 20 | descriptor.sampleCount = 1; 21 | super(descriptor); 22 | this.createGpuResource(); 23 | //-------- 24 | if (!depthStencilDescription) { 25 | depthStencilDescription = { 26 | depthWriteEnabled: true, 27 | depthCompare: "less", 28 | format: this.gpuResource.format 29 | }; 30 | } 31 | this._description = { format: this.gpuResource.format, ...depthStencilDescription }; 32 | //-------- 33 | this._attachment = { 34 | view: this._view, 35 | depthClearValue: 1, 36 | depthLoadOp: 'clear', 37 | depthStoreOp: 'store', 38 | }; 39 | if (descriptor.format === "depth24plus-stencil8") { 40 | this._attachment.stencilClearValue = 0; 41 | this._attachment.stencilLoadOp = "clear"; 42 | this._attachment.stencilStoreOp = "store"; 43 | } 44 | else if (descriptor.format === "depth32float") { 45 | this._isDepthTexture = true; 46 | } 47 | for (let z in depthStencilAttachmentOptions) { 48 | this._attachment[z] = depthStencilAttachmentOptions[z]; 49 | } 50 | } 51 | get isDepthTexture() { return this._isDepthTexture; } 52 | //--------------------------------- IShaderResource --------------------------------------------------------- 53 | mustBeTransfered = false; 54 | _visibility = GPUShaderStage.FRAGMENT; 55 | setPipelineType(pipelineType) { 56 | if (pipelineType === "render") 57 | this._visibility = GPUShaderStage.FRAGMENT; 58 | else if (pipelineType === "compute_mixed") 59 | this._visibility = GPUShaderStage.FRAGMENT | GPUShaderStage.COMPUTE; 60 | else if (pipelineType === "compute") 61 | this._visibility = GPUShaderStage.COMPUTE; 62 | } 63 | createBindGroupEntry(bindingId) { 64 | //console.log("view = ", this._view) 65 | return { 66 | binding: bindingId, 67 | resource: this._view 68 | }; 69 | } 70 | createBindGroupLayoutEntry(bindingId) { 71 | return { 72 | binding: bindingId, 73 | visibility: GPUShaderStage.FRAGMENT | GPUShaderStage.VERTEX, 74 | texture: { 75 | sampleType: "depth", 76 | } 77 | }; 78 | } 79 | createDeclaration(varName, bindingId, groupId) { 80 | return "@binding(" + bindingId + ") @group(" + groupId + ") var " + varName + ":texture_depth_2d;\n"; 81 | } 82 | createGpuResource() { 83 | //console.log("depthTexture create") 84 | this.create(); 85 | } 86 | destroyGpuResource() { 87 | if (this.gpuResource) { 88 | //console.warn("depthTexture destroy ") 89 | this._view = null; 90 | this.gpuResource.destroy(); 91 | this.gpuResource = null; 92 | this.create(); 93 | } 94 | } 95 | resize(width, height) { 96 | super.resize(width, height); 97 | this._attachment.view = this._view; 98 | } 99 | clone() { 100 | return new DepthStencilTexture(this.descriptor); 101 | } 102 | } 103 | -------------------------------------------------------------------------------- /dist/xGPU/pipelines/resources/textures/DepthTextureArray.d.ts: -------------------------------------------------------------------------------- 1 | /// 2 | import { ImageTextureArray } from "../../../shader/resources/ImageTextureArray"; 3 | import { DepthStencilTexture } from "./DepthStencilTexture"; 4 | export declare class DepthTextureArray extends ImageTextureArray { 5 | private _description; 6 | get description(): { 7 | depthWriteEnabled: boolean; 8 | depthCompare: string; 9 | format: string; 10 | sampleCount?: number; 11 | }; 12 | private _attachment; 13 | get attachment(): any; 14 | constructor(descriptor: { 15 | source: DepthStencilTexture[] | GPUTexture[]; 16 | size: GPUExtent3D; 17 | format?: "stencil8" | "depth16unorm" | "depth24plus" | "depth24plus-stencil8" | "depth32float"; 18 | usage?: GPUTextureUsageFlags; 19 | sampleCount?: number; 20 | }, depthStencilDescription?: { 21 | depthWriteEnabled: boolean; 22 | depthCompare: "never" | "less" | "equal" | "less-equal" | "greater" | "not-equal" | "greater-equal" | "always"; 23 | }); 24 | protected _visibility: GPUShaderStageFlags; 25 | setPipelineType(pipelineType: "compute" | "render" | "compute_mixed"): void; 26 | createBindGroupLayoutEntry(bindingId: number): { 27 | binding: number; 28 | visibility: number; 29 | texture: GPUTextureBindingLayout; 30 | }; 31 | get isDepthTexture(): boolean; 32 | createDeclaration(varName: string, bindingId: number, groupId: number): string; 33 | } 34 | -------------------------------------------------------------------------------- /dist/xGPU/pipelines/resources/textures/DepthTextureArray.js: -------------------------------------------------------------------------------- 1 | import { ImageTextureArray } from "../../../shader/resources/ImageTextureArray"; 2 | import { DepthStencilTexture } from "./DepthStencilTexture"; 3 | export class DepthTextureArray extends ImageTextureArray { 4 | _description; 5 | get description() { return this._description; } 6 | _attachment; 7 | get attachment() { return this._attachment; } 8 | ; 9 | constructor(descriptor, depthStencilDescription = null) { 10 | if (undefined === descriptor.format) 11 | descriptor.format = "depth32float"; 12 | if (undefined === descriptor.sampleCount) 13 | descriptor.sampleCount = 1; 14 | if (descriptor.source[0] instanceof DepthStencilTexture) { 15 | for (let i = 0; i < descriptor.source.length; i++) { 16 | descriptor.source[i] = descriptor.source[i].gpuResource; 17 | } 18 | } 19 | if (undefined === descriptor.usage) { 20 | descriptor.usage = descriptor.source[0].usage; 21 | } 22 | super(descriptor); 23 | //-------- 24 | if (!depthStencilDescription) { 25 | depthStencilDescription = { 26 | depthWriteEnabled: true, 27 | depthCompare: "less", 28 | format: this.gpuResource.format 29 | }; 30 | } 31 | this._description = { format: this.gpuResource.format, ...depthStencilDescription }; 32 | } 33 | _visibility = GPUShaderStage.FRAGMENT; 34 | setPipelineType(pipelineType) { 35 | if (pipelineType === "render") 36 | this._visibility = GPUShaderStage.FRAGMENT; 37 | else if (pipelineType === "compute_mixed") 38 | this._visibility = GPUShaderStage.FRAGMENT | GPUShaderStage.COMPUTE; 39 | else if (pipelineType === "compute") 40 | this._visibility = GPUShaderStage.COMPUTE; 41 | } 42 | createBindGroupLayoutEntry(bindingId) { 43 | let sampleType = "float"; 44 | if (this.sampledType === "i32") 45 | sampleType = "sint"; 46 | else if (this.sampledType === "u32") 47 | sampleType = "uint"; 48 | return { 49 | binding: bindingId, 50 | visibility: this._visibility, 51 | texture: { 52 | sampleType, 53 | viewDimension: "2d-array", 54 | multisampled: false 55 | }, 56 | }; 57 | } 58 | get isDepthTexture() { return true; } 59 | createDeclaration(varName, bindingId, groupId) { 60 | return "@binding(" + bindingId + ") @group(" + groupId + ") var " + varName + ":texture_depth_2d_array;\n"; 61 | } 62 | } 63 | -------------------------------------------------------------------------------- /dist/xGPU/pipelines/resources/textures/MultiSampleTexture.d.ts: -------------------------------------------------------------------------------- 1 | /// 2 | import { Texture } from "./Texture"; 3 | export type MultiSampleTextureDescriptor = { 4 | size: GPUExtent3D; 5 | format?: GPUTextureFormat; 6 | usage?: GPUTextureUsageFlags; 7 | sampleCount?: GPUSize32; 8 | alphaToCoverageEnabled?: boolean; 9 | mask?: number; 10 | resolveTarget?: GPUTextureView; 11 | }; 12 | export declare class MultiSampleTexture extends Texture { 13 | private _description; 14 | get description(): { 15 | count: number; 16 | mask: number; 17 | alphaToCoverageEnabled: boolean; 18 | }; 19 | constructor(descriptor: { 20 | size: GPUExtent3D; 21 | format?: GPUTextureFormat; 22 | usage?: GPUTextureUsageFlags; 23 | sampleCount?: GPUSize32; 24 | alphaToCoverageEnabled?: boolean; 25 | mask?: number; 26 | resolveTarget?: GPUTextureView; 27 | }); 28 | create(): void; 29 | get resolveTarget(): any; 30 | } 31 | -------------------------------------------------------------------------------- /dist/xGPU/pipelines/resources/textures/MultiSampleTexture.js: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2023 Thomas Le Coz. All rights reserved. 2 | // This code is governed by an MIT license that can be found in the LICENSE file. 3 | import { XGPU } from "../../../XGPU"; 4 | import { Texture } from "./Texture"; 5 | export class MultiSampleTexture extends Texture { 6 | _description; 7 | get description() { return this._description; } 8 | constructor(descriptor) { 9 | if (undefined === descriptor.format) 10 | descriptor.format = XGPU.getPreferredCanvasFormat(); 11 | if (undefined === descriptor.usage) 12 | descriptor.usage = GPUTextureUsage.RENDER_ATTACHMENT; 13 | if (undefined === descriptor.sampleCount) 14 | descriptor.sampleCount = 4; 15 | if (undefined === descriptor.alphaToCoverageEnabled) 16 | descriptor.alphaToCoverageEnabled = false; 17 | if (undefined === descriptor.mask) 18 | descriptor.mask = 0xFFFFFFFF; 19 | if (undefined === descriptor.resolveTarget) 20 | descriptor.resolveTarget = null; 21 | super(descriptor); 22 | this._description = { 23 | count: descriptor.sampleCount, 24 | mask: descriptor.mask, 25 | alphaToCoverageEnabled: descriptor.alphaToCoverageEnabled 26 | }; 27 | } 28 | create() { 29 | super.create(); 30 | } 31 | get resolveTarget() { return this.descriptor.resolveTarget; } 32 | } 33 | -------------------------------------------------------------------------------- /dist/xGPU/pipelines/resources/textures/RenderPassTexture.d.ts: -------------------------------------------------------------------------------- 1 | /// 2 | import { ImageTexture } from "../../../shader/resources/ImageTexture"; 3 | import { Pipeline } from "../../Pipeline"; 4 | import { RenderPipeline } from "../../RenderPipeline"; 5 | export type RenderPassTextureDescriptor = { 6 | size: GPUExtent3D; 7 | format?: GPUTextureFormat; 8 | usage?: GPUTextureUsageFlags; 9 | mipLevelCount?: GPUIntegerCoordinate; 10 | sampleCount?: GPUSize32; 11 | dimension?: GPUTextureDimension; 12 | viewFormats?: GPUTextureFormat[]; 13 | label?: string; 14 | }; 15 | export declare class RenderPassTexture extends ImageTexture { 16 | static RESOURCE_CHANGED: string; 17 | private ready; 18 | constructor(pipeline: RenderPipeline, descriptor?: { 19 | size: GPUExtent3D; 20 | format?: GPUTextureFormat; 21 | usage?: GPUTextureUsageFlags; 22 | mipLevelCount?: GPUIntegerCoordinate; 23 | sampleCount?: GPUSize32; 24 | dimension?: GPUTextureDimension; 25 | viewFormats?: GPUTextureFormat[]; 26 | label?: string; 27 | }); 28 | renderPipeline: RenderPipeline; 29 | protected _mustUseCopyTextureToTexture: boolean; 30 | get mustUseCopyTextureToTexture(): boolean; 31 | protected frameId: number; 32 | applyRenderPass(pipeline: Pipeline): void; 33 | resize(w: number, h: number): ImageTexture; 34 | createBindGroupEntry(bindingId: number): { 35 | binding: number; 36 | resource: GPUTextureView; 37 | }; 38 | get width(): number; 39 | get height(): number; 40 | get isRenderPass(): boolean; 41 | update(): void; 42 | get source(): ImageBitmap | HTMLCanvasElement | HTMLVideoElement | OffscreenCanvas | GPUTexture; 43 | set source(bmp: ImageBitmap | HTMLCanvasElement | HTMLVideoElement | OffscreenCanvas | GPUTexture); 44 | } 45 | -------------------------------------------------------------------------------- /dist/xGPU/pipelines/resources/textures/Texture.d.ts: -------------------------------------------------------------------------------- 1 | /// 2 | import { EventDispatcher } from "../../../EventDispatcher"; 3 | export type TextureDescriptor = { 4 | size: GPUExtent3D; 5 | format: GPUTextureFormat; 6 | usage?: GPUTextureUsageFlags; 7 | sampleCount?: GPUSize32; 8 | label?: string; 9 | }; 10 | export declare class Texture extends EventDispatcher { 11 | descriptor: TextureDescriptor; 12 | gpuResource: GPUTexture; 13 | protected _view: GPUTextureView; 14 | constructor(descriptor: { 15 | size: GPUExtent3D; 16 | format: GPUTextureFormat; 17 | usage?: GPUTextureUsageFlags; 18 | sampleCount?: GPUSize32; 19 | label?: string; 20 | }); 21 | get sampleCount(): number; 22 | get format(): any; 23 | get size(): GPUExtent3D; 24 | get usage(): number; 25 | get view(): GPUTextureView; 26 | destroy(): void; 27 | protected deviceId: number; 28 | time: number; 29 | create(): void; 30 | createGpuResource(): void; 31 | update(): void; 32 | private createView; 33 | resize(width: number, height: number): void; 34 | } 35 | -------------------------------------------------------------------------------- /dist/xGPU/pipelines/resources/textures/Texture.js: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2023 Thomas Le Coz. All rights reserved. 2 | // This code is governed by an MIT license that can be found in the LICENSE file. 3 | import { EventDispatcher } from "../../../EventDispatcher"; 4 | import { XGPU } from "../../../XGPU"; 5 | export class Texture extends EventDispatcher { 6 | descriptor; 7 | gpuResource = null; 8 | _view = null; 9 | constructor(descriptor) { 10 | super(); 11 | //console.log(descriptor.format + " ::: " + descriptor.usage) 12 | if (undefined === descriptor.usage) 13 | descriptor.usage = GPUTextureUsage.RENDER_ATTACHMENT; 14 | if (undefined === descriptor.sampleCount && descriptor.format !== "depth32float") 15 | descriptor.sampleCount = 1; 16 | if (undefined === descriptor.label) 17 | descriptor.label = "Texture"; 18 | this.descriptor = descriptor; 19 | } 20 | get sampleCount() { return this.descriptor.sampleCount; } 21 | get format() { return this.descriptor.format; } 22 | get size() { return this.descriptor.size; } 23 | get usage() { return this.descriptor.usage; } 24 | get view() { 25 | if (!this._view) 26 | this.create(); 27 | return this._view; 28 | } 29 | destroy() { 30 | if (this.gpuResource) { 31 | this.gpuResource.xgpuObject = null; 32 | this.gpuResource.destroy(); 33 | } 34 | this.gpuResource = null; 35 | this._view = null; 36 | } 37 | deviceId; 38 | time; 39 | create() { 40 | /*if (this.time && new Date().getTime() - this.time < 100 && XGPU.loseDeviceRecently) { 41 | return; 42 | }*/ 43 | this.time = new Date().getTime(); 44 | if (XGPU.loseDeviceRecently && this.deviceId === XGPU.deviceId) 45 | return; 46 | if (this.gpuResource) { 47 | this.gpuResource.xgpuObject = null; 48 | this.gpuResource.destroy(); 49 | } 50 | //console.warn("createTexture ", this.deviceId) 51 | this.deviceId = XGPU.deviceId; 52 | this.gpuResource = XGPU.device.createTexture(this.descriptor); 53 | this.gpuResource.xgpuObject = this; 54 | this.createView(); 55 | } 56 | createGpuResource() { 57 | this.create(); 58 | } 59 | update() { 60 | if (this.deviceId !== XGPU.deviceId) { 61 | this.create(); 62 | } 63 | } 64 | createView() { 65 | if (!this.gpuResource) 66 | this.create(); 67 | this._view = this.gpuResource.createView(); 68 | //(this._view as any).texture = this; 69 | } 70 | resize(width, height) { 71 | this.descriptor.size = [width, height]; 72 | this.create(); 73 | } 74 | } 75 | -------------------------------------------------------------------------------- /dist/xGPU/shader/Bindgroup.d.ts: -------------------------------------------------------------------------------- 1 | /// 2 | import { Pipeline } from "../pipelines/Pipeline"; 3 | import { IndexBuffer } from "../pipelines/resources/IndexBuffer"; 4 | import { Bindgroups } from "./Bindgroups"; 5 | import { ImageTexture } from "./resources/ImageTexture"; 6 | import { ImageTextureIO } from "./resources/ImageTextureIO"; 7 | import { IShaderResource } from "./resources/IShaderResource"; 8 | import { VertexBuffer } from "./resources/VertexBuffer"; 9 | import { VertexBufferIO } from "./resources/VertexBufferIO"; 10 | export declare class Bindgroup { 11 | bindgroupId: number; 12 | parent: Bindgroups; 13 | entries: any[]; 14 | elements: { 15 | name: string; 16 | resource: IShaderResource; 17 | }[]; 18 | mustRefreshBindgroup: boolean; 19 | applyDraw: boolean; 20 | protected _layout: GPUBindGroupLayout; 21 | protected _group: GPUBindGroup; 22 | name: string; 23 | protected _pingPongBindgroup: Bindgroup; 24 | vertexBufferIO: VertexBufferIO; 25 | textureIO: ImageTextureIO; 26 | resourcesIOs: (VertexBufferIO | ImageTextureIO)[]; 27 | constructor(descriptor?: any | any[]); 28 | add(name: string, resource: IShaderResource): IShaderResource; 29 | set(name: string, resource: IShaderResource): void; 30 | remove(name: string): void; 31 | getResourceName(resource: IShaderResource): string; 32 | get(name: string): IShaderResource; 33 | initFromObject(descriptor: any | any[]): IShaderResource[]; 34 | clearAfterDeviceLost(): void; 35 | protected deviceId: number; 36 | protected buildLayout(): void; 37 | private setupApplyCompleted; 38 | build(): GPUBindGroup; 39 | protected indexBuffer: IndexBuffer; 40 | protected vertexBuffers: VertexBuffer[]; 41 | protected vertexBufferReferenceByName: any; 42 | protected elementByName: any; 43 | private setupApply; 44 | setupDrawCompleted: boolean; 45 | setupDraw(force?: boolean): void; 46 | apply(renderPass: GPURenderPassEncoder | GPUComputePassEncoder): void; 47 | protected instances: any[]; 48 | protected instanceResourcesArray: any[]; 49 | get useInstances(): boolean; 50 | createInstance(instanceResources: any): void; 51 | protected _createInstance(resourcePerInstance: any): void; 52 | handleComputePipelineResourceIOs(): void; 53 | private swapElements; 54 | createPingPongBindgroup(resource1: IShaderResource[], resource2: IShaderResource[]): Bindgroup; 55 | protected renderPipelineimageIO: ImageTexture; 56 | protected renderPipelineBufferIO: VertexBuffer; 57 | handleRenderPipelineResourceIOs(): void; 58 | protected ioGroups: Bindgroup[]; 59 | protected io_index: number; 60 | debug: any; 61 | get pingPongBindgroup(): Bindgroup; 62 | get layout(): GPUBindGroupLayout; 63 | get group(): GPUBindGroup; 64 | update(pipeline: Pipeline): void; 65 | destroy(): void; 66 | } 67 | -------------------------------------------------------------------------------- /dist/xGPU/shader/Bindgroups.d.ts: -------------------------------------------------------------------------------- 1 | /// 2 | import { PrimitiveFloatUniform, PrimitiveIntUniform, PrimitiveUintUniform } from "../PrimitiveType"; 3 | import { Bindgroup } from "./Bindgroup"; 4 | import { IShaderResource } from "./resources/IShaderResource"; 5 | import { VertexBuffer } from "./resources/VertexBuffer"; 6 | import { Pipeline } from "../pipelines/Pipeline"; 7 | import { DrawConfig } from "../pipelines/resources/DrawConfig"; 8 | export declare class Bindgroups { 9 | pipeline: Pipeline; 10 | parent: Bindgroups; 11 | groups: Bindgroup[]; 12 | private _name; 13 | constructor(pipeline: Pipeline, name: string); 14 | get name(): string; 15 | clearAfterDeviceLost(): void; 16 | build(autoLayout?: boolean): { 17 | description: any; 18 | bindgroups: GPUBindGroup[]; 19 | buffers: VertexBuffer[]; 20 | nbVertex: number; 21 | }; 22 | getBindgroupByResource(resource: IShaderResource): Bindgroup; 23 | apply(passEncoder: GPURenderPassEncoder | GPUComputePassEncoder): void; 24 | update(): void; 25 | protected temp: { 26 | result: string; 27 | variables: string; 28 | }; 29 | getVertexShaderDeclaration(fromFragmentShader?: boolean): { 30 | result: string; 31 | variables: string; 32 | }; 33 | getFragmentShaderDeclaration(): { 34 | result: string; 35 | variables: string; 36 | }; 37 | getComputeShaderDeclaration(): { 38 | result: string; 39 | variables: string; 40 | }; 41 | protected createVertexBufferLayout(): { 42 | vertexLayouts: Iterable; 43 | buffers: VertexBuffer[]; 44 | nbVertex: number; 45 | }; 46 | handleRenderPipelineResourceIOs(): void; 47 | handleComputePipelineResourceIOs(): void; 48 | protected _resources: any; 49 | get resources(): any; 50 | add(bindgroup: Bindgroup | Bindgroups): (Bindgroup | Bindgroups); 51 | copy(options?: { 52 | oldGroups: Bindgroup[]; 53 | replacedGroup: Bindgroup[]; 54 | }): Bindgroups; 55 | propertyNameIsUsed(propertyName: string): boolean; 56 | get(propertyName: string): IShaderResource; 57 | getGroupByPropertyName(name: string): Bindgroup; 58 | getGroupByName(name: string): Bindgroup; 59 | getNameByResource(resource: IShaderResource | PrimitiveFloatUniform | PrimitiveIntUniform | PrimitiveUintUniform): string; 60 | setupDraw(force?: boolean): void; 61 | get drawConfig(): DrawConfig; 62 | get current(): Bindgroup; 63 | destroy(): void; 64 | } 65 | -------------------------------------------------------------------------------- /dist/xGPU/shader/ComputeShader.d.ts: -------------------------------------------------------------------------------- 1 | import { ComputePipeline } from "../pipelines/ComputePipeline"; 2 | import { ShaderStage } from "./shaderParts/ShaderStage"; 3 | import { ShaderStruct } from "./shaderParts/ShaderStruct"; 4 | export declare class ComputeShader extends ShaderStage { 5 | constructor(); 6 | build(shaderPipeline: ComputePipeline, inputs: ShaderStruct): { 7 | code: string; 8 | output: ShaderStruct; 9 | }; 10 | static removeStructDefinitionAndReplaceStructDeclarationName(shaderCode: string, structName: string, newStructName: string): string; 11 | } 12 | -------------------------------------------------------------------------------- /dist/xGPU/shader/ComputeShader.js: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2023 Thomas Le Coz. All rights reserved. 2 | // This code is governed by an MIT license that can be found in the LICENSE file. 3 | import { XGPU } from "../XGPU"; 4 | import { ShaderStage } from "./shaderParts/ShaderStage"; 5 | export class ComputeShader extends ShaderStage { 6 | constructor() { 7 | super("compute"); 8 | } 9 | build(shaderPipeline, inputs) { 10 | if (this._shaderInfos) 11 | return this._shaderInfos; 12 | let result = ""; 13 | const obj = shaderPipeline.bindGroups.getComputeShaderDeclaration(); 14 | result += obj.result + "\n\n"; 15 | //------ 16 | const w = shaderPipeline.workgroups; 17 | //this.unwrapVariableInMainFunction(obj.variables)//handleVariables(); 18 | let constants = this.unwrapVariableInWGSL(obj.variables, this.constants.value); 19 | result += constants + "\n\n"; 20 | let mainFunc = this.unwrapVariableInWGSL(obj.variables, this.main.value); 21 | result += "@compute @workgroup_size(" + w[0] + "," + w[1] + "," + w[2] + ")\n"; 22 | result += "fn main(" + inputs.getFunctionParams() + ") {\n"; 23 | //result += obj.variables + "\n"; 24 | //result += this.main.value; 25 | result += mainFunc; 26 | result += "}\n"; 27 | this._shaderInfos = { code: result, output: null }; 28 | if (XGPU.showComputeShader) { 29 | setTimeout(() => { 30 | console.log("------------- COMPUTE SHADER --------------"); 31 | console.log(this.formatWGSLCode(this._shaderInfos.code)); 32 | //console.log(formated) 33 | console.log("-------------------------------------------"); 34 | }, 100); 35 | } 36 | return this._shaderInfos; 37 | } 38 | static removeStructDefinitionAndReplaceStructDeclarationName(shaderCode, structName, newStructName) { 39 | // Expression régulière pour capturer la définition complète de la structure `structName` 40 | const structRegex = new RegExp(`struct\\s+${structName}\\s*\\{[^}]*\\}`, 'g'); 41 | // Supprimer la définition de `structName` 42 | shaderCode = shaderCode.replace(structRegex, ''); 43 | // Remplacer toutes les occurrences de `structName` par `newStructName` 44 | const nameRegex = new RegExp(`\\b${structName}\\b`, 'g'); 45 | shaderCode = shaderCode.replace(nameRegex, newStructName); 46 | return shaderCode; 47 | } 48 | } 49 | -------------------------------------------------------------------------------- /dist/xGPU/shader/FragmentShader.d.ts: -------------------------------------------------------------------------------- 1 | import { ShaderStage } from "./shaderParts/ShaderStage"; 2 | import { ShaderStruct } from "./shaderParts/ShaderStruct"; 3 | export declare class FragmentShader extends ShaderStage { 4 | constructor(); 5 | build(shaderPipeline: any, inputs: ShaderStruct): { 6 | code: string; 7 | output: ShaderStruct; 8 | }; 9 | } 10 | -------------------------------------------------------------------------------- /dist/xGPU/shader/FragmentShader.js: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2023 Thomas Le Coz. All rights reserved. 2 | // This code is governed by an MIT license that can be found in the LICENSE file. 3 | import { BuiltIns } from "../BuiltIns"; 4 | import { XGPU } from "../XGPU"; 5 | import { ShaderStage } from "./shaderParts/ShaderStage"; 6 | import { ShaderStruct } from "./shaderParts/ShaderStruct"; 7 | export class FragmentShader extends ShaderStage { 8 | constructor() { 9 | super("fragment"); 10 | } 11 | build(shaderPipeline, inputs) { 12 | if (this._shaderInfos) 13 | return this._shaderInfos; 14 | let result = ""; 15 | const obj = shaderPipeline.bindGroups.getVertexShaderDeclaration(true); 16 | result += obj.result; 17 | //console.log("-------- FRAGMENT -----------"); 18 | //console.log(result) 19 | for (let i = 0; i < this.inputs.length; i++) { 20 | inputs.addProperty(this.inputs[i]); 21 | } 22 | if (this.outputs.length === 0) { 23 | this.outputs[0] = { name: "color", ...BuiltIns.fragmentOutputs.color }; 24 | } 25 | const output = new ShaderStruct("Output", this.outputs); 26 | result += output.struct + "\n"; 27 | //------ 28 | //const mainFunc = this.unwrapVariableInMainFunction(obj.variables)//handleVariables(); 29 | let constants = this.unwrapVariableInWGSL(obj.variables, this.constants.value); 30 | result += constants + "\n\n"; 31 | let mainFunc = this.unwrapVariableInWGSL(obj.variables, this.main.value); 32 | result += "@fragment\n"; 33 | result += "fn main(" + inputs.getFunctionParams() + ") -> " + output.name + "{\n"; 34 | //result += obj.variables + "\n"; 35 | result += " var output:Output;\n"; 36 | //result += this.main.value; 37 | result += mainFunc; 38 | result += " return output;\n"; 39 | result += "}\n"; 40 | result = this.formatWGSLCode(result); 41 | if (XGPU.showFragmentShader) { 42 | console.log("------------- FRAGMENT SHADER --------------"); 43 | console.log(result); 44 | console.log("--------------------------------------------"); 45 | } 46 | this._shaderInfos = { code: result, output: output }; 47 | return this._shaderInfos; 48 | } 49 | } 50 | -------------------------------------------------------------------------------- /dist/xGPU/shader/ShaderType.d.ts: -------------------------------------------------------------------------------- 1 | export declare class ShaderType { 2 | static Float: { 3 | type: string; 4 | }; 5 | static Vec2: { 6 | type: string; 7 | }; 8 | static Vec3: { 9 | type: string; 10 | }; 11 | static Vec4: { 12 | type: string; 13 | }; 14 | static Int: { 15 | type: string; 16 | }; 17 | static IVec2: { 18 | type: string; 19 | }; 20 | static IVec3: { 21 | type: string; 22 | }; 23 | static IVec4: { 24 | type: string; 25 | }; 26 | static Uint: { 27 | type: string; 28 | }; 29 | static UVec2: { 30 | type: string; 31 | }; 32 | static UVec3: { 33 | type: string; 34 | }; 35 | static UVec4: { 36 | type: string; 37 | }; 38 | } 39 | -------------------------------------------------------------------------------- /dist/xGPU/shader/ShaderType.js: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2023 Thomas Le Coz. All rights reserved. 2 | // This code is governed by an MIT license that can be found in the LICENSE file. 3 | export class ShaderType { 4 | static Float = { type: "f32" }; 5 | static Vec2 = { type: "vec2" }; 6 | static Vec3 = { type: "vec3" }; 7 | static Vec4 = { type: "vec4" }; 8 | static Int = { type: "i32" }; 9 | static IVec2 = { type: "vec2" }; 10 | static IVec3 = { type: "vec3" }; 11 | static IVec4 = { type: "vec4" }; 12 | static Uint = { type: "u32" }; 13 | static UVec2 = { type: "vec2" }; 14 | static UVec3 = { type: "vec3" }; 15 | static UVec4 = { type: "vec4" }; 16 | } 17 | -------------------------------------------------------------------------------- /dist/xGPU/shader/VertexShader.d.ts: -------------------------------------------------------------------------------- 1 | import { RenderPipeline } from "../pipelines/RenderPipeline"; 2 | import { ShaderStage } from "./shaderParts/ShaderStage"; 3 | import { ShaderStruct } from "./shaderParts/ShaderStruct"; 4 | export declare class VertexShader extends ShaderStage { 5 | constructor(); 6 | build(pipeline: RenderPipeline, input: ShaderStruct): { 7 | code: string; 8 | output: ShaderStruct; 9 | }; 10 | } 11 | -------------------------------------------------------------------------------- /dist/xGPU/shader/VertexShader.js: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2023 Thomas Le Coz. All rights reserved. 2 | // This code is governed by an MIT license that can be found in the LICENSE file. 3 | import { BuiltIns } from "../BuiltIns"; 4 | import { XGPU } from "../XGPU"; 5 | import { ShaderStage } from "./shaderParts/ShaderStage"; 6 | import { ShaderStruct } from "./shaderParts/ShaderStruct"; 7 | export class VertexShader extends ShaderStage { 8 | //public keepRendererAspectRatio: boolean = true; 9 | constructor() { 10 | super("vertex"); 11 | } 12 | build(pipeline, input) { 13 | //this.main.text = this.extractDebugInfo(this.main.text); 14 | let result = ""; 15 | //if (this.keepRendererAspectRatio) result += "const xgpuRendererAspectRatio = " + (pipeline.renderer.width / pipeline.renderer.height).toFixed(4) + ";\n\n"; 16 | const obj = pipeline.bindGroups.getVertexShaderDeclaration(); 17 | result += obj.result; 18 | //----- 19 | //if the renderPipeline is "fed" by a computePipeline, the shaderStruct "input" 20 | //contains the output vertexBuffer from the computePipeline 21 | result += input.getComputeVariableDeclaration(); 22 | //----- 23 | let bool = false; 24 | for (let i = 0; i < this.outputs.length; i++) { 25 | if (this.outputs[i].builtin === BuiltIns.vertexOutputs.position.builtin) { 26 | bool = true; 27 | } 28 | } 29 | if (!bool) { 30 | this.outputs.unshift({ name: "position", ...BuiltIns.vertexOutputs.position }); 31 | } 32 | let output = new ShaderStruct("Output", [...this.outputs]); 33 | result += output.struct + "\n"; 34 | //let mainFunc = this.unwrapVariableInMainFunction(obj.variables)//handleVariables(); 35 | let constants = this.unwrapVariableInWGSL(obj.variables, this.constants.value); 36 | result += constants + "\n\n"; 37 | let mainFunc = this.unwrapVariableInWGSL(obj.variables, this.main.value); 38 | //------ 39 | //console.log("VertexShader.variables = ", obj.variables) 40 | result += "@vertex\n"; 41 | result += "fn main(" + input.getFunctionParams() + ") -> " + output.name + "{\n"; 42 | result += " var output:Output;\n"; 43 | result += mainFunc; 44 | result += " return output;\n"; 45 | result += "}\n"; 46 | result = this.formatWGSLCode(result); 47 | if (XGPU.showVertexShader) { 48 | console.log("------------- VERTEX SHADER --------------"); 49 | console.log(result); 50 | console.log("------------------------------------------"); 51 | } 52 | this._shaderInfos = { code: result, output: output }; 53 | return this._shaderInfos; 54 | } 55 | } 56 | -------------------------------------------------------------------------------- /dist/xGPU/shader/resources/CubeMapTexture.d.ts: -------------------------------------------------------------------------------- 1 | /// 2 | import { ImageTextureArray } from "./ImageTextureArray"; 3 | import { IShaderResource } from "./IShaderResource"; 4 | export type CubeMapTextureDescriptor = { 5 | source?: (ImageBitmap | HTMLVideoElement | HTMLCanvasElement | OffscreenCanvas)[]; 6 | size: GPUExtent3D; 7 | usage?: GPUTextureUsageFlags; 8 | dimension: string; 9 | defaultViewDescriptor?: GPUTextureViewDescriptor; 10 | sampledType?: "f32" | "i32" | "u32"; 11 | }; 12 | export declare class CubeMapTexture extends ImageTextureArray implements IShaderResource { 13 | descriptor: any; 14 | constructor(descriptor: { 15 | source?: (ImageBitmap | HTMLVideoElement | HTMLCanvasElement | OffscreenCanvas | GPUTexture)[]; 16 | size: GPUExtent3D; 17 | usage?: GPUTextureUsageFlags; 18 | defaultViewDescriptor?: GPUTextureViewDescriptor; 19 | dimension?: string; 20 | sampledType?: "f32" | "i32" | "u32"; 21 | }); 22 | clone(): CubeMapTexture; 23 | set right(bmp: ImageBitmap | HTMLVideoElement | HTMLCanvasElement | OffscreenCanvas | GPUTexture); 24 | set left(bmp: ImageBitmap | HTMLVideoElement | HTMLCanvasElement | OffscreenCanvas | GPUTexture); 25 | set bottom(bmp: ImageBitmap | HTMLVideoElement | HTMLCanvasElement | OffscreenCanvas | GPUTexture); 26 | set top(bmp: ImageBitmap | HTMLVideoElement | HTMLCanvasElement | OffscreenCanvas | GPUTexture); 27 | set back(bmp: ImageBitmap | HTMLVideoElement | HTMLCanvasElement | OffscreenCanvas | GPUTexture); 28 | set front(bmp: ImageBitmap | HTMLVideoElement | HTMLCanvasElement | OffscreenCanvas | GPUTexture); 29 | set sides(images: (ImageBitmap | HTMLVideoElement | HTMLCanvasElement | OffscreenCanvas | GPUTexture)[]); 30 | get sides(): (ImageBitmap | HTMLVideoElement | HTMLCanvasElement | OffscreenCanvas | GPUTexture)[]; 31 | createGpuResource(): void; 32 | createDeclaration(varName: string, bindingId: number, groupId?: number): string; 33 | createBindGroupLayoutEntry(bindingId: number): { 34 | binding: number; 35 | visibility: number; 36 | texture: GPUTextureBindingLayout; 37 | }; 38 | createBindGroupEntry(bindingId: number): { 39 | binding: number; 40 | resource: GPUTextureView; 41 | }; 42 | setPipelineType(pipelineType: "compute" | "render" | "compute_mixed"): void; 43 | } 44 | -------------------------------------------------------------------------------- /dist/xGPU/shader/resources/CubeMapTexture.js: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2023 Thomas Le Coz. All rights reserved. 2 | // This code is governed by an MIT license that can be found in the LICENSE file. 3 | import { XGPU } from "../../XGPU"; 4 | import { ImageTextureArray } from "./ImageTextureArray"; 5 | export class CubeMapTexture extends ImageTextureArray { 6 | constructor(descriptor) { 7 | descriptor = { ...descriptor }; 8 | if (!descriptor.dimension) 9 | descriptor.dimension = "2d"; 10 | if (undefined === descriptor.usage) 11 | descriptor.usage = GPUTextureUsage.TEXTURE_BINDING | GPUTextureUsage.COPY_DST | GPUTextureUsage.RENDER_ATTACHMENT; 12 | super(descriptor); 13 | if (descriptor.source) 14 | this.sides = descriptor.source; 15 | } 16 | clone() { 17 | if (!this.descriptor.source) 18 | this.descriptor.source = this._bitmaps; 19 | return new CubeMapTexture(this.descriptor); 20 | } 21 | set right(bmp) { 22 | this._bitmaps[0] = bmp; 23 | this.mustBeTransfered = true; 24 | } 25 | set left(bmp) { 26 | if (!this.descriptor.source) 27 | this.descriptor.source = {}; 28 | this._bitmaps[1] = bmp; 29 | this.mustBeTransfered = true; 30 | } 31 | set bottom(bmp) { 32 | if (!this.descriptor.source) 33 | this.descriptor.source = {}; 34 | this._bitmaps[2] = bmp; 35 | this.mustBeTransfered = true; 36 | } 37 | set top(bmp) { 38 | if (!this.descriptor.source) 39 | this.descriptor.source = {}; 40 | this._bitmaps[3] = bmp; 41 | this.mustBeTransfered = true; 42 | } 43 | set back(bmp) { 44 | if (!this.descriptor.source) 45 | this.descriptor.source = {}; 46 | this._bitmaps[4] = bmp; 47 | this.mustBeTransfered = true; 48 | } 49 | set front(bmp) { 50 | if (!this.descriptor.source) 51 | this.descriptor.source = {}; 52 | this._bitmaps[5] = bmp; 53 | this.mustBeTransfered = true; 54 | } 55 | set sides(images) { 56 | for (let i = 0; i < 6; i++) 57 | this._bitmaps[i] = images[i]; 58 | this.mustBeTransfered = true; 59 | this.update(); 60 | } 61 | get sides() { return this._bitmaps; } 62 | createGpuResource() { 63 | if (this.gpuResource) 64 | this.gpuResource.destroy(); 65 | this.gpuResource = XGPU.device.createTexture(this.descriptor); 66 | this._view = this.gpuResource.createView({ dimension: 'cube' }); 67 | for (let i = 0; i < this.mustUpdate.length; i++) 68 | this.mustUpdate[i] = true; 69 | this.mustBeTransfered = true; 70 | } 71 | //----- 72 | createDeclaration(varName, bindingId, groupId = 0) { 73 | return "@binding(" + bindingId + ") @group(" + groupId + ") var " + varName + ":texture_cube<" + this.sampledType + ">;\n"; 74 | } 75 | createBindGroupLayoutEntry(bindingId) { 76 | let sampleType = "float"; 77 | if (this.sampledType === "i32") 78 | sampleType = "sint"; 79 | else if (this.sampledType === "u32") 80 | sampleType = "uint"; 81 | return { 82 | binding: bindingId, 83 | visibility: GPUShaderStage.FRAGMENT, 84 | texture: { 85 | sampleType, 86 | viewDimension: "cube", 87 | multisampled: false 88 | }, 89 | }; 90 | } 91 | createBindGroupEntry(bindingId) { 92 | if (!this.gpuResource) 93 | this.createGpuResource(); 94 | return { 95 | binding: bindingId, 96 | resource: this._view, 97 | }; 98 | } 99 | setPipelineType(pipelineType) { 100 | if (pipelineType) { } 101 | //use to handle particular cases in descriptor relative to the nature of pipeline 102 | } 103 | } 104 | -------------------------------------------------------------------------------- /dist/xGPU/shader/resources/CubeMapTextureArray.d.ts: -------------------------------------------------------------------------------- 1 | /// 2 | import { ImageTextureArray } from "./ImageTextureArray"; 3 | import { IShaderResource } from "./IShaderResource"; 4 | export type ImageTextureArrayDescriptor = { 5 | source?: (ImageBitmap | HTMLVideoElement | HTMLCanvasElement | OffscreenCanvas)[]; 6 | size: GPUExtent3D; 7 | usage?: GPUTextureUsageFlags; 8 | dimension: string; 9 | defaultViewDescriptor?: GPUTextureViewDescriptor; 10 | sampledType?: "f32" | "i32" | "u32"; 11 | }; 12 | export declare class CubeMapTextureArray extends ImageTextureArray implements IShaderResource { 13 | descriptor: any; 14 | constructor(descriptor: ImageTextureArrayDescriptor); 15 | clone(): CubeMapTextureArray; 16 | set bitmaps(images: (ImageBitmap | HTMLVideoElement | HTMLCanvasElement | OffscreenCanvas | GPUTexture)[]); 17 | get bitmaps(): (ImageBitmap | HTMLVideoElement | HTMLCanvasElement | OffscreenCanvas | GPUTexture)[]; 18 | setCubeSideById(cubeid: number, sideId: number, image: (ImageBitmap | HTMLVideoElement | HTMLCanvasElement | OffscreenCanvas | GPUTexture)): void; 19 | createGpuResource(): void; 20 | createDeclaration(varName: string, bindingId: number, groupId?: number): string; 21 | createBindGroupLayoutEntry(bindingId: number): { 22 | binding: number; 23 | visibility: number; 24 | texture: GPUTextureBindingLayout; 25 | }; 26 | createBindGroupEntry(bindingId: number): { 27 | binding: number; 28 | resource: GPUTextureView; 29 | }; 30 | setPipelineType(pipelineType: "compute" | "render" | "compute_mixed"): void; 31 | } 32 | -------------------------------------------------------------------------------- /dist/xGPU/shader/resources/CubeMapTextureArray.js: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2023 Thomas Le Coz. All rights reserved. 2 | // This code is governed by an MIT license that can be found in the LICENSE file. 3 | import { XGPU } from "../../XGPU"; 4 | import { ImageTextureArray } from "./ImageTextureArray"; 5 | export class CubeMapTextureArray extends ImageTextureArray { 6 | constructor(descriptor) { 7 | descriptor = { ...descriptor }; 8 | if (descriptor.source) { 9 | if (descriptor.source.length === 0 || descriptor.source.length % 6 !== 0) { 10 | throw new Error("CubeMapTextureArray error : descriptor.source must contains an array of (ImageBitmap | HTMLVideoElement | HTMLCanvasElement | OffscreenCanvas) with a length greater than 0 and multiple of 6."); 11 | } 12 | } 13 | if (!descriptor.dimension) 14 | descriptor.dimension = "2d"; 15 | if (undefined === descriptor.usage) 16 | descriptor.usage = GPUTextureUsage.TEXTURE_BINDING | GPUTextureUsage.COPY_DST | GPUTextureUsage.RENDER_ATTACHMENT; 17 | super(descriptor); 18 | if (descriptor.source) 19 | this.bitmaps = descriptor.source; 20 | } 21 | clone() { 22 | if (!this.descriptor.source) 23 | this.descriptor.source = this._bitmaps; 24 | return new CubeMapTextureArray(this.descriptor); 25 | } 26 | set bitmaps(images) { 27 | if (images.length === 0 || images.length % 6 !== 0) { 28 | throw new Error("CubeMapTextureArray error : descriptor.source must contains an array of (ImageBitmap | HTMLVideoElement | HTMLCanvasElement | OffscreenCanvas) with a length greater than 0 and multiple of 6."); 29 | } 30 | for (let i = 0; i < images.length; i++) { 31 | this._bitmaps[i] = images[i]; 32 | this.mustUpdate[i] = true; 33 | } 34 | this.mustBeTransfered = true; 35 | this.update(); 36 | } 37 | get bitmaps() { return this._bitmaps; } 38 | setCubeSideById(cubeid, sideId, image) { 39 | if (this._bitmaps[cubeid * 6 + sideId] instanceof ImageBitmap) 40 | this._bitmaps[cubeid * 6 + sideId].close(); 41 | this._bitmaps[cubeid * 6 + sideId] = image; 42 | this.mustUpdate[cubeid * 6 + sideId] = true; 43 | this.mustBeTransfered = true; 44 | } 45 | createGpuResource() { 46 | if (this.gpuResource) 47 | this.gpuResource.destroy(); 48 | //console.log("cubemap createtexture ", this.descriptor) 49 | this.gpuResource = XGPU.device.createTexture(this.descriptor); 50 | this._view = this.gpuResource.createView({ dimension: 'cube-array', arrayLayerCount: this._bitmaps.length }); 51 | } 52 | //----- 53 | createDeclaration(varName, bindingId, groupId = 0) { 54 | return "@binding(" + bindingId + ") @group(" + groupId + ") var " + varName + ":texture_cube_array<" + this.sampledType + ">;\n"; 55 | } 56 | createBindGroupLayoutEntry(bindingId) { 57 | let sampleType = "float"; 58 | if (this.sampledType === "i32") 59 | sampleType = "sint"; 60 | else if (this.sampledType === "u32") 61 | sampleType = "uint"; 62 | return { 63 | binding: bindingId, 64 | visibility: GPUShaderStage.FRAGMENT, 65 | texture: { 66 | sampleType, 67 | viewDimension: "cube-array", 68 | multisampled: false 69 | }, 70 | }; 71 | } 72 | createBindGroupEntry(bindingId) { 73 | if (!this.gpuResource) 74 | this.createGpuResource(); 75 | return { 76 | binding: bindingId, 77 | resource: this._view, 78 | }; 79 | } 80 | setPipelineType(pipelineType) { 81 | if (pipelineType) { } 82 | //use to handle particular cases in descriptor relative to the nature of pipeline 83 | } 84 | } 85 | -------------------------------------------------------------------------------- /dist/xGPU/shader/resources/IShaderResource.d.ts: -------------------------------------------------------------------------------- 1 | import { Pipeline } from "../../pipelines/Pipeline"; 2 | export interface IShaderResource { 3 | mustBeTransfered: boolean; 4 | gpuResource: any; 5 | descriptor: any; 6 | setPipelineType(pipelineType: "compute" | "render" | "compute_mixed"): any; 7 | createDeclaration(varName: string, bindingId: number, groupId: number): string; 8 | createBindGroupLayoutEntry(bindingId: number): any; 9 | createBindGroupEntry(bindingId: number): any; 10 | createGpuResource(): any; 11 | destroyGpuResource(): any; 12 | update(pipeline?: Pipeline): any; 13 | clone(): IShaderResource; 14 | } 15 | -------------------------------------------------------------------------------- /dist/xGPU/shader/resources/IShaderResource.js: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2023 Thomas Le Coz. All rights reserved. 2 | // This code is governed by an MIT license that can be found in the LICENSE file. 3 | export {}; 4 | -------------------------------------------------------------------------------- /dist/xGPU/shader/resources/ImageTexture.d.ts: -------------------------------------------------------------------------------- 1 | /// 2 | import { EventDispatcher } from "../../EventDispatcher"; 3 | import { Pipeline } from "../../pipelines/Pipeline"; 4 | import { RenderPassTexture } from "../../pipelines/resources/textures/RenderPassTexture"; 5 | import { IShaderResource } from "./IShaderResource"; 6 | import { ImageTextureIO } from "./ImageTextureIO"; 7 | export type ImageTextureDescriptor = { 8 | source?: ImageBitmap | HTMLCanvasElement | HTMLVideoElement | OffscreenCanvas | GPUTexture | RenderPassTexture; 9 | size?: GPUExtent3D; 10 | usage?: GPUTextureUsageFlags; 11 | format?: GPUTextureFormat; 12 | defaultViewDescriptor?: GPUTextureViewDescriptor; 13 | sampledType?: "f32" | "i32" | "u32"; 14 | label?: string; 15 | }; 16 | export declare class ImageTexture extends EventDispatcher implements IShaderResource { 17 | resourceIO: ImageTextureIO; 18 | io: number; 19 | mustBeTransfered: boolean; 20 | descriptor: ImageTextureDescriptor; 21 | gpuResource: GPUTexture; 22 | protected _view: GPUTextureView; 23 | protected viewDescriptor: GPUTextureViewDescriptor; 24 | protected useOutsideTexture: boolean; 25 | protected renderPassTexture: RenderPassTexture; 26 | constructor(descriptor: { 27 | source?: ImageBitmap | HTMLCanvasElement | HTMLVideoElement | OffscreenCanvas | GPUTexture | RenderPassTexture; 28 | size?: GPUExtent3D; 29 | usage?: GPUTextureUsageFlags; 30 | format?: GPUTextureFormat; 31 | defaultViewDescriptor?: GPUTextureViewDescriptor; 32 | sampledType?: "f32" | "i32" | "u32"; 33 | label?: string; 34 | }); 35 | private initFromTexture; 36 | clone(): ImageTexture; 37 | get sampledType(): "f32" | "i32" | "u32"; 38 | set sampledType(type: "f32" | "i32" | "u32"); 39 | get isRenderPass(): boolean; 40 | protected gpuTextureIOs: GPUTexture[]; 41 | protected gpuTextureIO_index: number; 42 | initTextureIO(textures: GPUTexture[]): void; 43 | get texture(): GPUTexture; 44 | getCurrentTexture(): GPUTexture; 45 | createView(viewDescriptor?: GPUTextureViewDescriptor): GPUTextureView; 46 | resize(w: number, h: number): ImageTexture; 47 | get view(): GPUTextureView; 48 | get source(): ImageBitmap | HTMLCanvasElement | HTMLVideoElement | OffscreenCanvas | GPUTexture | RenderPassTexture; 49 | set source(bmp: ImageBitmap | HTMLCanvasElement | HTMLVideoElement | OffscreenCanvas | GPUTexture | RenderPassTexture); 50 | update(pipeline: Pipeline): void; 51 | deviceId: number; 52 | createGpuResource(): void; 53 | time: number; 54 | destroyGpuResource(): void; 55 | createDeclaration(varName: string, bindingId: number, groupId?: number): string; 56 | protected _textureType: { 57 | texture: any; 58 | } | { 59 | storageTexture: any; 60 | }; 61 | get textureType(): any; 62 | set textureType(o: any); 63 | createBindGroupLayoutEntry(bindingId: number): { 64 | binding: number; 65 | visibility: number; 66 | storageTexture?: GPUStorageTextureBindingLayout; 67 | texture?: GPUTextureBindingLayout; 68 | }; 69 | createBindGroupEntry(bindingId: number): { 70 | binding: number; 71 | resource: GPUTextureView; 72 | }; 73 | setPipelineType(pipelineType: "compute" | "render" | "compute_mixed"): void; 74 | } 75 | -------------------------------------------------------------------------------- /dist/xGPU/shader/resources/ImageTextureArray.d.ts: -------------------------------------------------------------------------------- 1 | /// 2 | import { ImageTexture } from "./ImageTexture"; 3 | import { IShaderResource } from "./IShaderResource"; 4 | export type ImageTextureArrayDescriptor = { 5 | source?: (ImageBitmap | HTMLVideoElement | HTMLCanvasElement | OffscreenCanvas | GPUTexture)[]; 6 | size: GPUExtent3D; 7 | usage?: GPUTextureUsageFlags; 8 | dimension: string; 9 | defaultViewDescriptor?: GPUTextureViewDescriptor; 10 | sampledType?: "f32" | "i32" | "u32"; 11 | }; 12 | export declare class ImageTextureArray extends ImageTexture implements IShaderResource { 13 | descriptor: any; 14 | protected _bitmaps: (ImageBitmap | HTMLVideoElement | HTMLCanvasElement | OffscreenCanvas | GPUTexture)[]; 15 | protected mustUpdate: boolean[]; 16 | constructor(descriptor: { 17 | source?: (ImageBitmap | HTMLVideoElement | HTMLCanvasElement | OffscreenCanvas)[]; 18 | size: GPUExtent3D; 19 | usage?: GPUTextureUsageFlags; 20 | defaultViewDescriptor?: GPUTextureViewDescriptor; 21 | dimension?: string; 22 | sampledType?: "f32" | "i32" | "u32"; 23 | }); 24 | clone(): ImageTextureArray; 25 | set bitmaps(images: (ImageBitmap | HTMLVideoElement | HTMLCanvasElement | OffscreenCanvas | GPUTexture)[]); 26 | get bitmaps(): (ImageBitmap | HTMLVideoElement | HTMLCanvasElement | OffscreenCanvas | GPUTexture)[]; 27 | setImageById(image: (ImageBitmap | HTMLVideoElement | HTMLCanvasElement | OffscreenCanvas | GPUTexture), id: number): void; 28 | createGpuResource(): void; 29 | updateInnerGpuTextures(commandEncoder: GPUCommandEncoder): void; 30 | update(): void; 31 | createDeclaration(varName: string, bindingId: number, groupId?: number): string; 32 | createBindGroupLayoutEntry(bindingId: number): { 33 | binding: number; 34 | visibility: number; 35 | texture: GPUTextureBindingLayout; 36 | }; 37 | createBindGroupEntry(bindingId: number): { 38 | binding: number; 39 | resource: GPUTextureView; 40 | }; 41 | } 42 | -------------------------------------------------------------------------------- /dist/xGPU/shader/resources/ImageTextureArray.js: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2023 Thomas Le Coz. All rights reserved. 2 | // This code is governed by an MIT license that can be found in the LICENSE file. 3 | import { XGPU } from "../../XGPU"; 4 | import { ImageTexture } from "./ImageTexture"; 5 | export class ImageTextureArray extends ImageTexture { 6 | _bitmaps = []; 7 | mustUpdate = []; 8 | constructor(descriptor) { 9 | descriptor = { ...descriptor }; 10 | if (descriptor.source && !descriptor.size) { 11 | descriptor.size = [descriptor.source[0].width, descriptor.source[0].height, descriptor.source.length]; 12 | } 13 | if (!descriptor.dimension) 14 | descriptor.dimension = "2d"; 15 | if (undefined === descriptor.usage) 16 | descriptor.usage = GPUTextureUsage.TEXTURE_BINDING | GPUTextureUsage.COPY_DST | GPUTextureUsage.RENDER_ATTACHMENT; 17 | super(descriptor); 18 | if (descriptor.source) 19 | this.bitmaps = descriptor.source; 20 | } 21 | clone() { 22 | if (!this.descriptor.source) 23 | this.descriptor.source = this._bitmaps; 24 | return new ImageTextureArray(this.descriptor); 25 | } 26 | set bitmaps(images) { 27 | for (let i = 0; i < images.length; i++) { 28 | this._bitmaps[i] = images[i]; 29 | this.mustUpdate[i] = true; 30 | } 31 | this.mustBeTransfered = true; 32 | this.update(); 33 | } 34 | get bitmaps() { return this._bitmaps; } 35 | setImageById(image, id) { 36 | this._bitmaps[id] = image; 37 | this.mustUpdate[id] = true; 38 | this.mustBeTransfered = true; 39 | } 40 | createGpuResource() { 41 | if (this.gpuResource) 42 | this.gpuResource.destroy(); 43 | //console.log("cubemap createtexture ", this.descriptor) 44 | this.gpuResource = XGPU.device.createTexture(this.descriptor); 45 | this._view = this.gpuResource.createView({ dimension: '2d-array', arrayLayerCount: this._bitmaps.length }); 46 | for (let i = 0; i < this.mustUpdate.length; i++) 47 | this.mustUpdate[i] = true; 48 | this.mustBeTransfered = true; 49 | } 50 | updateInnerGpuTextures(commandEncoder) { 51 | let bmp; 52 | for (let i = 0; i < this._bitmaps.length; i++) { 53 | bmp = this.bitmaps[i]; 54 | if (bmp instanceof GPUTexture) { 55 | commandEncoder.copyTextureToTexture({ texture: bmp }, { texture: this.gpuResource }, [this.gpuResource.width, this.gpuResource.height, i]); 56 | } 57 | } 58 | } 59 | update() { 60 | if (this.mustBeTransfered) { 61 | //console.log("update textureArray") 62 | if (!this.gpuResource) 63 | this.createGpuResource(); 64 | let bmp; 65 | for (let i = 0; i < this._bitmaps.length; i++) { 66 | bmp = this.bitmaps[i]; 67 | if (!(bmp instanceof GPUTexture) && this.mustUpdate[i]) { 68 | XGPU.device.queue.copyExternalImageToTexture({ source: bmp }, { texture: this.gpuResource, origin: [0, 0, i] }, [bmp.width, bmp.height]); 69 | this.mustUpdate[i] = false; 70 | } 71 | } 72 | this.mustBeTransfered = false; 73 | } 74 | } 75 | //----- 76 | createDeclaration(varName, bindingId, groupId = 0) { 77 | return "@binding(" + bindingId + ") @group(" + groupId + ") var " + varName + ":texture_2d_array<" + this.sampledType + ">;\n"; 78 | } 79 | createBindGroupLayoutEntry(bindingId) { 80 | let sampleType = "float"; 81 | if (this.sampledType === "i32") 82 | sampleType = "sint"; 83 | else if (this.sampledType === "u32") 84 | sampleType = "uint"; 85 | return { 86 | binding: bindingId, 87 | visibility: GPUShaderStage.FRAGMENT, 88 | texture: { 89 | sampleType, 90 | viewDimension: "2d-array", 91 | multisampled: false 92 | }, 93 | }; 94 | } 95 | createBindGroupEntry(bindingId) { 96 | if (!this.gpuResource) 97 | this.createGpuResource(); 98 | return { 99 | binding: bindingId, 100 | resource: this._view, 101 | }; 102 | } 103 | } 104 | -------------------------------------------------------------------------------- /dist/xGPU/shader/resources/ImageTextureIO.d.ts: -------------------------------------------------------------------------------- 1 | /// 2 | import { ImageTexture } from "./ImageTexture"; 3 | export declare class ImageTextureIO { 4 | textures: ImageTexture[]; 5 | descriptor: { 6 | size: GPUExtent3D; 7 | format: GPUTextureFormat; 8 | usage?: number; 9 | }; 10 | protected stagingBuffer: GPUBuffer; 11 | protected canCallMapAsync: boolean; 12 | onOutputData: (data: Uint32Array) => void; 13 | constructor(descriptor: { 14 | source: ImageBitmap | HTMLCanvasElement | HTMLVideoElement | OffscreenCanvas | GPUTexture | null; 15 | width?: number; 16 | height?: number; 17 | format?: GPUTextureFormat; 18 | }); 19 | clone(): ImageTextureIO; 20 | createDeclaration(name: string, bindingId: number, groupId: number): string; 21 | protected outputBuffer: GPUBuffer; 22 | destroy(): void; 23 | getOutputData(): Promise; 24 | get width(): number; 25 | get height(): number; 26 | textureSize(): GPUExtent3D; 27 | } 28 | -------------------------------------------------------------------------------- /dist/xGPU/shader/resources/ImageTextureIO.js: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2023 Thomas Le Coz. All rights reserved. 2 | // This code is governed by an MIT license that can be found in the LICENSE file. 3 | import { XGPU } from "../../XGPU"; 4 | import { ImageTexture } from "./ImageTexture"; 5 | export class ImageTextureIO { 6 | textures = []; 7 | descriptor; 8 | stagingBuffer; 9 | canCallMapAsync = true; 10 | onOutputData; 11 | constructor(descriptor) { 12 | let w, h; 13 | if (descriptor.source != null) { 14 | w = descriptor.source.width; 15 | h = descriptor.source.height; 16 | } 17 | else { 18 | if (!descriptor.width || !descriptor.height) { 19 | throw new Error("ImageTextureIO width and/or height missing in descriptor"); 20 | } 21 | w = descriptor.width; 22 | h = descriptor.height; 23 | } 24 | this.descriptor = { 25 | size: [w, h], 26 | format: "rgba8unorm", 27 | usage: (descriptor.source instanceof GPUTexture) ? descriptor.source.usage : undefined 28 | }; 29 | if (descriptor.format) 30 | this.descriptor.format = descriptor.format; 31 | this.textures[0] = new ImageTexture(this.descriptor); 32 | this.textures[1] = new ImageTexture(this.descriptor); 33 | this.textures[0].io = 1; 34 | this.textures[1].io = 2; 35 | this.textures[0].resourceIO = this; 36 | this.textures[1].resourceIO = this; 37 | if (descriptor.source != null) 38 | this.textures[0].source = descriptor.source; 39 | } 40 | clone() { 41 | const obj = { 42 | source: this.textures[0].gpuResource, 43 | width: this.descriptor.size[0], 44 | height: this.descriptor.size[1], 45 | format: this.descriptor.format 46 | }; 47 | return new ImageTextureIO(obj); 48 | } 49 | createDeclaration(name, bindingId, groupId) { 50 | let result = ""; 51 | const varName = name.substring(0, 1).toLowerCase() + name.slice(1); 52 | result += " @binding(" + bindingId + ") @group(" + groupId + ") var " + varName + " : texture_2d;\n"; 53 | result += " @binding(" + (bindingId + 1) + ") @group(" + groupId + ") var " + varName + "_out" + " : texture_storage_2d;\n"; 54 | return result; 55 | } 56 | outputBuffer; 57 | destroy() { 58 | if (this.stagingBuffer) 59 | this.stagingBuffer.destroy(); 60 | this.textures = undefined; 61 | this.onOutputData = undefined; 62 | } 63 | async getOutputData() { 64 | if (!this.onOutputData || !this.canCallMapAsync) 65 | return; 66 | if (!this.outputBuffer) { 67 | this.outputBuffer = XGPU.device.createBuffer({ 68 | size: this.width * this.height * 4 * 4, 69 | usage: GPUBufferUsage.COPY_SRC | GPUBufferUsage.COPY_DST, 70 | mappedAtCreation: false, 71 | }); 72 | this.stagingBuffer = XGPU.createStagingBuffer(this.outputBuffer.size); 73 | } 74 | var texture = this.textures[0].gpuResource; 75 | const copyEncoder = XGPU.device.createCommandEncoder(); 76 | const stage = this.stagingBuffer; 77 | copyEncoder.copyTextureToBuffer({ texture: texture }, { buffer: this.outputBuffer, bytesPerRow: Math.ceil((this.width * 4) / 256) * 256, rowsPerImage: this.height }, [this.width, this.height, 1]); 78 | copyEncoder.copyBufferToBuffer(this.outputBuffer, 0, stage, 0, stage.size); 79 | XGPU.device.queue.submit([copyEncoder.finish()]); 80 | this.canCallMapAsync = false; 81 | await this.stagingBuffer.mapAsync(GPUMapMode.READ, 0, stage.size); 82 | this.canCallMapAsync = true; 83 | const copyArray = stage.getMappedRange(0, stage.size); 84 | const data = copyArray.slice(0); 85 | stage.unmap(); 86 | this.onOutputData(new Uint32Array(data)); 87 | } 88 | get width() { return this.textures[0].gpuResource.width; } 89 | get height() { return this.textures[0].gpuResource.height; } 90 | textureSize() { return this.descriptor.size; } 91 | } 92 | -------------------------------------------------------------------------------- /dist/xGPU/shader/resources/StageableBuffer.d.ts: -------------------------------------------------------------------------------- 1 | /// 2 | import { EventDispatcher } from "../../EventDispatcher"; 3 | export declare class StageableBuffer extends EventDispatcher { 4 | static ON_OUTPUT_DATA: string; 5 | static ON_OUTPUT_PROCESS_START: string; 6 | onOutputData: ((data: ArrayBuffer) => void) | null; 7 | constructor(); 8 | protected stagingBuffer: GPUBuffer; 9 | protected canCallMapAsync: boolean; 10 | onCanCallMapAsync: (() => void) | null; 11 | get mustOutputData(): boolean; 12 | getOutputData(buffer: GPUBuffer): Promise; 13 | } 14 | -------------------------------------------------------------------------------- /dist/xGPU/shader/resources/StageableBuffer.js: -------------------------------------------------------------------------------- 1 | import { EventDispatcher } from "../../EventDispatcher"; 2 | import { XGPU } from "../../XGPU"; 3 | export class StageableBuffer extends EventDispatcher { 4 | static ON_OUTPUT_DATA = "ON_OUTPUT_DATA"; 5 | static ON_OUTPUT_PROCESS_START = "ON_OUTPUT_PROCESS_START"; 6 | onOutputData = null; 7 | constructor() { 8 | super(); 9 | } 10 | stagingBuffer; 11 | canCallMapAsync = true; 12 | onCanCallMapAsync = null; 13 | get mustOutputData() { 14 | return !!this.onOutputData || this.hasEventListener(StageableBuffer.ON_OUTPUT_DATA); 15 | } 16 | async getOutputData(buffer) { 17 | if (!this.onOutputData && !this.hasEventListener(StageableBuffer.ON_OUTPUT_DATA)) 18 | return; 19 | if (!this.canCallMapAsync) { 20 | //console.warn("the last call of 'getOutputData' is not completed yet. You must wait 'ON_OUTPUT_DATA' to call computePipeline.nextFrame()" ) 21 | return; 22 | } 23 | this.dispatchEvent(StageableBuffer.ON_OUTPUT_PROCESS_START); 24 | this.canCallMapAsync = false; 25 | //const buffer:GPUBuffer = this.gpuResource; 26 | //console.log("getOutputData ",buffer.size+" vs "+this.bufferSize); 27 | if (!this.stagingBuffer || buffer.size != this.stagingBuffer.size) 28 | this.stagingBuffer = XGPU.createStagingBuffer(buffer.size); 29 | const copyEncoder = XGPU.device.createCommandEncoder(); 30 | const stage = this.stagingBuffer; 31 | copyEncoder.copyBufferToBuffer(buffer, 0, stage, 0, stage.size); 32 | XGPU.device.queue.submit([copyEncoder.finish()]); 33 | await this.stagingBuffer.mapAsync(GPUMapMode.READ, 0, stage.size); 34 | const copyArray = stage.getMappedRange(0, stage.size); 35 | const data = copyArray.slice(0); 36 | stage.unmap(); 37 | this.canCallMapAsync = true; 38 | if (this.onCanCallMapAsync) 39 | this.onCanCallMapAsync(); 40 | this.dispatchEvent(StageableBuffer.ON_OUTPUT_DATA, data); 41 | if (this.onOutputData) 42 | this.onOutputData(data); 43 | } 44 | } 45 | -------------------------------------------------------------------------------- /dist/xGPU/shader/resources/TextureSampler.d.ts: -------------------------------------------------------------------------------- 1 | /// 2 | import { IShaderResource } from "./IShaderResource"; 3 | export type TextureSamplerDescriptor = { 4 | minFilter?: "nearest" | "linear"; 5 | magFilter?: "nearest" | "linear"; 6 | addressModeU?: "clamp-to-edge" | "repeat" | "mirror-repeat"; 7 | addressModeV?: "clamp-to-edge" | "repeat" | "mirror-repeat"; 8 | addressModeW?: "clamp-to-edge" | "repeat" | "mirror-repeat"; 9 | mipmapFilter?: "nearest" | "linear"; 10 | lodMinClamp?: number; 11 | lodMaxClamp?: number; 12 | maxAnisotropy?: number; 13 | compare?: "never" | "less" | "equal" | "less-equal" | "greater" | "not-equal" | "greater-equal" | "always"; 14 | }; 15 | export declare class TextureSampler implements IShaderResource { 16 | mustBeTransfered: boolean; 17 | gpuResource: GPUSampler; 18 | descriptor: TextureSamplerDescriptor; 19 | constructor(descriptor?: { 20 | minFilter?: "nearest" | "linear"; 21 | magFilter?: "nearest" | "linear"; 22 | addressModeU?: "clamp-to-edge" | "repeat" | "mirror-repeat"; 23 | addressModeV?: "clamp-to-edge" | "repeat" | "mirror-repeat"; 24 | addressModeW?: "clamp-to-edge" | "repeat" | "mirror-repeat"; 25 | mipmapFilter?: "nearest" | "linear"; 26 | lodMinClamp?: number; 27 | lodMaxClamp?: number; 28 | maxAnisotropy?: number; 29 | compare?: "never" | "less" | "equal" | "less-equal" | "greater" | "not-equal" | "greater-equal" | "always"; 30 | }); 31 | clone(): TextureSampler; 32 | get isComparison(): boolean; 33 | get isFiltering(): boolean; 34 | setAddressModes(u?: GPUAddressMode, v?: GPUAddressMode, w?: GPUAddressMode): void; 35 | setFilterModes(min?: GPUFilterMode, mag?: GPUFilterMode, mipmap?: GPUMipmapFilterMode): void; 36 | setClamp(min?: number, max?: number): void; 37 | setCompareFunction(compareType?: "never" | "less" | "equal" | "less-equal" | "greater" | "not-equal" | "greater-equal" | "always"): void; 38 | setMaxAnisotropy(n: number): void; 39 | protected deviceId: number; 40 | createGpuResource(): void; 41 | destroyGpuResource(): void; 42 | update(): void; 43 | createDeclaration(varName: string, bindingId: number, groupId?: number): string; 44 | createBindGroupLayoutEntry(bindingId: number): { 45 | binding: number; 46 | visibility: number; 47 | sampler: { 48 | type: string; 49 | }; 50 | }; 51 | createBindGroupEntry(bindingId: number): { 52 | binding: number; 53 | resource: GPUSampler; 54 | }; 55 | setPipelineType(pipelineType: "compute" | "render" | "compute_mixed"): void; 56 | } 57 | -------------------------------------------------------------------------------- /dist/xGPU/shader/resources/UniformBuffer.d.ts: -------------------------------------------------------------------------------- 1 | /// 2 | import { PrimitiveType } from "../../PrimitiveType"; 3 | import { IShaderResource } from "./IShaderResource"; 4 | import { UniformGroup, Uniformable } from "./UniformGroup"; 5 | import { StageableBuffer } from "./StageableBuffer"; 6 | export type UniformBufferDescriptor = { 7 | useLocalVariable?: boolean; 8 | visibility?: GPUShaderStageFlags; 9 | accessMode?: "read" | "read_write"; 10 | }; 11 | export declare class UniformBuffer extends StageableBuffer implements IShaderResource { 12 | gpuResource: GPUBuffer; 13 | descriptor: UniformBufferDescriptor; 14 | group: UniformGroup; 15 | get mustBeTransfered(): boolean; 16 | set mustBeTransfered(b: boolean); 17 | constructor(items: any, descriptor?: { 18 | useLocalVariable?: boolean; 19 | visibility?: GPUShaderStageFlags; 20 | accessMode?: "read" | "read_write"; 21 | }); 22 | cloned: boolean; 23 | clone(propertyNames?: string[]): UniformBuffer; 24 | add(name: string, data: PrimitiveType, useLocalVariable?: boolean): Uniformable; 25 | remove(name: string): Uniformable; 26 | update(): void; 27 | createStruct(uniformName: string): { 28 | struct: string; 29 | localVariables: string; 30 | }; 31 | createDeclaration(uniformName: string, bindingId: number, groupId?: number): string; 32 | getUniformById(id: number): Uniformable; 33 | getUniformByName(name: string): Uniformable; 34 | protected _accessMode: "read" | "read_write"; 35 | get accessMode(): "read" | "read_write"; 36 | protected _bufferType: "read-only-storage" | "storage" | "uniform"; 37 | get bufferType(): "read-only-storage" | "uniform" | "storage"; 38 | createGpuResource(): any; 39 | getItemsAsArray(): any[]; 40 | time: number; 41 | destroyGpuResource(): void; 42 | createBindGroupLayoutEntry(bindingId: number): { 43 | binding: number; 44 | visibility: number; 45 | buffer: { 46 | type: string; 47 | }; 48 | }; 49 | createBindGroupEntry(bindingId: number): { 50 | binding: number; 51 | resource: { 52 | buffer: GPUBuffer; 53 | }; 54 | }; 55 | get items(): any; 56 | get itemNames(): string[]; 57 | get nbComponent(): number; 58 | get nbUniforms(): number; 59 | protected _usage: number; 60 | protected debug: string; 61 | protected shaderVisibility: GPUShaderStageFlags; 62 | protected pipelineType: "compute" | "render" | "compute_mixed"; 63 | setPipelineType(pipelineType: "compute" | "render" | "compute_mixed"): void; 64 | } 65 | -------------------------------------------------------------------------------- /dist/xGPU/shader/resources/UniformGroup.d.ts: -------------------------------------------------------------------------------- 1 | /// 2 | import { PrimitiveFloatUniform, PrimitiveIntUniform, PrimitiveType, PrimitiveUintUniform } from "../../PrimitiveType"; 3 | import { UniformBuffer } from "./UniformBuffer"; 4 | import { UniformGroupArray } from "./UniformGroupArray"; 5 | import { EventDispatcher } from "../../EventDispatcher"; 6 | export type Uniformable = PrimitiveFloatUniform | PrimitiveIntUniform | PrimitiveUintUniform | UniformGroup | UniformGroupArray; 7 | export declare class UniformGroup extends EventDispatcher { 8 | static ON_CHANGE: string; 9 | static ON_CHANGED: string; 10 | unstackedItems: any; 11 | items: Uniformable[]; 12 | itemNames: string[]; 13 | arrayStride: number; 14 | startId: number; 15 | globalStartId: number; 16 | createVariableInsideMain: boolean; 17 | mustBeTransfered: boolean; 18 | protected mustDispatchChangeEvent: boolean; 19 | protected _name: string; 20 | wgsl: { 21 | struct: string; 22 | localVariables: string; 23 | }; 24 | wgslStructNames: string[]; 25 | datas: ArrayBuffer; 26 | dataView: DataView; 27 | private debug; 28 | set(datas: ArrayBuffer): void; 29 | protected buffer: UniformBuffer; 30 | get uniformBuffer(): UniformBuffer; 31 | set uniformBuffer(buffer: UniformBuffer); 32 | destroy(): void; 33 | protected usedAsUniformBuffer: boolean; 34 | constructor(items: any, useLocalVariable?: boolean, usedAsUniformBuffer?: boolean); 35 | get name(): string; 36 | set name(s: string); 37 | clone(propertyNames?: string[]): UniformGroup; 38 | remove(name: string): Uniformable; 39 | add(name: string, data: Uniformable, useLocalVariable?: boolean, stackItems?: boolean): Uniformable; 40 | getElementByName(name: string): Uniformable; 41 | protected getStructName(name: string): string; 42 | protected getVarName(name: string): string; 43 | createVariable(uniformBufferName: string): string; 44 | updateStack(): void; 45 | forceUpdate(): void; 46 | get type(): any; 47 | setDatas(item: PrimitiveType, dataView?: DataView, offset?: number): void; 48 | updateItemFromDataView(dataView: DataView, offset: number): void; 49 | copyIntoDataView(dataView: DataView, offset: number): void; 50 | transfertWholeBuffer: boolean; 51 | update(gpuResource: GPUBuffer): Promise; 52 | existingStrucName: string; 53 | getStruct(name: string): { 54 | struct: string; 55 | localVariables: string; 56 | }; 57 | stackItems(items: any): Uniformable[]; 58 | updateStartIdFromParentToChildren(): void; 59 | get definition(): { 60 | type: string; 61 | values: ArrayBuffer; 62 | items: any; 63 | name: string; 64 | }; 65 | } 66 | -------------------------------------------------------------------------------- /dist/xGPU/shader/resources/UniformGroupArray.d.ts: -------------------------------------------------------------------------------- 1 | /// 2 | import { EventDispatcher } from "../../EventDispatcher"; 3 | import { UniformBuffer } from "./UniformBuffer"; 4 | import { UniformGroup } from "./UniformGroup"; 5 | export declare class UniformGroupArray extends EventDispatcher { 6 | static ON_CHANGE: string; 7 | static ON_CHANGED: string; 8 | groups: UniformGroup[]; 9 | startId: number; 10 | globalStartId: number; 11 | createVariableInsideMain: boolean; 12 | name: string; 13 | mustBeTransfered: boolean; 14 | protected mustDispatchChangeEvent: boolean; 15 | protected buffer: UniformBuffer; 16 | get uniformBuffer(): UniformBuffer; 17 | set uniformBuffer(buffer: UniformBuffer); 18 | constructor(groups: UniformGroup[], createLocalVariable?: boolean); 19 | updateStartIdFromParentToChildren(): void; 20 | clone(): UniformGroupArray; 21 | get type(): any; 22 | copyIntoDataView(dataView: DataView, offset: number): void; 23 | protected getStructName(name: string): string; 24 | protected getVarName(name: string): string; 25 | createVariable(uniformBufferName: string): string; 26 | update(gpuResource: GPUBuffer): void; 27 | forceUpdate(): void; 28 | getElementById(id: number): UniformGroup; 29 | get length(): number; 30 | get arrayStride(): number; 31 | get isArray(): boolean; 32 | get isUniformGroup(): boolean; 33 | get definition(): { 34 | type: string; 35 | groups: any[]; 36 | name: string; 37 | }; 38 | } 39 | -------------------------------------------------------------------------------- /dist/xGPU/shader/resources/VertexAttribute.d.ts: -------------------------------------------------------------------------------- 1 | import { VertexBuffer } from "./VertexBuffer"; 2 | export declare class VertexAttribute { 3 | static Float(datas?: number[][] | number[] | number, offset?: number): { 4 | type: string; 5 | offset: number; 6 | datas: number | number[] | number[][]; 7 | }; 8 | static Vec2(datas?: number[][] | number[] | number, offset?: number): { 9 | type: string; 10 | offset: number; 11 | datas: number | number[] | number[][]; 12 | }; 13 | static Vec3(datas?: number[][] | number[] | number, offset?: number): { 14 | type: string; 15 | offset: number; 16 | datas: number | number[] | number[][]; 17 | }; 18 | static Vec4(datas?: number[][] | number[] | number, offset?: number): { 19 | type: string; 20 | offset: number; 21 | datas: number | number[] | number[][]; 22 | }; 23 | static Int(datas?: number[][] | number[] | number, offset?: number): { 24 | type: string; 25 | offset: number; 26 | datas: number | number[] | number[][]; 27 | }; 28 | static IVec2(datas?: number[][] | number[] | number, offset?: number): { 29 | type: string; 30 | offset: number; 31 | datas: number | number[] | number[][]; 32 | }; 33 | static IVec3(datas?: number[][] | number[] | number, offset?: number): { 34 | type: string; 35 | offset: number; 36 | datas: number | number[] | number[][]; 37 | }; 38 | static IVec4(datas?: number[][] | number[] | number, offset?: number): { 39 | type: string; 40 | offset: number; 41 | datas: number | number[] | number[][]; 42 | }; 43 | static Uint(datas?: number[][] | number[] | number, offset?: number): { 44 | type: string; 45 | offset: number; 46 | datas: number | number[] | number[][]; 47 | }; 48 | static UVec2(datas?: number[][] | number[] | number, offset?: number): { 49 | type: string; 50 | offset: number; 51 | datas: number | number[] | number[][]; 52 | }; 53 | static UVec3(datas?: number[][] | number[] | number, offset?: number): { 54 | type: string; 55 | offset: number; 56 | datas: number | number[] | number[][]; 57 | }; 58 | static UVec4(datas?: number[][] | number[] | number, offset?: number): { 59 | type: string; 60 | offset: number; 61 | datas: number | number[] | number[][]; 62 | }; 63 | static get types(): any; 64 | private _name; 65 | private _dataType; 66 | private nbValues; 67 | private vertexType; 68 | private _data; 69 | dataOffset: number; 70 | mustBeTransfered: boolean; 71 | protected _vertexBuffer: VertexBuffer; 72 | constructor(name: string, dataType: string, offset?: number); 73 | protected waitingVertexBuffer: boolean; 74 | get vertexBuffer(): VertexBuffer; 75 | set vertexBuffer(vb: VertexBuffer); 76 | get datas(): number[][] | number[]; 77 | set datas(n: number[][] | number[]); 78 | get useByVertexData(): boolean; 79 | get format(): string; 80 | get type(): string; 81 | get bytePerElement(): number; 82 | get varType(): string; 83 | get name(): string; 84 | get nbComponent(): number; 85 | private renameVertexDataType; 86 | private getVertexDataType; 87 | } 88 | -------------------------------------------------------------------------------- /dist/xGPU/shader/resources/VertexBuffer.d.ts: -------------------------------------------------------------------------------- 1 | /// 2 | import { ShaderStruct } from "../shaderParts/ShaderStruct"; 3 | import { IShaderResource } from "./IShaderResource"; 4 | import { VertexAttribute } from "./VertexAttribute"; 5 | import { VertexBufferIO } from "./VertexBufferIO"; 6 | import { StageableBuffer } from "./StageableBuffer"; 7 | export type VertexBufferDescriptor = { 8 | stepMode?: "vertex" | "instance"; 9 | accessMode?: "read" | "read_write"; 10 | usage?: GPUBufferUsageFlags; 11 | datas?: Float32Array | Int32Array | Uint32Array | Uint16Array; 12 | }; 13 | export declare class VertexBuffer extends StageableBuffer implements IShaderResource { 14 | bufferId: number; 15 | io: number; 16 | resourceIO: VertexBufferIO; 17 | mustBeTransfered: boolean; 18 | vertexArrays: VertexAttribute[]; 19 | attributes: any; 20 | gpuResource: GPUBuffer; 21 | descriptor: VertexBufferDescriptor; 22 | private _nbComponent; 23 | private _datas; 24 | nbComponentData: number; 25 | attributeChanged: boolean; 26 | constructor(attributes: any, descriptor?: { 27 | stepMode?: "vertex" | "instance"; 28 | accessMode?: "read" | "read_write"; 29 | usage?: GPUBufferUsageFlags; 30 | datas?: Float32Array | Int32Array | Uint32Array | Uint16Array; 31 | gpuUpdateMode?: "auto" | "manual"; 32 | }); 33 | clone(): VertexBuffer; 34 | protected gpuBufferIOs: GPUBuffer[]; 35 | protected gpuBufferIO_index: number; 36 | initBufferIO(buffers: GPUBuffer[]): void; 37 | get buffer(): GPUBuffer; 38 | getCurrentBuffer(): GPUBuffer; 39 | get stepMode(): "vertex" | "instance"; 40 | get length(): number; 41 | get nbComponent(): number; 42 | get nbVertex(): number; 43 | get datas(): Float32Array | Int32Array | Uint32Array | Uint16Array; 44 | set datas(f: Float32Array | Int32Array | Uint32Array | Uint16Array); 45 | setComplexDatas(datas: Float32Array | Int32Array | Uint32Array, nbComponentTotal: number): void; 46 | get attributeDescriptor(): any; 47 | private _byteCount; 48 | createArray(name: string, dataType: string, offset?: number): VertexAttribute; 49 | getAttributeByName(name: string): VertexAttribute; 50 | createDeclaration(vertexBufferName: string, bindingId: number, groupId?: number, isInput?: boolean): string; 51 | debug: boolean; 52 | createBindGroupLayoutEntry(bindingId: number): any; 53 | createBindGroupEntry(bindingId: number): any; 54 | protected pipelineType: "compute" | "render" | "compute_mixed"; 55 | setPipelineType(pipelineType: "compute" | "render" | "compute_mixed"): void; 56 | createStruct(name: string): ShaderStruct; 57 | arrayStride: number; 58 | stackAttributes(builtinOffset?: number): { 59 | stepMode: "instance" | "vertex"; 60 | arrayStride: number; 61 | attributes: any[]; 62 | }; 63 | addVertexInstance(instanceId: number, o: any): void; 64 | protected layout: any; 65 | createVertexBufferLayout(builtinOffset?: number): any; 66 | lowLevelBuffer: boolean; 67 | createLowLevelBuffer(bufferSize: number, accessMode?: "read" | "read_write", usage?: number): void; 68 | resizeLowLevelBuffer(byteLength: number, copyPreviousDataWithin?: boolean): void; 69 | updateLowLevelBuffer(buffer: ArrayBuffer, bufferOffset: number, dataOffset?: number, size?: number): void; 70 | protected _bufferSize: number; 71 | protected deviceId: number; 72 | get bufferSize(): number; 73 | createGpuResource(): void; 74 | time: number; 75 | protected destroyed: boolean; 76 | destroyGpuResource(): void; 77 | updateBuffer(): void; 78 | getVertexArrayById(id: number): VertexAttribute; 79 | protected updateAttributes(): void; 80 | update(): boolean; 81 | } 82 | -------------------------------------------------------------------------------- /dist/xGPU/shader/resources/VertexBufferIO.d.ts: -------------------------------------------------------------------------------- 1 | import { StageableBuffer } from "./StageableBuffer"; 2 | import { VertexBuffer } from "./VertexBuffer"; 3 | export declare class VertexBufferIO extends StageableBuffer { 4 | buffers: VertexBuffer[]; 5 | descriptor: any; 6 | protected deviceId: number; 7 | constructor(attributes: any, descriptor?: any); 8 | get input(): VertexBuffer; 9 | get output(): VertexBuffer; 10 | destroy(): void; 11 | private rebuildAfterDeviceLost; 12 | currentDatas: ArrayBuffer; 13 | getOutputData(): Promise; 14 | clone(): VertexBufferIO; 15 | createDeclaration(name: string, bindingId: number, groupId: number): string; 16 | createVertexInstances(nbInstance: number, createInstance: (instanceId: number) => any): void; 17 | protected view: any; 18 | getVertexInstances(datas: Float32Array, onGetInstance: (o: any) => void): void; 19 | dataStructureChanged: boolean; 20 | nextDatas: Float32Array | Int32Array | Uint32Array; 21 | set datas(v: Float32Array | Int32Array | Uint32Array); 22 | protected attributeDesc: any; 23 | get attributeDescriptor(): any; 24 | update(): void; 25 | get bufferSize(): number; 26 | get nbVertex(): number; 27 | } 28 | -------------------------------------------------------------------------------- /dist/xGPU/shader/resources/VideoTexture.d.ts: -------------------------------------------------------------------------------- 1 | /// 2 | import { Bindgroup } from "../Bindgroup"; 3 | import { IShaderResource } from "./IShaderResource"; 4 | export type VideoTextureDescriptor = { 5 | source?: HTMLVideoElement; 6 | format?: GPUTextureFormat; 7 | usage?: GPUTextureUsageFlags; 8 | size?: GPUExtent3D; 9 | mipLevelCount?: GPUIntegerCoordinate; 10 | sampleCount?: GPUSize32; 11 | dimension?: GPUTextureDimension; 12 | viewFormats?: GPUTextureFormat[]; 13 | defaultViewDescriptor?: any; 14 | }; 15 | export declare class VideoTexture implements IShaderResource { 16 | mustBeTransfered: boolean; 17 | descriptor: VideoTextureDescriptor; 18 | useWebcodec: boolean; 19 | gpuResource: HTMLVideoElement; 20 | protected bindgroups: Bindgroup[]; 21 | addBindgroup(bindgroup: Bindgroup): void; 22 | constructor(descriptor: { 23 | source?: HTMLVideoElement; 24 | format?: GPUTextureFormat; 25 | usage?: GPUTextureUsageFlags; 26 | size?: GPUExtent3D; 27 | mipLevelCount?: GPUIntegerCoordinate; 28 | sampleCount?: GPUSize32; 29 | dimension?: GPUTextureDimension; 30 | viewFormats?: GPUTextureFormat[]; 31 | defaultViewDescriptor?: any; 32 | }); 33 | clone(): VideoTexture; 34 | set source(video: HTMLVideoElement); 35 | createDeclaration(varName: string, bindingId: number, groupId?: number): string; 36 | createBindGroupLayoutEntry(bindingId: number): { 37 | binding: number; 38 | visibility: number; 39 | externalTexture: GPUExternalTextureBindingLayout; 40 | }; 41 | createGpuResource(): void; 42 | update(): void; 43 | protected deviceId: number; 44 | destroyGpuResource(): void; 45 | private videoFrame; 46 | createBindGroupEntry(bindingId: number): { 47 | binding: number; 48 | resource: GPUExternalTexture; 49 | }; 50 | setPipelineType(pipelineType: "compute" | "render" | "compute_mixed"): void; 51 | } 52 | -------------------------------------------------------------------------------- /dist/xGPU/shader/resources/attributes/FloatBuffer.d.ts: -------------------------------------------------------------------------------- 1 | import { VertexAttribute } from "../VertexAttribute"; 2 | export declare class FloatBuffer extends VertexAttribute { 3 | constructor(datas?: number[][] | number[] | number, offset?: number); 4 | } 5 | -------------------------------------------------------------------------------- /dist/xGPU/shader/resources/attributes/FloatBuffer.js: -------------------------------------------------------------------------------- 1 | import { VertexAttribute } from "../VertexAttribute"; 2 | export class FloatBuffer extends VertexAttribute { 3 | constructor(datas, offset) { 4 | if (datas != undefined && offset === undefined) { 5 | if (typeof datas === "number") { 6 | offset = datas; 7 | datas = undefined; 8 | } 9 | } 10 | super("", "float32", offset); 11 | if (typeof (datas) != "number") 12 | this.datas = datas; 13 | } 14 | } 15 | -------------------------------------------------------------------------------- /dist/xGPU/shader/resources/attributes/IVec2Buffer.d.ts: -------------------------------------------------------------------------------- 1 | import { VertexAttribute } from "../VertexAttribute"; 2 | export declare class IVec2Buffer extends VertexAttribute { 3 | constructor(datas?: number[][] | number[] | number, offset?: number); 4 | } 5 | -------------------------------------------------------------------------------- /dist/xGPU/shader/resources/attributes/IVec2Buffer.js: -------------------------------------------------------------------------------- 1 | import { VertexAttribute } from "../VertexAttribute"; 2 | export class IVec2Buffer extends VertexAttribute { 3 | constructor(datas, offset) { 4 | if (datas != undefined && offset === undefined) { 5 | if (typeof datas === "number") { 6 | offset = datas; 7 | datas = undefined; 8 | } 9 | } 10 | super("", "sint32x2", offset); 11 | if (typeof (datas) != "number") 12 | this.datas = datas; 13 | } 14 | } 15 | -------------------------------------------------------------------------------- /dist/xGPU/shader/resources/attributes/IVec3Buffer.d.ts: -------------------------------------------------------------------------------- 1 | import { VertexAttribute } from "../VertexAttribute"; 2 | export declare class IVec3Buffer extends VertexAttribute { 3 | constructor(datas?: number[][] | number[] | number, offset?: number); 4 | } 5 | -------------------------------------------------------------------------------- /dist/xGPU/shader/resources/attributes/IVec3Buffer.js: -------------------------------------------------------------------------------- 1 | import { VertexAttribute } from "../VertexAttribute"; 2 | export class IVec3Buffer extends VertexAttribute { 3 | constructor(datas, offset) { 4 | if (datas != undefined && offset === undefined) { 5 | if (typeof datas === "number") { 6 | offset = datas; 7 | datas = undefined; 8 | } 9 | } 10 | super("", "sint32x3", offset); 11 | if (typeof (datas) != "number") 12 | this.datas = datas; 13 | } 14 | } 15 | -------------------------------------------------------------------------------- /dist/xGPU/shader/resources/attributes/IVec4Buffer.d.ts: -------------------------------------------------------------------------------- 1 | import { VertexAttribute } from "../VertexAttribute"; 2 | export declare class IVec4Buffer extends VertexAttribute { 3 | constructor(datas?: number[][] | number[] | number, offset?: number); 4 | } 5 | -------------------------------------------------------------------------------- /dist/xGPU/shader/resources/attributes/IVec4Buffer.js: -------------------------------------------------------------------------------- 1 | import { VertexAttribute } from "../VertexAttribute"; 2 | export class IVec4Buffer extends VertexAttribute { 3 | constructor(datas, offset) { 4 | if (datas != undefined && offset === undefined) { 5 | if (typeof datas === "number") { 6 | offset = datas; 7 | datas = undefined; 8 | } 9 | } 10 | super("", "sint32x4", offset); 11 | if (typeof (datas) != "number") 12 | this.datas = datas; 13 | } 14 | } 15 | -------------------------------------------------------------------------------- /dist/xGPU/shader/resources/attributes/IntBuffer.d.ts: -------------------------------------------------------------------------------- 1 | import { VertexAttribute } from "../VertexAttribute"; 2 | export declare class IntBuffer extends VertexAttribute { 3 | constructor(datas?: number[][] | number[] | number, offset?: number); 4 | } 5 | -------------------------------------------------------------------------------- /dist/xGPU/shader/resources/attributes/IntBuffer.js: -------------------------------------------------------------------------------- 1 | import { VertexAttribute } from "../VertexAttribute"; 2 | export class IntBuffer extends VertexAttribute { 3 | constructor(datas, offset) { 4 | if (datas != undefined && offset === undefined) { 5 | if (typeof datas === "number") { 6 | offset = datas; 7 | datas = undefined; 8 | } 9 | } 10 | super("", "sint32", offset); 11 | if (typeof (datas) != "number") 12 | this.datas = datas; 13 | } 14 | } 15 | -------------------------------------------------------------------------------- /dist/xGPU/shader/resources/attributes/UVec2Buffer.d.ts: -------------------------------------------------------------------------------- 1 | import { VertexAttribute } from "../VertexAttribute"; 2 | export declare class UVec2Buffer extends VertexAttribute { 3 | constructor(datas?: number[][] | number[] | number, offset?: number); 4 | } 5 | -------------------------------------------------------------------------------- /dist/xGPU/shader/resources/attributes/UVec2Buffer.js: -------------------------------------------------------------------------------- 1 | import { VertexAttribute } from "../VertexAttribute"; 2 | export class UVec2Buffer extends VertexAttribute { 3 | constructor(datas, offset) { 4 | if (datas != undefined && offset === undefined) { 5 | if (typeof datas === "number") { 6 | offset = datas; 7 | datas = undefined; 8 | } 9 | } 10 | super("", "uint32x2", offset); 11 | if (typeof (datas) != "number") 12 | this.datas = datas; 13 | } 14 | } 15 | -------------------------------------------------------------------------------- /dist/xGPU/shader/resources/attributes/UVec3Buffer.d.ts: -------------------------------------------------------------------------------- 1 | import { VertexAttribute } from "../VertexAttribute"; 2 | export declare class UVec3Buffer extends VertexAttribute { 3 | constructor(datas?: number[][] | number[] | number, offset?: number); 4 | } 5 | -------------------------------------------------------------------------------- /dist/xGPU/shader/resources/attributes/UVec3Buffer.js: -------------------------------------------------------------------------------- 1 | import { VertexAttribute } from "../VertexAttribute"; 2 | export class UVec3Buffer extends VertexAttribute { 3 | constructor(datas, offset) { 4 | if (datas != undefined && offset === undefined) { 5 | if (typeof datas === "number") { 6 | offset = datas; 7 | datas = undefined; 8 | } 9 | } 10 | super("", "uint32x3", offset); 11 | if (typeof (datas) != "number") 12 | this.datas = datas; 13 | } 14 | } 15 | -------------------------------------------------------------------------------- /dist/xGPU/shader/resources/attributes/UVec4Buffer.d.ts: -------------------------------------------------------------------------------- 1 | import { VertexAttribute } from "../VertexAttribute"; 2 | export declare class UVec4Buffer extends VertexAttribute { 3 | constructor(datas?: number[][] | number[] | number, offset?: number); 4 | } 5 | -------------------------------------------------------------------------------- /dist/xGPU/shader/resources/attributes/UVec4Buffer.js: -------------------------------------------------------------------------------- 1 | import { VertexAttribute } from "../VertexAttribute"; 2 | export class UVec4Buffer extends VertexAttribute { 3 | constructor(datas, offset) { 4 | if (datas != undefined && offset === undefined) { 5 | if (typeof datas === "number") { 6 | offset = datas; 7 | datas = undefined; 8 | } 9 | } 10 | super("", "uint32x4", offset); 11 | if (typeof (datas) != "number") 12 | this.datas = datas; 13 | } 14 | } 15 | -------------------------------------------------------------------------------- /dist/xGPU/shader/resources/attributes/UintBuffer.d.ts: -------------------------------------------------------------------------------- 1 | import { VertexAttribute } from "../VertexAttribute"; 2 | export declare class UintBuffer extends VertexAttribute { 3 | constructor(datas?: number[][] | number[] | number, offset?: number); 4 | } 5 | -------------------------------------------------------------------------------- /dist/xGPU/shader/resources/attributes/UintBuffer.js: -------------------------------------------------------------------------------- 1 | import { VertexAttribute } from "../VertexAttribute"; 2 | export class UintBuffer extends VertexAttribute { 3 | constructor(datas, offset) { 4 | if (datas != undefined && offset === undefined) { 5 | if (typeof datas === "number") { 6 | offset = datas; 7 | datas = undefined; 8 | } 9 | } 10 | super("", "uint32", offset); 11 | if (typeof (datas) != "number") 12 | this.datas = datas; 13 | } 14 | } 15 | -------------------------------------------------------------------------------- /dist/xGPU/shader/resources/attributes/Vec2Buffer.d.ts: -------------------------------------------------------------------------------- 1 | import { VertexAttribute } from "../VertexAttribute"; 2 | export declare class Vec2Buffer extends VertexAttribute { 3 | constructor(datas?: number[][] | number[] | number, offset?: number); 4 | } 5 | -------------------------------------------------------------------------------- /dist/xGPU/shader/resources/attributes/Vec2Buffer.js: -------------------------------------------------------------------------------- 1 | import { VertexAttribute } from "../VertexAttribute"; 2 | export class Vec2Buffer extends VertexAttribute { 3 | constructor(datas, offset) { 4 | if (datas != undefined && offset === undefined) { 5 | if (typeof datas === "number") { 6 | offset = datas; 7 | datas = undefined; 8 | } 9 | } 10 | //console.log("Vec2Buffer ", offset) 11 | super("", "float32x2", offset); 12 | //console.log("Vec2Buffer.dataOffset = ", this.dataOffset) 13 | if (typeof (datas) != "number") { 14 | this.datas = datas; 15 | } 16 | } 17 | } 18 | -------------------------------------------------------------------------------- /dist/xGPU/shader/resources/attributes/Vec3Buffer.d.ts: -------------------------------------------------------------------------------- 1 | import { VertexAttribute } from "../VertexAttribute"; 2 | export declare class Vec3Buffer extends VertexAttribute { 3 | constructor(datas?: number[][] | number[] | number, offset?: number); 4 | } 5 | -------------------------------------------------------------------------------- /dist/xGPU/shader/resources/attributes/Vec3Buffer.js: -------------------------------------------------------------------------------- 1 | import { VertexAttribute } from "../VertexAttribute"; 2 | export class Vec3Buffer extends VertexAttribute { 3 | constructor(datas, offset) { 4 | if (datas != undefined && offset === undefined) { 5 | if (typeof datas === "number") { 6 | offset = datas; 7 | datas = undefined; 8 | } 9 | } 10 | super("", "float32x3", offset); 11 | if (typeof (datas) != "number") { 12 | this.datas = datas; 13 | } 14 | } 15 | } 16 | -------------------------------------------------------------------------------- /dist/xGPU/shader/resources/attributes/Vec4Buffer.d.ts: -------------------------------------------------------------------------------- 1 | import { VertexAttribute } from "../VertexAttribute"; 2 | export declare class Vec4Buffer extends VertexAttribute { 3 | constructor(datas?: number[][] | number[] | number, offset?: number); 4 | } 5 | -------------------------------------------------------------------------------- /dist/xGPU/shader/resources/attributes/Vec4Buffer.js: -------------------------------------------------------------------------------- 1 | import { VertexAttribute } from "../VertexAttribute"; 2 | export class Vec4Buffer extends VertexAttribute { 3 | constructor(datas, offset) { 4 | if (datas != undefined && offset === undefined) { 5 | if (typeof datas === "number") { 6 | offset = datas; 7 | datas = undefined; 8 | } 9 | } 10 | super("", "float32x4", offset); 11 | if (typeof (datas) != "number") { 12 | this.datas = datas; 13 | } 14 | } 15 | } 16 | -------------------------------------------------------------------------------- /dist/xGPU/shader/shaderParts/ShaderNode.d.ts: -------------------------------------------------------------------------------- 1 | export declare class ShaderNode { 2 | enabled: boolean; 3 | executeSubNodeAfterCode: boolean; 4 | private _text; 5 | private insideMainFunction; 6 | private _nodeByName; 7 | get nodeByName(): { 8 | [key: string]: ShaderNode; 9 | }; 10 | private subNodes; 11 | constructor(code?: string, insideMainFunction?: boolean); 12 | get text(): string; 13 | set text(s: string); 14 | replaceValues(values: { 15 | old: string; 16 | new: string; 17 | }[]): void; 18 | replaceKeyWord(wordToReplace: string, replacement: string): void; 19 | get value(): string; 20 | createNode(code?: string): ShaderNode; 21 | addNode(nodeName: string, code?: string): ShaderNode; 22 | } 23 | -------------------------------------------------------------------------------- /dist/xGPU/shader/shaderParts/ShaderNode.js: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2023 Thomas Le Coz. All rights reserved. 2 | // This code is governed by an MIT license that can be found in the LICENSE file. 3 | export class ShaderNode { 4 | enabled = true; 5 | executeSubNodeAfterCode = true; 6 | _text; 7 | insideMainFunction; 8 | _nodeByName = {}; 9 | get nodeByName() { 10 | return this._nodeByName; 11 | } 12 | subNodes; 13 | constructor(code = "", insideMainFunction = false) { 14 | this.text = code; 15 | this.insideMainFunction = insideMainFunction; 16 | } 17 | get text() { return this._text; } 18 | set text(s) { 19 | //--------- remove useless tabulations while keeping tabs structure ------- 20 | const lines = s.split("\n"); 21 | let line; 22 | let nbTabMin = 99999999; 23 | if (lines.length > 1) { 24 | for (let i = 0; i < lines.length; i++) { 25 | line = lines[i]; 26 | for (let j = 0; j < line.length; j++) { 27 | if (line[j] === "\n") 28 | continue; 29 | if (line[j] !== " ") { 30 | if (nbTabMin > j) 31 | nbTabMin = j; 32 | break; 33 | } 34 | } 35 | } 36 | if (this.insideMainFunction && nbTabMin >= 3) 37 | nbTabMin -= 3; 38 | for (let i = 0; i < lines.length; i++) { 39 | lines[i] = lines[i].slice(nbTabMin); 40 | } 41 | s = lines.join("\n"); 42 | } 43 | //----------------------------------------------------------------------- 44 | this._text = s; 45 | } 46 | replaceValues(values) { 47 | for (let i = 0; i < values.length; i++) { 48 | this.replaceKeyWord(values[i].old, values[i].new); 49 | //this._text = this._text.replace(values[i].old, values[i].new); 50 | } 51 | } 52 | replaceKeyWord(wordToReplace, replacement) { 53 | const regex = new RegExp(`(?<=[^\\w.])\\b${wordToReplace}\\b`, 'g'); 54 | this._text = this._text.replace(regex, replacement); 55 | } 56 | get value() { 57 | let result = ""; 58 | if (this.executeSubNodeAfterCode) { 59 | result += this.text + "\n"; 60 | } 61 | if (this.subNodes) { 62 | for (let i = 0; i < this.subNodes.length; i++) { 63 | result += this.subNodes[i].value + "\n"; 64 | } 65 | } 66 | if (!this.executeSubNodeAfterCode) 67 | result += this.text + "\n"; 68 | //console.log(this.text + " vs " + result) 69 | return result; 70 | } 71 | createNode(code = "") { 72 | const node = new ShaderNode(code); 73 | if (!this.subNodes) 74 | this.subNodes = []; 75 | this.subNodes.push(node); 76 | return node; 77 | } 78 | addNode(nodeName, code = "") { 79 | const node = this.createNode(code); 80 | this._nodeByName[nodeName] = node; 81 | return node; 82 | } 83 | } 84 | -------------------------------------------------------------------------------- /dist/xGPU/shader/shaderParts/ShaderStage.d.ts: -------------------------------------------------------------------------------- 1 | import { ShaderNode } from "./ShaderNode"; 2 | import { ShaderStruct } from "./ShaderStruct"; 3 | export declare class ShaderStage { 4 | inputs: { 5 | name: string; 6 | type: any; 7 | builtin?: string; 8 | }[]; 9 | outputs: { 10 | name: string; 11 | type: any; 12 | builtin?: string; 13 | }[]; 14 | export: { 15 | name: string; 16 | type: any; 17 | }[]; 18 | require: { 19 | name: string; 20 | type: any; 21 | }[]; 22 | pipelineConstants: any; 23 | constants: ShaderNode; 24 | main: ShaderNode; 25 | shaderType: "vertex" | "fragment" | "compute"; 26 | constructor(shaderType: "vertex" | "fragment" | "compute"); 27 | debugLogs: { 28 | label: string; 29 | val: string; 30 | }[]; 31 | debugRenders: { 32 | label: string; 33 | val: string; 34 | color: string; 35 | }[]; 36 | protected unwrapVariableInMainFunction(shaderVariables: string): string; 37 | protected unwrapVariableInWGSL(shaderVariables: string, wgsl: string): string; 38 | addOutputVariable(name: string, shaderType: { 39 | type: string; 40 | }): void; 41 | addInputVariable(name: string, shaderTypeOrBuiltIn: { 42 | type: string; 43 | builtin?: string; 44 | }): void; 45 | protected formatWGSLCode(code: string): string; 46 | get shaderInfos(): { 47 | code: string; 48 | output: ShaderStruct; 49 | }; 50 | protected _shaderInfos: { 51 | code: string; 52 | output: ShaderStruct; 53 | }; 54 | build(shaderPipeline: any, input: ShaderStruct): { 55 | code: string; 56 | output: ShaderStruct; 57 | }; 58 | } 59 | -------------------------------------------------------------------------------- /dist/xGPU/shader/shaderParts/ShaderStruct.d.ts: -------------------------------------------------------------------------------- 1 | export declare class ShaderStruct { 2 | protected properties: { 3 | name: string; 4 | type: string; 5 | builtin?: string; 6 | }[]; 7 | protected isShaderIO: boolean; 8 | name: string; 9 | constructor(name: string, properties?: ({ 10 | name: string; 11 | type: string; 12 | builtin?: string; 13 | })[]); 14 | clone(name?: string): ShaderStruct; 15 | addProperty(o: { 16 | name: string; 17 | type: string; 18 | builtin?: string; 19 | offset?: number; 20 | size?: number; 21 | obj?: any; 22 | }): ShaderStruct; 23 | getComputeVariableDeclaration(offset?: number): string; 24 | getFunctionParams(): string; 25 | getComputeFunctionParams(): string; 26 | getInputFromOutput(): ShaderStruct; 27 | get struct(): string; 28 | } 29 | -------------------------------------------------------------------------------- /dist/xGPU/shader/shaderParts/ShaderStruct.js: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2023 Thomas Le Coz. All rights reserved. 2 | // This code is governed by an MIT license that can be found in the LICENSE file. 3 | import { VertexBuffer } from "../resources/VertexBuffer"; 4 | export class ShaderStruct { 5 | properties = []; 6 | isShaderIO = false; 7 | name; 8 | constructor(name, properties) { 9 | if (name === "Input" || name === "Output") { 10 | this.isShaderIO = true; 11 | } 12 | //console.log(name + " => isShaderIO = ", this.isShaderIO) 13 | this.name = name; 14 | if (properties) { 15 | for (let i = 0; i < properties.length; i++) { 16 | if (!properties[i].builtin) 17 | properties[i].builtin = ""; 18 | } 19 | this.properties = properties; 20 | } 21 | } 22 | clone(name) { 23 | let n = name ? name : this.name; 24 | return new ShaderStruct(n, [...this.properties]); 25 | } 26 | addProperty(o) { 27 | //console.warn("addProperty ", o) 28 | if (!o.builtin) 29 | o.builtin = ""; 30 | this.properties.push(o); 31 | return this; 32 | } 33 | getComputeVariableDeclaration(offset = 0) { 34 | let o; 35 | let result = ""; 36 | let k = 0; 37 | for (let i = 0; i < this.properties.length; i++) { 38 | o = this.properties[i]; 39 | if (o.type.createDeclaration) { //if o.type has a type PipelineResource 40 | if (o.type instanceof VertexBuffer) { 41 | o.type.name = o.name; 42 | result += o.type.createDeclaration((offset + k++), 0, !o.isOutput); 43 | } 44 | else { 45 | result += o.type.createDeclaration(offset + k++); 46 | if (o.type.createStruct) 47 | result += o.type.createStruct().struct; 48 | } 49 | } 50 | } 51 | return result; 52 | } 53 | getFunctionParams() { 54 | let result = ""; 55 | let o; 56 | //console.log("getFunctionParams ", this.properties) 57 | for (let i = 0; i < this.properties.length; i++) { 58 | o = this.properties[i]; 59 | result += o.builtin + " " + o.name + ":" + o.type; 60 | if (i != this.properties.length - 1) 61 | result += ", "; 62 | if (i != this.properties.length - 1) 63 | result += " "; 64 | } 65 | return result; 66 | } 67 | getComputeFunctionParams() { 68 | let result = ""; 69 | let o; 70 | let k = 0; 71 | for (let i = 0; i < this.properties.length; i++) { 72 | o = this.properties[i]; 73 | if (!o.type.createDeclaration) { 74 | if (k++ !== 0) 75 | result += ", "; 76 | result += o.builtin + " " + o.name + ":" + o.type; 77 | } 78 | } 79 | return result; 80 | } 81 | getInputFromOutput() { 82 | if (this.name != "Output") 83 | return null; 84 | return new ShaderStruct("Input", this.properties.slice(1)); 85 | } 86 | get struct() { 87 | let result = "struct " + this.name + " {\n"; 88 | let o; 89 | for (let i = 0; i < this.properties.length; i++) { 90 | o = this.properties[i]; 91 | if (this.isShaderIO) { 92 | if (i > 0) 93 | o.builtin = "@location(" + (i - 1) + ")"; 94 | //console.log(o.name + " , i = ", i, " location = ", o.builtin, " -- ", o.builtin.length) 95 | result += " " + o.builtin + " " + o.name + ":" + o.type + ",\n"; 96 | } 97 | else { 98 | if (undefined !== o.size) 99 | result += " " + "@size(" + o.size + ") @align(16) " + o.name + ":" + o.type + ",\n"; 100 | else 101 | result += " " + " " + o.name + ":" + o.type + ",\n"; 102 | } 103 | } 104 | result += "}\n\n"; 105 | /* 106 | const varName = this.name.substring(0, 1).toLowerCase() + this.name.slice(1); 107 | for (let i = 0; i < this.properties.length; i++) { 108 | o = this.properties[i]; 109 | if (o.obj) result += o.obj.createVariable(varName) + "\n"; 110 | } 111 | */ 112 | return result; 113 | } 114 | } 115 | -------------------------------------------------------------------------------- /dist/xgpu_pipeline_resources.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/tlecoz/XGPU/b2230801e3a9370f23b496986420a236eded31d3/dist/xgpu_pipeline_resources.jpg -------------------------------------------------------------------------------- /githubPush.js: -------------------------------------------------------------------------------- 1 | import { execSync } from 'child_process'; 2 | 3 | // Vérifiez si un argument a été fourni 4 | if (process.argv.length !== 3) { 5 | console.log("Usage: npm run push -- commit_message"); 6 | process.exit(1); 7 | } 8 | 9 | const commitMessage = process.argv[2]; 10 | 11 | // Exécutez vos commandes 12 | execSync('node set_xgpu_prod.js', { stdio: 'inherit' }); 13 | execSync('git add .', { stdio: 'inherit' }); 14 | execSync(`git commit -m "${commitMessage}"`, { stdio: 'inherit' }); 15 | execSync('git push', { stdio: 'inherit' }); 16 | execSync('node set_xgpu_dev.js', { stdio: 'inherit' }); -------------------------------------------------------------------------------- /index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | Vite + TS 9 | 16 | 17 | 18 | 19 |
20 | 21 | 22 | -------------------------------------------------------------------------------- /package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "xgpu", 3 | "version": "0.9.25", 4 | "description": "XGPU is an extendable library for WebGPU that provides a higher-level, easy-to-use interface for building rendering engines or processing numeric data. It handles automatic data binding, buffer alignment, variable declarations in shaders, and more. XGPU is focused solely on WebGPU, allowing you to produce code that is easy to read, write, maintain, and reuse.", 5 | "repository": { 6 | "type": "git", 7 | "url": "https://github.com/tlecoz/XGPU" 8 | }, 9 | "keywords": [ 10 | "WebGPU", 11 | "GPU", 12 | "shader", 13 | "computeShader", 14 | "wgpu-matrix", 15 | "webgpu", 16 | "wgpu", 17 | "typescript" 18 | ], 19 | "files": [ 20 | "dist/**/*.js", 21 | "dist/**/*.d.ts", 22 | "dist/documentation.json" 23 | ], 24 | "author": "Thomas Le Coz ", 25 | "licence": "MIT", 26 | "homepage": "https://github.com/tlecoz/XGPU#readme", 27 | "main": "dist/XGPU.js", 28 | "types": "dist/index.d.ts", 29 | "type": "module", 30 | "scripts": { 31 | "dev": "vite", 32 | "build:test": "tsc --project tsconfig_build.json --emitDeclarationOnly", 33 | "build:types": "tsc --project tsconfig_build.json", 34 | "build": "vite build && npm run build:types && npx tsjsondoc ./src ./dist", 35 | "doc": "node updateDoc.js", 36 | "push": "node githubPush.js", 37 | "publish": "node publish.js" 38 | }, 39 | "devDependencies": { 40 | "@webgpu/types": "^0.1.26", 41 | "cross-spawn": "^7.0.3", 42 | "postcss": ">=8.4.31", 43 | "rimraf": "^5.0.0", 44 | "tsjsondoc": "^1.2.9", 45 | "typedoc": "^0.24.8", 46 | "typedoc-plugin-markdown": "^3.15.4", 47 | "typescript": "^4.6.4", 48 | "vite": "^5.3.1", 49 | "vite-plugin-checker": "^0.6.4", 50 | "vite-plugin-external": "^1.2.8" 51 | }, 52 | "dependencies": { 53 | "@types/dom-webcodecs": "^0.1.7", 54 | "@webgpu/types": "^0.1.31", 55 | "gl-matrix": "^3.4.3" 56 | } 57 | } -------------------------------------------------------------------------------- /public/samples.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/tlecoz/XGPU/b2230801e3a9370f23b496986420a236eded31d3/public/samples.jpg -------------------------------------------------------------------------------- /public/xgpu_pipeline_resources.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/tlecoz/XGPU/b2230801e3a9370f23b496986420a236eded31d3/public/xgpu_pipeline_resources.jpg -------------------------------------------------------------------------------- /publish.js: -------------------------------------------------------------------------------- 1 | import { execSync } from 'child_process'; 2 | 3 | // Exécutez vos commandes 4 | execSync('node set_xgpu_prod.js', { stdio: 'inherit' }); 5 | execSync('vite build', { stdio: 'inherit' }); 6 | execSync('tsc --project tsconfig_build.json', { stdio: 'inherit' }); 7 | execSync('npx tsjsondoc ./src ./dist', { stdio: 'inherit' }); 8 | execSync('npm publish', { stdio: 'inherit' }); 9 | execSync('node set_xgpu_dev.js', { stdio: 'inherit' }); -------------------------------------------------------------------------------- /set_xgpu_dev.js: -------------------------------------------------------------------------------- 1 | import fs from 'fs'; 2 | import path from 'path'; 3 | import { fileURLToPath, pathToFileURL } from 'url'; 4 | 5 | // Obtenir le chemin du module actuel 6 | const currentDir = path.dirname(fileURLToPath(import.meta.url)); 7 | 8 | // Chemin vers le projet xgpu 9 | const XGPU_PATH = path.join(currentDir, './'); 10 | const PACKAGE_JSON_PATH = pathToFileURL(path.join(XGPU_PATH, 'package.json')).href; 11 | 12 | // Lire le package.json de xgpu de manière synchrone 13 | const packageJsonData = fs.readFileSync(fileURLToPath(PACKAGE_JSON_PATH), 'utf-8'); 14 | const packageJson = JSON.parse(packageJsonData); 15 | 16 | 17 | // Modifier les champs nécessaires 18 | packageJson.main = "src/index.ts"; 19 | packageJson.types = "src/index.ts"; 20 | 21 | // Écrire les modifications dans le package.json de xgpu 22 | fs.writeFileSync(fileURLToPath(PACKAGE_JSON_PATH), JSON.stringify(packageJson, null, 2)); 23 | -------------------------------------------------------------------------------- /set_xgpu_prod.js: -------------------------------------------------------------------------------- 1 | import fs from 'fs'; 2 | import path from 'path'; 3 | import { fileURLToPath, pathToFileURL } from 'url'; 4 | 5 | // Obtenir le chemin du module actuel 6 | const currentDir = path.dirname(fileURLToPath(import.meta.url)); 7 | 8 | // Chemin vers le projet xgpu 9 | const XGPU_PATH = path.join(currentDir, './'); 10 | const PACKAGE_JSON_PATH = pathToFileURL(path.join(XGPU_PATH, 'package.json')).href; 11 | 12 | // Lire le package.json de xgpu de manière synchrone 13 | const packageJsonData = fs.readFileSync(fileURLToPath(PACKAGE_JSON_PATH), 'utf-8'); 14 | const packageJson = JSON.parse(packageJsonData); 15 | 16 | 17 | // Modifier les champs nécessaires 18 | packageJson.main = "dist/XGPU.js"; 19 | packageJson.types = "dist/index.d.ts"; 20 | 21 | // Écrire les modifications dans le package.json de xgpu 22 | fs.writeFileSync(fileURLToPath(PACKAGE_JSON_PATH), JSON.stringify(packageJson, null, 2)); 23 | -------------------------------------------------------------------------------- /src/index.ts: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2023 Thomas Le Coz. All rights reserved. 2 | // This code is governed by an MIT license that can be found in the LICENSE file. 3 | 4 | export * from "./xGPU/XGPU" 5 | export * from "./xGPU/EventDispatcher" 6 | export * from "./xGPU/IRenderer" 7 | export * from "./xGPU/GPURenderer" 8 | //export * from "./xGPU/GPURendererV2" 9 | export * from "./xGPU/TextureRenderer" 10 | export * from "./xGPU/GPUType" 11 | export * from "./xGPU/BuiltIns" 12 | export * from "./xGPU/PrimitiveType" 13 | export * from "./xGPU/blendmodes/AlphaBlendMode" 14 | export * from "./xGPU/blendmodes/BlendMode" 15 | 16 | 17 | 18 | export * from "./xGPU/pipelines/Pipeline" 19 | export * from "./xGPU/pipelines/RenderPipeline" 20 | export * from "./xGPU/pipelines/ComputePipeline" 21 | export * from "./xGPU/pipelines/VertexShaderDebuggerPipeline" 22 | export * from "./xGPU/pipelines/resources/IndexBuffer" 23 | 24 | 25 | export * from "./xGPU/pipelines/resources/textures/Texture" 26 | export * from "./xGPU/pipelines/resources/textures/DepthStencilTexture" 27 | export * from "./xGPU/pipelines/resources/textures/MultiSampleTexture" 28 | 29 | export * from "./xGPU/pipelines/PipelinePlugin" 30 | 31 | export * from "./xGPU/shader/Bindgroup" 32 | export * from "./xGPU/shader/Bindgroups" 33 | export * from "./xGPU/shader/ComputeShader" 34 | export * from "./xGPU/shader/FragmentShader" 35 | 36 | export * from "./xGPU/shader/ShaderType" 37 | export * from "./xGPU/shader/VertexShader" 38 | 39 | export * from "./xGPU/shader/shaderParts/ShaderNode" 40 | export * from "./xGPU/shader/shaderParts/ShaderStage" 41 | export * from "./xGPU/shader/shaderParts/ShaderStruct" 42 | 43 | export * from "./xGPU/shader/resources/IShaderResource" 44 | export * from "./xGPU/shader/resources/CubeMapTexture" 45 | export * from "./xGPU/shader/resources/ImageTexture" 46 | export * from "./xGPU/shader/resources/ImageTextureArray" 47 | export * from "./xGPU/pipelines/resources/textures/DepthTextureArray" 48 | export * from "./xGPU/shader/resources/ImageTextureIO" 49 | export * from "./xGPU/shader/resources/TextureSampler" 50 | export * from "./xGPU/shader/resources/UniformBuffer" 51 | export * from "./xGPU/shader/resources/UniformGroup" 52 | export * from "./xGPU/shader/resources/UniformGroupArray" 53 | export * from "./xGPU/shader/resources/VertexAttribute" 54 | export * from "./xGPU/shader/resources/VertexBuffer" 55 | export * from "./xGPU/shader/resources/VertexBufferIO" 56 | export * from "./xGPU/shader/resources/VideoTexture" 57 | export * from "./xGPU/pipelines/resources/textures/RenderPassTexture" 58 | 59 | export * from "./xGPU/shader/resources/attributes/FloatBuffer" 60 | export * from "./xGPU/shader/resources/attributes/Vec2Buffer" 61 | export * from "./xGPU/shader/resources/attributes/Vec3Buffer" 62 | export * from "./xGPU/shader/resources/attributes/Vec4Buffer" 63 | 64 | export * from "./xGPU/shader/resources/attributes/IntBuffer" 65 | export * from "./xGPU/shader/resources/attributes/IVec2Buffer" 66 | export * from "./xGPU/shader/resources/attributes/IVec3Buffer" 67 | export * from "./xGPU/shader/resources/attributes/IVec4Buffer" 68 | 69 | export * from "./xGPU/shader/resources/attributes/UintBuffer" 70 | export * from "./xGPU/shader/resources/attributes/UVec2Buffer" 71 | export * from "./xGPU/shader/resources/attributes/UVec3Buffer" 72 | export * from "./xGPU/shader/resources/attributes/UVec4Buffer" 73 | 74 | export * from "./xGPU/HighLevelParser" 75 | 76 | 77 | 78 | 79 | -------------------------------------------------------------------------------- /src/vite-env.d.ts: -------------------------------------------------------------------------------- 1 | /// 2 | -------------------------------------------------------------------------------- /src/xGPU/EventDispatcher.ts: -------------------------------------------------------------------------------- 1 | 2 | 3 | export class EventDispatcher { 4 | 5 | protected eventListeners: any = {}; 6 | 7 | constructor() { 8 | 9 | } 10 | 11 | public addEventListener(eventName: string, callback: ( data?: any) => void, removeListenerAfterDispatch: boolean = false) { 12 | if (!this.eventListeners[eventName]) this.eventListeners[eventName] = []; 13 | if (removeListenerAfterDispatch) (callback as any).removeAfter = true; 14 | this.eventListeners[eventName].push(callback); 15 | } 16 | public removeEventListener(eventName: string, callback: (dispatcher: EventDispatcher, data?: any) => void) { 17 | if (this.eventListeners[eventName]) { 18 | const id = this.eventListeners[eventName].indexOf(callback); 19 | if (id != -1) { 20 | this.eventListeners[eventName].splice(id, 1); 21 | } 22 | } 23 | } 24 | public clearEvents(eventName) { 25 | this.addEventListener[eventName] = []; 26 | } 27 | public hasEventListener(eventName): boolean { return !!this.eventListeners[eventName] } 28 | 29 | public dispatchEvent(eventName: string, eventData?: any) { 30 | if (this.eventListeners[eventName]) { 31 | 32 | const t = [...this.eventListeners[eventName]]; 33 | t.forEach(callback => { 34 | callback( eventData); 35 | if ((callback as any).removeAfter) this.removeEventListener(eventName, callback); 36 | }); 37 | } 38 | } 39 | } -------------------------------------------------------------------------------- /src/xGPU/IRenderer.ts: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2023 Thomas Le Coz. All rights reserved. 2 | // This code is governed by an MIT license that can be found in the LICENSE file. 3 | 4 | import { RenderPipeline } from "./pipelines/RenderPipeline"; 5 | 6 | export interface IRenderer { 7 | 8 | addPipeline(pipeline: RenderPipeline, offset?: number): void; 9 | resize(w: number, h: number); 10 | destroy(): void; 11 | update(): void; 12 | 13 | get renderPipelines(): RenderPipeline[]; 14 | get canvas(): HTMLCanvasElement; 15 | get resized(): boolean; 16 | get width(): number; 17 | get height(): number; 18 | get texture(): GPUTexture; 19 | get view(): GPUTextureView; 20 | get frameId(): number; 21 | get commandEncoder(): GPUCommandEncoder; 22 | 23 | } -------------------------------------------------------------------------------- /src/xGPU/WebGPUProperties.ts: -------------------------------------------------------------------------------- 1 | export class WebGPUProperties { 2 | 3 | private static build(obj: any, currentId: number, currentNames: string[]) { 4 | 5 | let infoById = {}; 6 | let processedIds = new Set(); 7 | let stack = [{ id: currentId, names: currentNames }]; 8 | while (stack.length > 0) { 9 | let current = stack.pop(); 10 | let currentId = current.id; 11 | let currentNames = current.names; 12 | if (processedIds.has(currentId)) continue; 13 | 14 | for (let name in obj) { 15 | let id = obj[name]; 16 | let combinedId = currentId | id; 17 | let combinedNames = [...new Set(currentNames.concat(name))]; 18 | 19 | if (!(combinedId in infoById)) { 20 | infoById[combinedId] = combinedNames; 21 | stack.push({ id: combinedId, names: combinedNames }); 22 | } else { 23 | infoById[combinedId] = [...new Set(infoById[combinedId].concat(combinedNames))]; 24 | } 25 | } 26 | processedIds.add(currentId); 27 | } 28 | return infoById; 29 | } 30 | 31 | private static resolve(obj: any, id: number) { 32 | if (id in obj) return obj[id].join("|"); 33 | return "undefined" 34 | } 35 | 36 | private static async getResult(WebGpuObject: any): Promise { 37 | return new Promise((resolve) => { 38 | const result = this.build(WebGpuObject, 0, []) 39 | setTimeout(() => { 40 | //i make a pause to unblock the thread 41 | resolve(result); 42 | }, 1) 43 | }); 44 | } 45 | private static ready: boolean = false; 46 | private static textureUsage: any; 47 | private static bufferUsage: any; 48 | private static shaderStage: any; 49 | 50 | public static async init(): Promise { 51 | if (!this._instance) new WebGPUProperties(); 52 | return new Promise(async (resolve) => { 53 | if (this.ready) resolve(); 54 | else { 55 | this.bufferUsage = await this.getResult(GPUBufferUsage); 56 | this.shaderStage = await this.getResult(GPUShaderStage); 57 | this.textureUsage = await this.getResult(GPUTextureUsage); 58 | this.ready = true; 59 | resolve(); 60 | } 61 | }); 62 | } 63 | 64 | private static _instance: WebGPUProperties; 65 | constructor() { 66 | if (WebGPUProperties._instance) { 67 | throw new Error("WebGPUProperties is not instanciable"); 68 | } 69 | WebGPUProperties._instance = this; 70 | } 71 | 72 | 73 | 74 | public static getTextureUsageById(id: number): string { 75 | return this.resolve(this.textureUsage, id); 76 | } 77 | 78 | public static getBufferUsageById(id: number): string { 79 | return this.resolve(this.bufferUsage, id); 80 | } 81 | 82 | public static getShaderStageById(id: number): string { 83 | return this.resolve(this.shaderStage, id); 84 | } 85 | } 86 | 87 | -------------------------------------------------------------------------------- /src/xGPU/blendmodes/AlphaBlendMode.ts: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2023 Thomas Le Coz. All rights reserved. 2 | // This code is governed by an MIT license that can be found in the LICENSE file. 3 | 4 | import { BlendMode } from "./BlendMode"; 5 | 6 | export class AlphaBlendMode extends BlendMode { 7 | 8 | constructor() { 9 | super(); 10 | 11 | this.color.operation = "add"; 12 | this.color.srcFactor = "src-alpha"; 13 | this.color.dstFactor = "one-minus-src-alpha"; 14 | 15 | this.alpha.operation = "add"; 16 | this.alpha.srcFactor = "src-alpha"; 17 | this.alpha.dstFactor = "one-minus-src-alpha"; 18 | } 19 | 20 | } -------------------------------------------------------------------------------- /src/xGPU/blendmodes/BlendMode.ts: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2023 Thomas Le Coz. All rights reserved. 2 | // This code is governed by an MIT license that can be found in the LICENSE file. 3 | 4 | export abstract class BlendMode { 5 | 6 | public color: { 7 | operation: "add" | "subtract" | "reverse-subtract" | "min" | "max", 8 | srcFactor: "zero" | "one" | "src" | "one-minus-src" | "src-alpha" | "one-minus-src-alpha" | "dst" | "one-minus-dst" | "one-minus-dst-alpha" | "src-alpha-saturated" | "constant" | "one-minus-constant", 9 | dstFactor: "zero" | "one" | "src" | "one-minus-src" | "src-alpha" | "one-minus-src-alpha" | "dst" | "one-minus-dst" | "one-minus-dst-alpha" | "src-alpha-saturated" | "constant" | "one-minus-constant", 10 | } = { operation: "add", srcFactor: "one", dstFactor: "zero" } 11 | 12 | public alpha: { 13 | operation: "add" | "subtract" | "reverse-subtract" | "min" | "max", 14 | srcFactor: "zero" | "one" | "src" | "one-minus-src" | "src-alpha" | "one-minus-src-alpha" | "dst" | "one-minus-dst" | "one-minus-dst-alpha" | "src-alpha-saturated" | "constant" | "one-minus-constant", 15 | dstFactor: "zero" | "one" | "src" | "one-minus-src" | "src-alpha" | "one-minus-src-alpha" | "dst" | "one-minus-dst" | "one-minus-dst-alpha" | "src-alpha-saturated" | "constant" | "one-minus-constant", 16 | } = { operation: "add", srcFactor: "one", dstFactor: "zero" } 17 | 18 | constructor() { 19 | 20 | } 21 | } -------------------------------------------------------------------------------- /src/xGPU/pipelines/PipelinePlugin.ts: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2023 Thomas Le Coz. All rights reserved. 2 | // This code is governed by an MIT license that can be found in the LICENSE file. 3 | 4 | import { ShaderNode } from "../shader/shaderParts/ShaderNode"; 5 | import { Pipeline } from "./Pipeline"; 6 | 7 | export class PipelinePlugin { 8 | 9 | protected target: Pipeline; 10 | protected requiredNames: any; 11 | 12 | public bindgroupResources: any = {}; 13 | 14 | 15 | 16 | public vertexShader: { 17 | outputs?: any, 18 | inputs?: any, 19 | constants?: string, 20 | main?: string | string[], 21 | } = {}; 22 | 23 | public fragmentShader: { 24 | outputs?: any, 25 | inputs?: any, 26 | constants?: string, 27 | main?: string | string[], 28 | } = {}; 29 | 30 | constructor(target: Pipeline, required?: any) { 31 | this.target = target; 32 | 33 | if (required) { 34 | this.requiredNames = {}; 35 | for (let z in required) { 36 | this.requiredNames[z] = target.getResourceName(required[z]); 37 | } 38 | } 39 | 40 | } 41 | 42 | public apply(vertexShaderNode: ShaderNode = null, fragmentShaderNode: ShaderNode = null): PipelinePlugin { 43 | 44 | 45 | 46 | //if (!this.target.resources.bindgroups.plugins) this.target.resources.bindgroups.plugins = {}; 47 | //const plugins = this.target.resources.bindgroups.plugins; 48 | let plugins; 49 | for (let z in this.target.resources.bindgroups) { 50 | plugins = this.target.resources.bindgroups[z]; 51 | break; 52 | } 53 | 54 | 55 | for (let z in this.bindgroupResources) plugins[z] = this.bindgroupResources[z]; 56 | 57 | 58 | 59 | //------ VERTEX SHADER -------- 60 | 61 | 62 | 63 | let vs = this.target.resources.vertexShader; 64 | if (typeof vs === "string") vs = { main: vs } 65 | 66 | if (this.vertexShader.outputs) { 67 | if (!vs.outputs) vs.outputs = {}; 68 | for (let z in this.vertexShader.outputs) { 69 | vs.outputs[z] = this.vertexShader.outputs[z]; 70 | } 71 | } 72 | 73 | if (this.vertexShader.inputs) { 74 | if (!vs.inputs) vs.inputs = {}; 75 | for (let z in this.vertexShader.inputs) { 76 | vs.inputs[z] = this.vertexShader.inputs[z]; 77 | } 78 | } 79 | 80 | if (this.vertexShader.constants) { 81 | if (!vs.constants) vs.constants = ""; 82 | vs.constants += this.vertexShader.constants; 83 | } 84 | 85 | if (this.vertexShader.main) { 86 | let main: string; 87 | if (typeof this.vertexShader.main === "string") main = this.vertexShader.main as string; 88 | else main = (this.vertexShader.main as string[]).join("\n"); 89 | 90 | if (vertexShaderNode) vertexShaderNode.text = main; 91 | else { 92 | if (!vs.main) vs.main = ""; 93 | vs.main += main; 94 | } 95 | } 96 | this.target.resources.vertexShader = vs; 97 | 98 | //-------- FRAGMENT SHADER -------- 99 | let fs = this.target.resources.fragmentShader; 100 | if (typeof fs === "string") fs = { main: fs }; 101 | 102 | if (this.fragmentShader.outputs) { 103 | if (!fs.outputs) fs.outputs = {}; 104 | for (let z in this.fragmentShader.outputs) { 105 | fs.outputs[z] = this.fragmentShader.outputs[z]; 106 | } 107 | } 108 | 109 | if (this.fragmentShader.inputs) { 110 | if (!fs.inputs) fs.inputs = {}; 111 | for (let z in this.fragmentShader.inputs) { 112 | fs.inputs[z] = this.fragmentShader.inputs[z]; 113 | } 114 | } 115 | 116 | if (this.fragmentShader.constants) { 117 | if (!fs.constants) fs.constants = ""; 118 | fs.constants += this.fragmentShader.constants; 119 | } 120 | 121 | if (this.fragmentShader.main) { 122 | let main: string; 123 | if (typeof this.fragmentShader.main === "string") main = this.fragmentShader.main as string; 124 | else main = (this.fragmentShader.main as string[]).join("\n"); 125 | 126 | if (fragmentShaderNode) fragmentShaderNode.text = main; 127 | else { 128 | if (!fs.main) fs.main = ""; 129 | fs.main += main; 130 | } 131 | } 132 | this.target.resources.fragmentShader = fs; 133 | 134 | this.target.initFromObject(this.target.resources); 135 | 136 | return this; 137 | } 138 | 139 | 140 | 141 | } -------------------------------------------------------------------------------- /src/xGPU/pipelines/resources/DrawConfig.ts: -------------------------------------------------------------------------------- 1 | import { RenderPipeline } from "../RenderPipeline"; 2 | import { IndexBuffer } from "./IndexBuffer"; 3 | 4 | export class DrawConfig { 5 | 6 | public vertexCount: number = -1; 7 | public instanceCount: number = 1; 8 | public firstVertexId: number = 0; 9 | public firstInstanceId: number = 0; 10 | public baseVertex: number = 0; 11 | public indexBuffer: IndexBuffer; 12 | 13 | protected pipeline: RenderPipeline; 14 | protected setupDrawCompleted: boolean = false; 15 | 16 | constructor(renderPipeline: RenderPipeline) { 17 | this.pipeline = renderPipeline; 18 | } 19 | 20 | public draw(renderPass: GPURenderPassEncoder) { 21 | //console.log("DrawConfig.draw") 22 | if (this.indexBuffer) { 23 | //console.log(this.indexBuffer.nbPoint, this.instanceCount, this.firstVertexId, this.baseVertex, this.firstInstanceId) 24 | renderPass.setIndexBuffer(this.indexBuffer.gpuResource, this.indexBuffer.dataType, this.indexBuffer.offset, this.indexBuffer.getBufferSize()) 25 | renderPass.drawIndexed(this.indexBuffer.nbPoint, this.instanceCount, this.firstVertexId, this.baseVertex, this.firstInstanceId); 26 | } else { 27 | renderPass.draw(this.vertexCount, this.instanceCount, this.firstVertexId, this.firstInstanceId); 28 | } 29 | } 30 | 31 | 32 | 33 | 34 | 35 | } -------------------------------------------------------------------------------- /src/xGPU/pipelines/resources/textures/DepthTextureArray.ts: -------------------------------------------------------------------------------- 1 | import { ImageTextureArray } from "../../../shader/resources/ImageTextureArray"; 2 | import { DepthStencilTexture } from "./DepthStencilTexture"; 3 | 4 | export class DepthTextureArray extends ImageTextureArray { 5 | 6 | private _description: { depthWriteEnabled: boolean, depthCompare: string, format: string, sampleCount?: number }; 7 | public get description(): { depthWriteEnabled: boolean, depthCompare: string, format: string, sampleCount?: number } { return this._description; } 8 | 9 | private _attachment: any; 10 | public get attachment(): any { return this._attachment }; 11 | 12 | constructor(descriptor: { 13 | source: DepthStencilTexture[] | GPUTexture[], 14 | size: GPUExtent3D, 15 | format?: "stencil8" | "depth16unorm" | "depth24plus" | "depth24plus-stencil8" | "depth32float", 16 | usage?: GPUTextureUsageFlags, 17 | sampleCount?: number, 18 | }, depthStencilDescription: { 19 | depthWriteEnabled: boolean, 20 | depthCompare: "never" | "less" | "equal" | "less-equal" | "greater" | "not-equal" | "greater-equal" | "always", 21 | } = null) { 22 | 23 | if (undefined === descriptor.format) descriptor.format = "depth32float"; 24 | if (undefined === descriptor.sampleCount) descriptor.sampleCount = 1; 25 | 26 | 27 | if (descriptor.source[0] instanceof DepthStencilTexture) { 28 | for (let i = 0; i < descriptor.source.length; i++) { 29 | descriptor.source[i] = (descriptor.source[i] as DepthStencilTexture).gpuResource as GPUTexture; 30 | } 31 | } 32 | 33 | if (undefined === descriptor.usage) { 34 | descriptor.usage = (descriptor.source[0] as GPUTexture).usage; 35 | } 36 | 37 | 38 | super(descriptor as any); 39 | 40 | //-------- 41 | if (!depthStencilDescription) { 42 | depthStencilDescription = { 43 | depthWriteEnabled: true, 44 | depthCompare: "less", 45 | format: this.gpuResource.format 46 | 47 | } as any 48 | } 49 | this._description = { format: this.gpuResource.format, ...depthStencilDescription }; 50 | 51 | } 52 | 53 | 54 | protected _visibility: GPUShaderStageFlags = GPUShaderStage.FRAGMENT; 55 | 56 | public setPipelineType(pipelineType: "compute" | "render" | "compute_mixed") { 57 | if (pipelineType === "render") this._visibility = GPUShaderStage.FRAGMENT; 58 | else if (pipelineType === "compute_mixed") this._visibility = GPUShaderStage.FRAGMENT | GPUShaderStage.COMPUTE; 59 | else if (pipelineType === "compute") this._visibility = GPUShaderStage.COMPUTE; 60 | } 61 | 62 | 63 | public createBindGroupLayoutEntry(bindingId: number): { binding: number, visibility: number, texture: GPUTextureBindingLayout } { 64 | 65 | let sampleType: GPUTextureSampleType = "float"; 66 | if (this.sampledType === "i32") sampleType = "sint"; 67 | else if (this.sampledType === "u32") sampleType = "uint"; 68 | 69 | return { 70 | binding: bindingId, 71 | visibility: this._visibility, 72 | texture: { 73 | sampleType, 74 | viewDimension: "2d-array", 75 | multisampled: false 76 | }, 77 | } 78 | } 79 | 80 | public get isDepthTexture(): boolean { return true; } 81 | 82 | public createDeclaration(varName: string, bindingId: number, groupId: number): string { 83 | return "@binding(" + bindingId + ") @group(" + groupId + ") var " + varName + ":texture_depth_2d_array;\n"; 84 | } 85 | 86 | 87 | } -------------------------------------------------------------------------------- /src/xGPU/pipelines/resources/textures/MultiSampleTexture.ts: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2023 Thomas Le Coz. All rights reserved. 2 | // This code is governed by an MIT license that can be found in the LICENSE file. 3 | 4 | import { XGPU } from "../../../XGPU"; 5 | import { Texture, TextureDescriptor } from "./Texture"; 6 | 7 | export type MultiSampleTextureDescriptor = { 8 | size: GPUExtent3D, 9 | format?: GPUTextureFormat, 10 | usage?: GPUTextureUsageFlags, 11 | sampleCount?: GPUSize32, 12 | alphaToCoverageEnabled?: boolean, 13 | mask?: number, 14 | resolveTarget?: GPUTextureView 15 | } 16 | 17 | export class MultiSampleTexture extends Texture { 18 | 19 | private _description: { count: number, mask: number, alphaToCoverageEnabled: boolean }; 20 | public get description(): { count: number, mask: number, alphaToCoverageEnabled: boolean } { return this._description } 21 | 22 | constructor(descriptor: { 23 | size: GPUExtent3D, 24 | format?: GPUTextureFormat, 25 | usage?: GPUTextureUsageFlags, 26 | sampleCount?: GPUSize32, 27 | alphaToCoverageEnabled?: boolean, 28 | mask?: number, 29 | resolveTarget?: GPUTextureView 30 | }) { 31 | 32 | if (undefined === descriptor.format) descriptor.format = XGPU.getPreferredCanvasFormat(); 33 | if (undefined === descriptor.usage) descriptor.usage = GPUTextureUsage.RENDER_ATTACHMENT; 34 | if (undefined === descriptor.sampleCount) descriptor.sampleCount = 4; 35 | if (undefined === descriptor.alphaToCoverageEnabled) descriptor.alphaToCoverageEnabled = false; 36 | if (undefined === descriptor.mask) descriptor.mask = 0xFFFFFFFF; 37 | if (undefined === descriptor.resolveTarget) descriptor.resolveTarget = null; 38 | 39 | super(descriptor as TextureDescriptor); 40 | 41 | this._description = { 42 | count: descriptor.sampleCount, 43 | mask: descriptor.mask, 44 | alphaToCoverageEnabled: descriptor.alphaToCoverageEnabled 45 | } 46 | } 47 | 48 | public create(): void { 49 | super.create(); 50 | } 51 | 52 | public get resolveTarget(): any { return (this.descriptor as MultiSampleTextureDescriptor).resolveTarget } 53 | 54 | 55 | 56 | } -------------------------------------------------------------------------------- /src/xGPU/pipelines/resources/textures/Texture.ts: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2023 Thomas Le Coz. All rights reserved. 2 | // This code is governed by an MIT license that can be found in the LICENSE file. 3 | 4 | import { EventDispatcher } from "../../../EventDispatcher"; 5 | import { XGPU } from "../../../XGPU"; 6 | 7 | export type TextureDescriptor = { 8 | size: GPUExtent3D, 9 | format: GPUTextureFormat, 10 | usage?: GPUTextureUsageFlags, 11 | sampleCount?: GPUSize32, 12 | label?: string, 13 | } 14 | 15 | export class Texture extends EventDispatcher { 16 | 17 | public descriptor: TextureDescriptor; 18 | public gpuResource: GPUTexture = null; 19 | protected _view: GPUTextureView = null; 20 | 21 | constructor(descriptor: { 22 | size: GPUExtent3D, 23 | format: GPUTextureFormat, 24 | usage?: GPUTextureUsageFlags, 25 | sampleCount?: GPUSize32, 26 | label?: string 27 | }) { 28 | 29 | super(); 30 | //console.log(descriptor.format + " ::: " + descriptor.usage) 31 | if (undefined === descriptor.usage) descriptor.usage = GPUTextureUsage.RENDER_ATTACHMENT; 32 | if (undefined === descriptor.sampleCount && descriptor.format !== "depth32float") descriptor.sampleCount = 1; 33 | if (undefined === descriptor.label) descriptor.label = "Texture"; 34 | this.descriptor = descriptor; 35 | 36 | } 37 | public get sampleCount(): number { return this.descriptor.sampleCount } 38 | public get format(): any { return this.descriptor.format } 39 | public get size(): GPUExtent3D { return this.descriptor.size } 40 | public get usage(): number { return this.descriptor.usage } 41 | public get view(): GPUTextureView { 42 | 43 | if (!this._view) this.create(); 44 | return this._view; 45 | } 46 | 47 | public destroy(): void { 48 | if (this.gpuResource) { 49 | (this.gpuResource as any).xgpuObject = null; 50 | this.gpuResource.destroy(); 51 | } 52 | this.gpuResource = null; 53 | this._view = null; 54 | } 55 | 56 | protected deviceId: number; 57 | public time: number; 58 | public create(): void { 59 | 60 | /*if (this.time && new Date().getTime() - this.time < 100 && XGPU.loseDeviceRecently) { 61 | return; 62 | }*/ 63 | this.time = new Date().getTime(); 64 | 65 | 66 | if (XGPU.loseDeviceRecently && this.deviceId === XGPU.deviceId) return 67 | 68 | if (this.gpuResource) { 69 | (this.gpuResource as any).xgpuObject = null; 70 | this.gpuResource.destroy(); 71 | } 72 | //console.warn("createTexture ", this.deviceId) 73 | 74 | 75 | 76 | this.deviceId = XGPU.deviceId; 77 | this.gpuResource = XGPU.device.createTexture(this.descriptor as GPUTextureDescriptor); 78 | (this.gpuResource as any).xgpuObject = this; 79 | this.createView(); 80 | } 81 | 82 | 83 | public createGpuResource(): void { 84 | this.create(); 85 | } 86 | 87 | public update() { 88 | if (this.deviceId !== XGPU.deviceId) { 89 | 90 | this.create(); 91 | 92 | } 93 | } 94 | 95 | private createView(): void { 96 | if (!this.gpuResource) this.create(); 97 | this._view = this.gpuResource.createView(); 98 | //(this._view as any).texture = this; 99 | } 100 | 101 | public resize(width: number, height: number): void { 102 | this.descriptor.size = [width, height]; 103 | this.create(); 104 | } 105 | 106 | 107 | } -------------------------------------------------------------------------------- /src/xGPU/shader/ComputeShader.ts: -------------------------------------------------------------------------------- 1 | 2 | // Copyright (c) 2023 Thomas Le Coz. All rights reserved. 3 | // This code is governed by an MIT license that can be found in the LICENSE file. 4 | 5 | import { XGPU } from "../XGPU"; 6 | import { ComputePipeline } from "../pipelines/ComputePipeline"; 7 | import { ShaderStage } from "./shaderParts/ShaderStage"; 8 | import { ShaderStruct } from "./shaderParts/ShaderStruct"; 9 | 10 | 11 | export class ComputeShader extends ShaderStage { 12 | 13 | 14 | 15 | constructor() { 16 | super("compute"); 17 | 18 | } 19 | 20 | public build(shaderPipeline: ComputePipeline, inputs: ShaderStruct): { code: string, output: ShaderStruct } { 21 | 22 | if (this._shaderInfos) return this._shaderInfos; 23 | 24 | 25 | 26 | let result = ""; 27 | const obj = shaderPipeline.bindGroups.getComputeShaderDeclaration(); 28 | result += obj.result + "\n\n"; 29 | 30 | 31 | //------ 32 | 33 | const w = shaderPipeline.workgroups; 34 | 35 | //this.unwrapVariableInMainFunction(obj.variables)//handleVariables(); 36 | let constants = this.unwrapVariableInWGSL(obj.variables, this.constants.value); 37 | result += constants + "\n\n"; 38 | 39 | 40 | let mainFunc = this.unwrapVariableInWGSL(obj.variables, this.main.value); 41 | 42 | result += "@compute @workgroup_size(" + w[0] + "," + w[1] + "," + w[2] + ")\n"; 43 | result += "fn main(" + inputs.getFunctionParams() + ") {\n"; 44 | //result += obj.variables + "\n"; 45 | //result += this.main.value; 46 | result += mainFunc; 47 | result += "}\n"; 48 | 49 | 50 | 51 | this._shaderInfos = { code: result, output: null }; 52 | 53 | if (XGPU.showComputeShader) { 54 | setTimeout(()=>{ 55 | console.log("------------- COMPUTE SHADER --------------") 56 | 57 | console.log(this.formatWGSLCode(this._shaderInfos.code)); 58 | //console.log(formated) 59 | console.log("-------------------------------------------") 60 | },100) 61 | 62 | } 63 | 64 | return this._shaderInfos; 65 | 66 | 67 | 68 | 69 | } 70 | 71 | 72 | public static removeStructDefinitionAndReplaceStructDeclarationName(shaderCode: string, structName: string, newStructName: string): string { 73 | // Expression régulière pour capturer la définition complète de la structure `structName` 74 | const structRegex = new RegExp(`struct\\s+${structName}\\s*\\{[^}]*\\}`, 'g'); 75 | 76 | // Supprimer la définition de `structName` 77 | shaderCode = shaderCode.replace(structRegex, ''); 78 | 79 | // Remplacer toutes les occurrences de `structName` par `newStructName` 80 | const nameRegex = new RegExp(`\\b${structName}\\b`, 'g'); 81 | shaderCode = shaderCode.replace(nameRegex, newStructName); 82 | 83 | return shaderCode; 84 | } 85 | 86 | 87 | 88 | 89 | 90 | } -------------------------------------------------------------------------------- /src/xGPU/shader/FragmentShader.ts: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2023 Thomas Le Coz. All rights reserved. 2 | // This code is governed by an MIT license that can be found in the LICENSE file. 3 | 4 | import { BuiltIns } from "../BuiltIns"; 5 | import { XGPU } from "../XGPU"; 6 | import { ShaderStage } from "./shaderParts/ShaderStage"; 7 | import { ShaderStruct } from "./shaderParts/ShaderStruct"; 8 | 9 | export class FragmentShader extends ShaderStage { 10 | 11 | 12 | 13 | constructor() { 14 | super("fragment"); 15 | } 16 | 17 | public build(shaderPipeline: any, inputs: ShaderStruct): { code: string, output: ShaderStruct } { 18 | if (this._shaderInfos) return this._shaderInfos; 19 | 20 | 21 | 22 | 23 | 24 | let result = ""; 25 | const obj = shaderPipeline.bindGroups.getVertexShaderDeclaration(true); 26 | result += obj.result; 27 | 28 | //console.log("-------- FRAGMENT -----------"); 29 | //console.log(result) 30 | 31 | for (let i = 0; i < this.inputs.length; i++) { 32 | inputs.addProperty(this.inputs[i]); 33 | } 34 | 35 | if (this.outputs.length === 0) { 36 | this.outputs[0] = { name: "color", ...BuiltIns.fragmentOutputs.color } 37 | } 38 | const output: ShaderStruct = new ShaderStruct("Output", this.outputs); 39 | result += output.struct + "\n" 40 | 41 | 42 | 43 | //------ 44 | 45 | //const mainFunc = this.unwrapVariableInMainFunction(obj.variables)//handleVariables(); 46 | let constants = this.unwrapVariableInWGSL(obj.variables, this.constants.value); 47 | result += constants + "\n\n"; 48 | 49 | 50 | let mainFunc = this.unwrapVariableInWGSL(obj.variables, this.main.value); 51 | 52 | result += "@fragment\n"; 53 | result += "fn main(" + inputs.getFunctionParams() + ") -> " + output.name + "{\n"; 54 | //result += obj.variables + "\n"; 55 | result += " var output:Output;\n"; 56 | //result += this.main.value; 57 | result += mainFunc; 58 | result += " return output;\n" 59 | result += "}\n"; 60 | 61 | result = this.formatWGSLCode(result) 62 | 63 | if (XGPU.showFragmentShader) { 64 | console.log("------------- FRAGMENT SHADER --------------") 65 | console.log(result) 66 | console.log("--------------------------------------------") 67 | } 68 | 69 | 70 | this._shaderInfos = { code: result, output: output }; 71 | 72 | return this._shaderInfos; 73 | } 74 | } -------------------------------------------------------------------------------- /src/xGPU/shader/ShaderType.ts: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2023 Thomas Le Coz. All rights reserved. 2 | // This code is governed by an MIT license that can be found in the LICENSE file. 3 | 4 | export class ShaderType { 5 | 6 | public static Float = { type: "f32" }; 7 | public static Vec2 = { type: "vec2" }; 8 | public static Vec3 = { type: "vec3" }; 9 | public static Vec4 = { type: "vec4" }; 10 | 11 | public static Int = { type: "i32" }; 12 | public static IVec2 = { type: "vec2" }; 13 | public static IVec3 = { type: "vec3" }; 14 | public static IVec4 = { type: "vec4" }; 15 | 16 | public static Uint = { type: "u32" }; 17 | public static UVec2 = { type: "vec2" }; 18 | public static UVec3 = { type: "vec3" }; 19 | public static UVec4 = { type: "vec4" }; 20 | 21 | } -------------------------------------------------------------------------------- /src/xGPU/shader/VertexShader.ts: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2023 Thomas Le Coz. All rights reserved. 2 | // This code is governed by an MIT license that can be found in the LICENSE file. 3 | 4 | import { BuiltIns } from "../BuiltIns"; 5 | import { XGPU } from "../XGPU"; 6 | import { RenderPipeline } from "../pipelines/RenderPipeline"; 7 | import { ShaderStage } from "./shaderParts/ShaderStage"; 8 | import { ShaderStruct } from "./shaderParts/ShaderStruct"; 9 | 10 | 11 | export class VertexShader extends ShaderStage { 12 | 13 | //public keepRendererAspectRatio: boolean = true; 14 | 15 | constructor() { 16 | super("vertex"); 17 | } 18 | 19 | 20 | 21 | 22 | public build(pipeline: RenderPipeline, input: ShaderStruct): { code: string, output: ShaderStruct } { 23 | 24 | //this.main.text = this.extractDebugInfo(this.main.text); 25 | 26 | let result = "" 27 | //if (this.keepRendererAspectRatio) result += "const xgpuRendererAspectRatio = " + (pipeline.renderer.width / pipeline.renderer.height).toFixed(4) + ";\n\n"; 28 | const obj = pipeline.bindGroups.getVertexShaderDeclaration(); 29 | result += obj.result; 30 | 31 | //----- 32 | //if the renderPipeline is "fed" by a computePipeline, the shaderStruct "input" 33 | //contains the output vertexBuffer from the computePipeline 34 | result += input.getComputeVariableDeclaration(); 35 | 36 | //----- 37 | 38 | let bool = false; 39 | for (let i = 0; i < this.outputs.length; i++) { 40 | if (this.outputs[i].builtin === BuiltIns.vertexOutputs.position.builtin) { 41 | bool = true; 42 | } 43 | } 44 | if (!bool) { 45 | 46 | 47 | this.outputs.unshift({ name: "position", ...BuiltIns.vertexOutputs.position }); 48 | } 49 | 50 | 51 | let output: ShaderStruct = new ShaderStruct("Output", [...this.outputs]); 52 | result += output.struct + "\n" 53 | 54 | 55 | 56 | //let mainFunc = this.unwrapVariableInMainFunction(obj.variables)//handleVariables(); 57 | let constants = this.unwrapVariableInWGSL(obj.variables, this.constants.value); 58 | result += constants + "\n\n"; 59 | 60 | 61 | let mainFunc = this.unwrapVariableInWGSL(obj.variables, this.main.value); 62 | 63 | 64 | //------ 65 | //console.log("VertexShader.variables = ", obj.variables) 66 | result += "@vertex\n"; 67 | result += "fn main(" + input.getFunctionParams() + ") -> " + output.name + "{\n"; 68 | result += " var output:Output;\n"; 69 | result += mainFunc; 70 | result += " return output;\n" 71 | result += "}\n"; 72 | 73 | result = this.formatWGSLCode(result) 74 | 75 | if (XGPU.showVertexShader) { 76 | 77 | console.log("------------- VERTEX SHADER --------------") 78 | console.log(result); 79 | console.log("------------------------------------------") 80 | } 81 | 82 | this._shaderInfos = { code: result, output: output }; 83 | 84 | 85 | return this._shaderInfos; 86 | } 87 | } -------------------------------------------------------------------------------- /src/xGPU/shader/resources/IShaderResource.ts: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2023 Thomas Le Coz. All rights reserved. 2 | // This code is governed by an MIT license that can be found in the LICENSE file. 3 | 4 | import { Pipeline } from "../../pipelines/Pipeline"; 5 | 6 | export interface IShaderResource { 7 | 8 | mustBeTransfered: boolean; 9 | gpuResource: any; 10 | descriptor: any; 11 | 12 | setPipelineType(pipelineType: "compute" | "render" | "compute_mixed"); //used to handle particular cases in descriptor relative to the nature of pipeline 13 | 14 | createDeclaration(varName: string, bindingId: number, groupId: number): string; 15 | createBindGroupLayoutEntry(bindingId: number): any; 16 | createBindGroupEntry(bindingId: number): any; 17 | 18 | createGpuResource(); 19 | destroyGpuResource(); 20 | update(pipeline?: Pipeline); 21 | 22 | clone(): IShaderResource; 23 | 24 | } -------------------------------------------------------------------------------- /src/xGPU/shader/resources/StageableBuffer.ts: -------------------------------------------------------------------------------- 1 | import { EventDispatcher } from "../../EventDispatcher"; 2 | import { XGPU } from "../../XGPU"; 3 | 4 | export class StageableBuffer extends EventDispatcher { 5 | 6 | public static ON_OUTPUT_DATA:string = "ON_OUTPUT_DATA"; 7 | public static ON_OUTPUT_PROCESS_START:string = "ON_OUTPUT_PROCESS_START"; 8 | public onOutputData:((data:ArrayBuffer)=>void)|null = null; 9 | 10 | 11 | constructor(){ 12 | super(); 13 | } 14 | 15 | 16 | protected stagingBuffer:GPUBuffer; 17 | protected canCallMapAsync:boolean = true; 18 | public onCanCallMapAsync:(()=>void)|null = null; 19 | 20 | 21 | public get mustOutputData():boolean{ 22 | return !!this.onOutputData || this.hasEventListener(StageableBuffer.ON_OUTPUT_DATA) 23 | } 24 | 25 | public async getOutputData(buffer:GPUBuffer){ 26 | if(!this.onOutputData && !this.hasEventListener(StageableBuffer.ON_OUTPUT_DATA)) return; 27 | 28 | 29 | if (!this.canCallMapAsync){ 30 | //console.warn("the last call of 'getOutputData' is not completed yet. You must wait 'ON_OUTPUT_DATA' to call computePipeline.nextFrame()" ) 31 | return 32 | } 33 | 34 | this.dispatchEvent(StageableBuffer.ON_OUTPUT_PROCESS_START) 35 | this.canCallMapAsync = false; 36 | //const buffer:GPUBuffer = this.gpuResource; 37 | 38 | //console.log("getOutputData ",buffer.size+" vs "+this.bufferSize); 39 | 40 | if (!this.stagingBuffer || buffer.size != this.stagingBuffer.size) this.stagingBuffer = XGPU.createStagingBuffer(buffer.size); 41 | const copyEncoder = XGPU.device.createCommandEncoder(); 42 | const stage = this.stagingBuffer; 43 | 44 | copyEncoder.copyBufferToBuffer(buffer, 0, stage, 0, stage.size); 45 | XGPU.device.queue.submit([copyEncoder.finish()]); 46 | 47 | await this.stagingBuffer.mapAsync(GPUMapMode.READ, 0, stage.size) 48 | 49 | const copyArray = stage.getMappedRange(0, stage.size); 50 | const data = copyArray.slice(0); 51 | stage.unmap(); 52 | this.canCallMapAsync = true; 53 | if(this.onCanCallMapAsync) this.onCanCallMapAsync(); 54 | 55 | this.dispatchEvent(StageableBuffer.ON_OUTPUT_DATA,data); 56 | if(this.onOutputData) this.onOutputData(data); 57 | 58 | } 59 | 60 | } -------------------------------------------------------------------------------- /src/xGPU/shader/resources/attributes/FloatBuffer.ts: -------------------------------------------------------------------------------- 1 | import { VertexAttribute } from "../VertexAttribute"; 2 | 3 | export class FloatBuffer extends VertexAttribute { 4 | 5 | constructor(datas?: number[][] | number[] | number, offset?: number) { 6 | 7 | if (datas != undefined && offset === undefined) { 8 | if (typeof datas === "number") { 9 | offset = datas; 10 | datas = undefined; 11 | } 12 | } 13 | 14 | super("", "float32", offset) 15 | if (typeof (datas) != "number") this.datas = datas; 16 | } 17 | } -------------------------------------------------------------------------------- /src/xGPU/shader/resources/attributes/IVec2Buffer.ts: -------------------------------------------------------------------------------- 1 | import { VertexAttribute } from "../VertexAttribute"; 2 | 3 | export class IVec2Buffer extends VertexAttribute { 4 | 5 | constructor(datas?: number[][] | number[] | number, offset?: number) { 6 | 7 | if (datas != undefined && offset === undefined) { 8 | if (typeof datas === "number") { 9 | offset = datas; 10 | datas = undefined; 11 | } 12 | } 13 | 14 | super("", "sint32x2", offset) 15 | if (typeof (datas) != "number") this.datas = datas; 16 | } 17 | } -------------------------------------------------------------------------------- /src/xGPU/shader/resources/attributes/IVec3Buffer.ts: -------------------------------------------------------------------------------- 1 | import { VertexAttribute } from "../VertexAttribute"; 2 | 3 | export class IVec3Buffer extends VertexAttribute { 4 | 5 | constructor(datas?: number[][] | number[] | number, offset?: number) { 6 | 7 | if (datas != undefined && offset === undefined) { 8 | if (typeof datas === "number") { 9 | offset = datas; 10 | datas = undefined; 11 | } 12 | } 13 | 14 | super("", "sint32x3", offset) 15 | if (typeof (datas) != "number") this.datas = datas; 16 | } 17 | } -------------------------------------------------------------------------------- /src/xGPU/shader/resources/attributes/IVec4Buffer.ts: -------------------------------------------------------------------------------- 1 | import { VertexAttribute } from "../VertexAttribute"; 2 | 3 | export class IVec4Buffer extends VertexAttribute { 4 | 5 | constructor(datas?: number[][] | number[] | number, offset?: number) { 6 | 7 | if (datas != undefined && offset === undefined) { 8 | if (typeof datas === "number") { 9 | offset = datas; 10 | datas = undefined; 11 | } 12 | } 13 | 14 | super("", "sint32x4", offset) 15 | if (typeof (datas) != "number") this.datas = datas; 16 | } 17 | } -------------------------------------------------------------------------------- /src/xGPU/shader/resources/attributes/IntBuffer.ts: -------------------------------------------------------------------------------- 1 | import { VertexAttribute } from "../VertexAttribute"; 2 | 3 | export class IntBuffer extends VertexAttribute { 4 | 5 | constructor(datas?: number[][] | number[] | number, offset?: number) { 6 | 7 | if (datas != undefined && offset === undefined) { 8 | if (typeof datas === "number") { 9 | offset = datas; 10 | datas = undefined; 11 | } 12 | } 13 | 14 | super("", "sint32", offset) 15 | if (typeof (datas) != "number") this.datas = datas; 16 | } 17 | } -------------------------------------------------------------------------------- /src/xGPU/shader/resources/attributes/UVec2Buffer.ts: -------------------------------------------------------------------------------- 1 | import { VertexAttribute } from "../VertexAttribute"; 2 | 3 | export class UVec2Buffer extends VertexAttribute { 4 | 5 | constructor(datas?: number[][] | number[] | number, offset?: number) { 6 | 7 | if (datas != undefined && offset === undefined) { 8 | if (typeof datas === "number") { 9 | offset = datas; 10 | datas = undefined; 11 | } 12 | } 13 | 14 | super("", "uint32x2", offset) 15 | if (typeof (datas) != "number") this.datas = datas; 16 | } 17 | } -------------------------------------------------------------------------------- /src/xGPU/shader/resources/attributes/UVec3Buffer.ts: -------------------------------------------------------------------------------- 1 | import { VertexAttribute } from "../VertexAttribute"; 2 | 3 | export class UVec3Buffer extends VertexAttribute { 4 | 5 | constructor(datas?: number[][] | number[] | number, offset?: number) { 6 | 7 | if (datas != undefined && offset === undefined) { 8 | if (typeof datas === "number") { 9 | offset = datas; 10 | datas = undefined; 11 | } 12 | } 13 | 14 | super("", "uint32x3", offset) 15 | if (typeof (datas) != "number") this.datas = datas; 16 | } 17 | } -------------------------------------------------------------------------------- /src/xGPU/shader/resources/attributes/UVec4Buffer.ts: -------------------------------------------------------------------------------- 1 | import { VertexAttribute } from "../VertexAttribute"; 2 | 3 | export class UVec4Buffer extends VertexAttribute { 4 | 5 | constructor(datas?: number[][] | number[] | number, offset?: number) { 6 | 7 | if (datas != undefined && offset === undefined) { 8 | if (typeof datas === "number") { 9 | offset = datas; 10 | datas = undefined; 11 | } 12 | } 13 | 14 | super("", "uint32x4", offset) 15 | if (typeof (datas) != "number") this.datas = datas; 16 | } 17 | } -------------------------------------------------------------------------------- /src/xGPU/shader/resources/attributes/UintBuffer.ts: -------------------------------------------------------------------------------- 1 | import { VertexAttribute } from "../VertexAttribute"; 2 | 3 | export class UintBuffer extends VertexAttribute { 4 | 5 | constructor(datas?: number[][] | number[] | number, offset?: number) { 6 | 7 | if (datas != undefined && offset === undefined) { 8 | if (typeof datas === "number") { 9 | offset = datas; 10 | datas = undefined; 11 | } 12 | } 13 | 14 | super("", "uint32", offset) 15 | if (typeof (datas) != "number") this.datas = datas; 16 | } 17 | } -------------------------------------------------------------------------------- /src/xGPU/shader/resources/attributes/Vec2Buffer.ts: -------------------------------------------------------------------------------- 1 | import { VertexAttribute } from "../VertexAttribute"; 2 | 3 | export class Vec2Buffer extends VertexAttribute { 4 | 5 | 6 | constructor(datas?: number[][] | number[] | number, offset?: number) { 7 | 8 | if (datas != undefined && offset === undefined) { 9 | if (typeof datas === "number") { 10 | offset = datas; 11 | datas = undefined; 12 | } 13 | } 14 | 15 | //console.log("Vec2Buffer ", offset) 16 | 17 | super("", "float32x2", offset) 18 | //console.log("Vec2Buffer.dataOffset = ", this.dataOffset) 19 | if (typeof (datas) != "number") { 20 | this.datas = datas; 21 | } 22 | 23 | } 24 | 25 | 26 | } -------------------------------------------------------------------------------- /src/xGPU/shader/resources/attributes/Vec3Buffer.ts: -------------------------------------------------------------------------------- 1 | import { VertexAttribute } from "../VertexAttribute"; 2 | 3 | export class Vec3Buffer extends VertexAttribute { 4 | 5 | 6 | constructor(datas?: number[][] | number[] | number, offset?: number) { 7 | 8 | if (datas != undefined && offset === undefined) { 9 | if (typeof datas === "number") { 10 | offset = datas; 11 | datas = undefined; 12 | } 13 | } 14 | 15 | super("", "float32x3", offset) 16 | 17 | if (typeof (datas) != "number") { 18 | this.datas = datas; 19 | } 20 | 21 | } 22 | 23 | 24 | } -------------------------------------------------------------------------------- /src/xGPU/shader/resources/attributes/Vec4Buffer.ts: -------------------------------------------------------------------------------- 1 | import { VertexAttribute } from "../VertexAttribute"; 2 | 3 | export class Vec4Buffer extends VertexAttribute { 4 | 5 | 6 | constructor(datas?: number[][] | number[] | number, offset?: number) { 7 | 8 | if (datas != undefined && offset === undefined) { 9 | if (typeof datas === "number") { 10 | offset = datas; 11 | datas = undefined; 12 | } 13 | } 14 | 15 | super("", "float32x4", offset) 16 | 17 | if (typeof (datas) != "number") { 18 | this.datas = datas; 19 | } 20 | 21 | } 22 | 23 | 24 | } -------------------------------------------------------------------------------- /src/xGPU/shader/shaderParts/ShaderNode.ts: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2023 Thomas Le Coz. All rights reserved. 2 | // This code is governed by an MIT license that can be found in the LICENSE file. 3 | 4 | export class ShaderNode { 5 | 6 | public enabled: boolean = true; 7 | public executeSubNodeAfterCode: boolean = true; 8 | 9 | 10 | private _text: string; 11 | private insideMainFunction: boolean; 12 | 13 | private _nodeByName:{[key:string]:ShaderNode} = {}; 14 | public get nodeByName():{[key:string]:ShaderNode}{ 15 | return this._nodeByName; 16 | } 17 | 18 | 19 | private subNodes: ShaderNode[]; 20 | 21 | constructor(code: string = "", insideMainFunction: boolean = false) { 22 | this.text = code; 23 | this.insideMainFunction = insideMainFunction; 24 | } 25 | 26 | 27 | public get text(): string { return this._text } 28 | public set text(s: string) { 29 | 30 | //--------- remove useless tabulations while keeping tabs structure ------- 31 | 32 | const lines = s.split("\n"); 33 | let line; 34 | let nbTabMin = 99999999; 35 | 36 | if (lines.length > 1) { 37 | for (let i = 0; i < lines.length; i++) { 38 | line = lines[i]; 39 | for (let j = 0; j < line.length; j++) { 40 | if (line[j] === "\n") continue; 41 | if (line[j] !== " ") { 42 | if (nbTabMin > j) nbTabMin = j; 43 | break; 44 | } 45 | } 46 | } 47 | 48 | if (this.insideMainFunction && nbTabMin >= 3) nbTabMin -= 3; 49 | for (let i = 0; i < lines.length; i++) { 50 | lines[i] = lines[i].slice(nbTabMin); 51 | } 52 | 53 | s = lines.join("\n"); 54 | } 55 | //----------------------------------------------------------------------- 56 | 57 | this._text = s; 58 | } 59 | 60 | public replaceValues(values: { old: string, new: string }[]) { 61 | for (let i = 0; i < values.length; i++) { 62 | this.replaceKeyWord(values[i].old, values[i].new); 63 | //this._text = this._text.replace(values[i].old, values[i].new); 64 | } 65 | } 66 | 67 | public replaceKeyWord(wordToReplace: string, replacement: string) { 68 | const regex = new RegExp(`(?<=[^\\w.])\\b${wordToReplace}\\b`, 'g'); 69 | this._text = this._text.replace(regex, replacement); 70 | } 71 | 72 | 73 | 74 | public get value(): string { 75 | 76 | let result = ""; 77 | 78 | if (this.executeSubNodeAfterCode) { 79 | 80 | result += this.text + "\n"; 81 | } 82 | if (this.subNodes) { 83 | for (let i = 0; i < this.subNodes.length; i++) { 84 | result += this.subNodes[i].value + "\n"; 85 | } 86 | } 87 | 88 | if (!this.executeSubNodeAfterCode) result += this.text + "\n"; 89 | 90 | 91 | //console.log(this.text + " vs " + result) 92 | return result; 93 | } 94 | 95 | public createNode(code: string = ""): ShaderNode { 96 | const node = new ShaderNode(code); 97 | if (!this.subNodes) this.subNodes = []; 98 | this.subNodes.push(node); 99 | return node; 100 | } 101 | 102 | public addNode(nodeName:string,code:string=""):ShaderNode{ 103 | const node = this.createNode(code); 104 | this._nodeByName[nodeName] = node; 105 | return node; 106 | } 107 | 108 | 109 | 110 | } -------------------------------------------------------------------------------- /tsconfig.json: -------------------------------------------------------------------------------- 1 | { 2 | "compilerOptions": { 3 | "target": "ESNext", 4 | "useDefineForClassFields": true, 5 | "module": "ESNext", 6 | "lib": [ 7 | "ESNext", 8 | "DOM" 9 | ], 10 | "outDir": "dist", 11 | "rootDir": "src", 12 | "declaration": true, 13 | "declarationDir": "dist", 14 | "moduleResolution": "Node", 15 | "strict": false, 16 | "resolveJsonModule": true, 17 | "isolatedModules": true, 18 | "esModuleInterop": true, 19 | "noEmit": false, 20 | "noUnusedLocals": true, 21 | "noUnusedParameters": true, 22 | "noImplicitReturns": true, 23 | "skipLibCheck": true, 24 | "typeRoots": [ 25 | "./node_modules/@webgpu/types", 26 | "./node_modules/@types" 27 | ] 28 | }, 29 | "include": [ 30 | "src", 31 | "index.ts" 32 | ], 33 | } -------------------------------------------------------------------------------- /tsconfig_build.json: -------------------------------------------------------------------------------- 1 | { 2 | "compilerOptions": { 3 | "target": "ESNext", 4 | "useDefineForClassFields": true, 5 | "module": "ESNext", 6 | "lib": [ 7 | "ESNext", 8 | "DOM" 9 | ], 10 | "outDir": "dist", 11 | "rootDir": "src", 12 | "declaration": true, 13 | "declarationDir": "dist", 14 | "moduleResolution": "Node", 15 | "strict": false, 16 | "resolveJsonModule": true, 17 | "isolatedModules": true, 18 | "esModuleInterop": true, 19 | "noEmit": false, 20 | "noUnusedLocals": true, 21 | "noUnusedParameters": true, 22 | "noImplicitReturns": true, 23 | "skipLibCheck": true, 24 | "typeRoots": [ 25 | "./node_modules/@webgpu/types", 26 | "./node_modules/@types" 27 | ] 28 | }, 29 | "include": [ 30 | "src/**/*.ts" 31 | ], 32 | "exclude": [ 33 | "src/main.ts" 34 | ] 35 | } -------------------------------------------------------------------------------- /typedoc.json: -------------------------------------------------------------------------------- 1 | { 2 | "entryPoints": [ 3 | "src/xGPU/**/*.ts" 4 | ], 5 | "exclude": [ 6 | "**/samples/**/*" 7 | ] 8 | } -------------------------------------------------------------------------------- /updateDoc.js: -------------------------------------------------------------------------------- 1 | import { execSync } from 'child_process'; 2 | 3 | //update package.json and define 'main' entry to 'dist/index.ts' 4 | execSync('node set_xgpu_prod.js', { stdio: 'inherit' }); 5 | 6 | //build xgpu and update 'dist' 7 | execSync('vite build && tsc --project tsconfig_build.json', { stdio: 'inherit' }); 8 | 9 | //generate the documentation in ../xgpu-documentation/src 10 | execSync('npx tsjsondoc ./src ../xgpu-documentation/src/', { stdio: 'inherit' }); 11 | 12 | //update back package.json and set 'main' to 'src/index.ts' so I can use locally synchronously with xgpu-samples 13 | execSync('node set_xgpu_dev.js', { stdio: 'inherit' }); 14 | 15 | try { 16 | console.log("Trying to push..."); 17 | execSync('cd ../xgpu-documentation && git add . && git commit -m "update documentation" && git push', { stdio: 'inherit' }); 18 | 19 | console.log("documentation correctly updated on github & netlify"); 20 | } catch (error) { 21 | console.error('Error during github push', error); 22 | //get current branch name 23 | const branchName = execSync("cd ../xgpu-documentation && git rev-parse --abbrev-ref HEAD", { encoding: 'utf8' }).trim(); 24 | //go back to the state of xgpu-documentation at the last successfull push 25 | execSync(`cd ../xgpu-documentation && git fetch origin && git reset --hard origin/${branchName}`, { stdio: 'inherit' }); 26 | } 27 | 28 | -------------------------------------------------------------------------------- /vite.config.js: -------------------------------------------------------------------------------- 1 | // vite.config.js 2 | import { defineConfig } from 'vite' 3 | 4 | export default defineConfig({ 5 | 6 | 7 | build: { 8 | //minify: false, 9 | lib: { 10 | // Could also be a dictionary or array of multiple entry points 11 | entry: 'src/index.ts', 12 | name: 'xGPU', 13 | // the proper extensions will be added 14 | fileName: 'XGPU', 15 | }, 16 | 17 | 18 | rollupOptions: { 19 | // make sure to externalize deps that shouldn't be bundled 20 | // into your library 21 | external: ['gl-matrix'], 22 | output: { 23 | // Provide global variables to use in the UMD build 24 | // for externalized deps 25 | globals: { 26 | glMatrix: 'glMatrix', 27 | }, 28 | }, 29 | }, 30 | 31 | }, 32 | }) -------------------------------------------------------------------------------- /xgpu-0.9.23.tgz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/tlecoz/XGPU/b2230801e3a9370f23b496986420a236eded31d3/xgpu-0.9.23.tgz --------------------------------------------------------------------------------