@@ -332,3 +332,82 @@ const indexBuffer = root
332332
333333```
334334
335+ ## Binding buffers
336+
337+ To use a buffer in a shader, it needs to be bound using a bind group.
338+ There are two approaches provided by TypeGPU.
339+
340+ ### Manual binding
341+
342+ The default option is to create bind group layouts and bind your buffers via bind groups.
343+ Read more in the chapter dedicated to [ bind groups] ( /TypeGPU/fundamentals/bind-groups ) .
344+
345+ ``` ts twoslash
346+ import tgpu from ' typegpu' ;
347+ import * as d from ' typegpu/data' ;
348+
349+ const root = await tgpu .init ();
350+ // ---cut---
351+ const pointsBuffer = root
352+ .createBuffer (d .arrayOf (d .vec2i , 100 ))
353+ .$usage (' storage' );
354+
355+ const bindGroupLayout = tgpu .bindGroupLayout ({
356+ points: { storage: d .arrayOf (d .vec2i , 100 ), access: ' mutable' },
357+ });
358+
359+ const bindGroup = root
360+ .createBindGroup (bindGroupLayout , { points: pointsBuffer });
361+
362+ const mainCompute = tgpu [' ~unstable' ].computeFn ({
363+ in: { gid: d .builtin .globalInvocationId },
364+ workgroupSize: [1 ],
365+ })((input ) => {
366+ // Access and modify the bound buffer via the layout
367+ bindGroupLayout .$ .points [input .gid [0 ]] = d .vec2i (1 , 2 );
368+ });
369+
370+ const pipeline = root [' ~unstable' ]
371+ .withCompute (mainCompute )
372+ .createPipeline ();
373+
374+ pipeline
375+ .with (bindGroupLayout , bindGroup )
376+ .dispatchWorkgroups (100 );
377+ ```
378+
379+ ### Using fixed resources
380+
381+ For scenarios where buffers remain consistent across multiple compute or render operations,
382+ TypeGPU offers fixed resources that appear bindless from a code perspective.
383+ Fixed buffers are created using dedicated root methods.
384+
385+ | WGSL type | TypeGPU constructor |
386+ | ----------------------------| -------------------------|
387+ | ` var<uniform> ` | ` root.createUniform() ` |
388+ | ` var<storage, read> ` | ` root.createReadonly() ` |
389+ | ` var<storage, read_write> ` | ` root.createMutable() ` |
390+
391+ ``` ts twoslash
392+ import tgpu from ' typegpu' ;
393+ import * as d from ' typegpu/data' ;
394+
395+ const root = await tgpu .init ();
396+ // ---cut---
397+ const pointsBuffer = root .createMutable (d .arrayOf (d .vec2i , 100 ));
398+
399+ const mainCompute = tgpu [' ~unstable' ].computeFn ({
400+ in: { gid: d .builtin .globalInvocationId },
401+ workgroupSize: [1 ],
402+ })((input ) => {
403+ // Access and modify the fixed buffer directly
404+ pointsBuffer .$ [input .gid [0 ]] = d .vec2i ();
405+ });
406+
407+ const pipeline = root [' ~unstable' ].withCompute (mainCompute ).createPipeline ();
408+ pipeline .dispatchWorkgroups (100 );
409+ ```
410+
411+ TypeGPU automatically generates a "catch-all" bind group and populates it with the fixed resources.
412+
413+ You can also use [ ` resolveWithContext ` ] ( /TypeGPU/fundamentals/resolve/#resolvewithcontext ) to access the automatically generated bind group and layout containing your fixed resources.
0 commit comments