Skip to content

Commit 421913c

Browse files
author
Mike Solomon
committed
Modifies example
1 parent d71df4f commit 421913c

File tree

5 files changed

+115
-45
lines changed

5 files changed

+115
-45
lines changed

package.json

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@
55
"main": "index.js",
66
"scripts": {
77
"sandbox": "spago -x sandbox.dhall build && vite build sandbox/",
8+
"sandbox-dev": "spago -x sandbox-dev.dhall build && vite dev sandbox/",
89
"format": "purs-tidy format-in-place \"src/**/*.purs sandbox/**/*.purs\" && prettier --write \"src/**/*.js\""
910
},
1011
"keywords": [],

sandbox-dev.dhall

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,6 @@
1+
let conf = ./spago.dhall
2+
3+
in conf
4+
// { sources = conf.sources # [ "sandbox/**/*.purs" ]
5+
, dependencies = conf.dependencies # [ "aff", "aff-promise", "arraybuffer", "control", "float32", "foldable-traversable", "uint", "web-dom" ]
6+
}

sandbox/Sandbox.purs

Lines changed: 83 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -13,17 +13,23 @@ import Data.Float32 (fromNumber')
1313
import Data.Foldable (traverse_)
1414
import Data.Int (toNumber)
1515
import Data.Int.Bits (complement, (.&.))
16+
import Data.JSDate (getTime, now)
1617
import Data.Maybe (Maybe(..), maybe)
18+
import Data.Number (pi, sin)
1719
import Data.UInt (fromInt)
1820
import Effect (Effect)
1921
import Effect.Aff (error, launchAff_, throwError)
2022
import Effect.Class (liftEffect)
2123
import Unsafe.Coerce (unsafeCoerce)
2224
import Web.DOM.Element (setAttribute)
2325
import Web.DOM.NonElementParentNode (getElementById)
26+
import Web.GPU.BufferSource (fromFloat32Array)
2427
import Web.GPU.GPU (requestAdapter)
2528
import Web.GPU.GPUAdapter (requestDevice)
29+
import Web.GPU.GPUBindGroupEntry (GPUBufferBinding, gpuBindGroupEntry)
30+
import Web.GPU.GPUBindGroupLayoutEntry (gpuBindGroupLayoutEntry)
2631
import Web.GPU.GPUBuffer (GPUBuffer, getMappedRange, unmap)
32+
import Web.GPU.GPUBufferBindingLayout (GPUBufferBindingLayout)
2733
import Web.GPU.GPUBufferUsage (GPUBufferUsageFlags)
2834
import Web.GPU.GPUBufferUsage as GPUBufferUsage
2935
import Web.GPU.GPUCanvasAlphaMode (opaque)
@@ -35,7 +41,7 @@ import Web.GPU.GPUCommandEncoder (beginRenderPass, finish)
3541
import Web.GPU.GPUCompareFunction as GPUCompareFunction
3642
import Web.GPU.GPUCullMode (none)
3743
import Web.GPU.GPUDepthStencilState (GPUDepthStencilState)
38-
import Web.GPU.GPUDevice (createBuffer, createCommandEncoder, createPipelineLayout, createRenderPipeline, createShaderModule, createTexture)
44+
import Web.GPU.GPUDevice (createBuffer, createBindGroupLayout, createBindGroup, createCommandEncoder, createPipelineLayout, createRenderPipeline, createShaderModule, createTexture)
3945
import Web.GPU.GPUDevice as GPUDevice
4046
import Web.GPU.GPUExtent3D (gpuExtent3DWHD)
4147
import Web.GPU.GPUFragmentState (GPUFragmentState)
@@ -44,12 +50,13 @@ import Web.GPU.GPUIndexFormat (uint16)
4450
import Web.GPU.GPULoadOp as GPULoadOp
4551
import Web.GPU.GPUPrimitiveState (GPUPrimitiveState)
4652
import Web.GPU.GPUPrimitiveTopology (triangleList)
47-
import Web.GPU.GPUQueue (submit)
53+
import Web.GPU.GPUQueue (submit, writeBuffer)
4854
import Web.GPU.GPURenderPassColorAttachment (GPURenderPassColorAttachment)
4955
import Web.GPU.GPURenderPassDepthStencilAttachment (GPURenderPassDepthStencilAttachment)
5056
import Web.GPU.GPURenderPassDescriptor (GPURenderPassDescriptor)
51-
import Web.GPU.GPURenderPassEncoder (drawIndexedWithInstanceCount, end, setIndexBuffer, setPipeline, setScissorRect, setVertexBuffer, setViewport)
57+
import Web.GPU.GPURenderPassEncoder (drawIndexedWithInstanceCount, end, setBindGroup, setIndexBuffer, setPipeline, setScissorRect, setVertexBuffer, setViewport)
5258
import Web.GPU.GPURenderPipelineDescriptor (GPURenderPipelineDescriptor)
59+
import Web.GPU.GPUShaderStage as GPUShaderStage
5360
import Web.GPU.GPUStoreOp as GPUStoreOp
5461
import Web.GPU.GPUTexture (createView)
5562
import Web.GPU.GPUTextureDescriptor (GPUTextureDescriptor)
@@ -111,6 +118,42 @@ main = do
111118
, 1.0
112119
-- 🔵
113120
]
121+
let
122+
makeUniformData yScale = do
123+
uniformData :: Float32Array <- fromArray $ map fromNumber'
124+
[
125+
-- ♟️ ModelViewProjection Matrix (Identity)
126+
1.0
127+
, 0.0
128+
, 0.0
129+
, 0.0
130+
, 0.0
131+
, 1.0 * yScale
132+
, 0.0
133+
, 0.0
134+
, 0.0
135+
, 0.0
136+
, 1.0
137+
, 0.0
138+
, 0.0
139+
, 0.0
140+
, 0.0
141+
, 1.0
142+
,
143+
-- 🔴 Primary Color
144+
0.9
145+
, 0.1
146+
, 0.3
147+
, 1.0
148+
,
149+
-- 🟣 Accent Color
150+
0.8
151+
, 0.2
152+
, 0.8
153+
, 1.0
154+
]
155+
pure uniformData
156+
uniformData <- makeUniformData 1.0
114157
-- 📇 Index Buffer Data
115158
indices :: Uint16Array <- fromArray $ map fromInt [ 0, 1, 2 ]
116159
-- 🏭 Entry to WebGPU
@@ -156,22 +199,36 @@ main = do
156199
positionBuffer <- liftEffect $ createBufferF positions GPUBufferUsage.vertex
157200
colorBuffer <- liftEffect $ createBufferF colors GPUBufferUsage.vertex
158201
indexBuffer <- liftEffect $ createBufferF indices GPUBufferUsage.index
202+
-- ✋ Declare buffer handles
203+
204+
uniformBuffer <- liftEffect $ createBufferF uniformData
205+
(GPUBufferUsage.uniform .|. GPUBufferUsage.copyDst)
206+
159207
-- 🖍️ Shaders
160208
let
161209
vsmDesc =
162210
x
163211
{ code:
164212
"""
213+
struct UBO {
214+
modelViewProj: mat4x4<f32>,
215+
primaryColor: vec4<f32>,
216+
accentColor: vec4<f32>
217+
};
218+
165219
struct VSOut {
166220
@builtin(position) Position: vec4<f32>,
167221
@location(0) color: vec3<f32>,
168222
};
169223
224+
@group(0) @binding(0)
225+
var<uniform> uniforms: UBO;
226+
170227
@vertex
171228
fn main(@location(0) inPos: vec3<f32>,
172229
@location(1) inColor: vec3<f32>) -> VSOut {
173230
var vsOut: VSOut;
174-
vsOut.Position = vec4<f32>(inPos, 1.0);
231+
vsOut.Position = uniforms.modelViewProj * vec4<f32>(inPos, 1.0);
175232
vsOut.color = inColor;
176233
return vsOut;
177234
}
@@ -231,8 +288,24 @@ fn main(@location(0) inColor: vec3<f32>) -> @location(0) vec4<f32> {
231288
, depthCompare: GPUCompareFunction.less
232289
}
233290

291+
uniformBindGroupLayout <- liftEffect $ createBindGroupLayout device $ x
292+
{ entries:
293+
[ gpuBindGroupLayoutEntry 0 GPUShaderStage.vertex
294+
(x {} :: GPUBufferBindingLayout)
295+
]
296+
}
297+
298+
-- 🗄️ Bind Group
299+
-- ✍ This would be used when *encoding commands*
300+
uniformBindGroup <- liftEffect $ createBindGroup device $ x
301+
{ layout: uniformBindGroupLayout
302+
, entries:
303+
[ gpuBindGroupEntry 0
304+
(x { buffer: uniformBuffer } :: GPUBufferBinding)
305+
]
306+
}
234307
-- 🦄 Uniform Data
235-
let pipelineLayoutDesc = x { bindGroupLayouts: [] }
308+
let pipelineLayoutDesc = x { bindGroupLayouts: [ uniformBindGroupLayout ] }
236309
layout <- liftEffect $ createPipelineLayout device pipelineLayoutDesc
237310

238311
-- 🎭 Shader Stages
@@ -354,6 +427,11 @@ fn main(@location(0) inColor: vec3<f32>) -> @location(0) vec4<f32> {
354427
setVertexBuffer passEncoder 0 positionBuffer
355428
setVertexBuffer passEncoder 1 colorBuffer
356429
setIndexBuffer passEncoder indexBuffer uint16
430+
tn <- getTime <$> now
431+
let y = sin (tn * 0.001 * pi) * 0.4 + 0.6
432+
newBuffer <- makeUniformData y
433+
writeBuffer queue uniformBuffer 0 (fromFloat32Array newBuffer)
434+
setBindGroup passEncoder 0 uniformBindGroup
357435
drawIndexedWithInstanceCount passEncoder 3 1
358436
end passEncoder
359437
toSubmit <- finish commandEncoder

sandbox/index.js

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,2 +1,2 @@
1-
import { main } from "../output-es/Sandbox"
1+
import { main } from "../output/Sandbox" // find way to do vite alias on windows, seems broken...
22
main();

src/Web/GPU/GPUBindGroupLayoutEntry.purs

Lines changed: 24 additions & 39 deletions
Original file line numberDiff line numberDiff line change
@@ -15,42 +15,27 @@ import Web.GPU.GPUTextureBindingLayout (GPUTextureBindingLayout)
1515
import Web.GPU.Internal.Types (GPUIndex32)
1616

1717
data GPUBindGroupLayoutEntry
18-
gpuBufferBindingLayout
19-
:: GPUIndex32
20-
-> GPUShaderStageFlags
21-
-> GPUBufferBindingLayout
22-
-> GPUBindGroupLayoutEntry
23-
gpuBufferBindingLayout binding visibility buffer = unsafeCoerce
24-
{ binding, visibility, buffer }
25-
26-
gpuSamplerBindingLayout
27-
:: GPUIndex32
28-
-> GPUShaderStageFlags
29-
-> GPUSamplerBindingLayout
30-
-> GPUBindGroupLayoutEntry
31-
gpuSamplerBindingLayout binding visibility sampler = unsafeCoerce
32-
{ binding, visibility, sampler }
33-
34-
gpuTextureBindingLayout
35-
:: GPUIndex32
36-
-> GPUShaderStageFlags
37-
-> GPUTextureBindingLayout
38-
-> GPUBindGroupLayoutEntry
39-
gpuTextureBindingLayout binding visibility texture = unsafeCoerce
40-
{ binding, visibility, texture }
41-
42-
gpuStorageTextureBindingLayout
43-
:: GPUIndex32
44-
-> GPUShaderStageFlags
45-
-> GPUStorageTextureBindingLayout
46-
-> GPUBindGroupLayoutEntry
47-
gpuStorageTextureBindingLayout binding visibility storageTexture = unsafeCoerce
48-
{ binding, visibility, storageTexture }
49-
50-
gpuExternalTextureBindingLayout
51-
:: GPUIndex32
52-
-> GPUShaderStageFlags
53-
-> GPUExternalTextureBindingLayout
54-
-> GPUBindGroupLayoutEntry
55-
gpuExternalTextureBindingLayout binding visibility externalTexture =
56-
unsafeCoerce { binding, visibility, externalTexture }
18+
19+
class AsGPUBindGroupLayoutEntry e where
20+
gpuBindGroupLayoutEntry
21+
:: GPUIndex32 -> GPUShaderStageFlags -> e -> GPUBindGroupLayoutEntry
22+
23+
instance AsGPUBindGroupLayoutEntry GPUBufferBindingLayout where
24+
gpuBindGroupLayoutEntry binding visibility buffer = unsafeCoerce
25+
{ binding, visibility, buffer }
26+
27+
instance AsGPUBindGroupLayoutEntry GPUSamplerBindingLayout where
28+
gpuBindGroupLayoutEntry binding visibility sampler = unsafeCoerce
29+
{ binding, visibility, sampler }
30+
31+
instance AsGPUBindGroupLayoutEntry GPUTextureBindingLayout where
32+
gpuBindGroupLayoutEntry binding visibility texture = unsafeCoerce
33+
{ binding, visibility, texture }
34+
35+
instance AsGPUBindGroupLayoutEntry GPUStorageTextureBindingLayout where
36+
gpuBindGroupLayoutEntry binding visibility storageTexture = unsafeCoerce
37+
{ binding, visibility, storageTexture }
38+
39+
instance AsGPUBindGroupLayoutEntry GPUExternalTextureBindingLayout where
40+
gpuBindGroupLayoutEntry binding visibility externalTexture =
41+
unsafeCoerce { binding, visibility, externalTexture }

0 commit comments

Comments
 (0)