Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

TSL: Introduce array and instancedArray #29881

Draft
wants to merge 4 commits into
base: dev
Choose a base branch
from
Draft

Conversation

sunag
Copy link
Collaborator

@sunag sunag commented Nov 14, 2024

Description

Node allows the addition of anonymous attributes, so we don't need to link it to geometry for different effects. This also allows us to simplify the code for whoever is creating their shaders, making the process much simpler, closer to what would we do in conventional (non-gpu) JS code.

I made a revision so that toReadOnly() can be automatically applied to WebGPU if it is not in the compute shader, simplifying the process.

Common usage would be array( count|array, type ) or instancedArray( count|array, type ) can be seen in the example below.

webgpu_compute_birds example

New approach

// Labels applied to storage nodes and uniform nodes are reflected within the shader output,
// and are useful for debugging purposes.
				
const positionStorage = array( positionArray, 'vec3' ).label( 'positionStorage' );
const velocityStorage = array( velocityArray, 'vec3' ).label( 'velocityStorage' );
const phaseStorage = array( phaseArray, 'float' ).label( 'phaseStorage' );

Previous approach

// Create storage buffer attributes.

const positionBufferAttribute = new THREE.StorageBufferAttribute( positionArray, 3 );
const velocityBufferAttribute = new THREE.StorageBufferAttribute( velocityArray, 3 );
const phaseBufferAttribute = new THREE.StorageBufferAttribute( phaseArray, 1 );

// Labels applied to storage nodes and uniform nodes are reflected within the shader output,
// and are useful for debugging purposes.

// Access storage buffer attribute data from within shaders with a StorageNode.

const positionStorage = storage( positionBufferAttribute, 'vec3', positionBufferAttribute.count ).label( 'positionStorage' );
const velocityStorage = storage( velocityBufferAttribute, 'vec3', velocityBufferAttribute.count ).label( 'velocityStorage' );
const phaseStorage = storage( phaseBufferAttribute, 'float', phaseBufferAttribute.count ).label( 'phaseStorage' );

// Create read-only storage nodes. Storage nodes can only be accessed outside of compute shaders in a read-only state.

const positionRead = storageObject( positionBufferAttribute, 'vec3', positionBufferAttribute.count ).toReadOnly();
const velocityRead = storageObject( velocityBufferAttribute, 'vec3', velocityBufferAttribute.count ).toReadOnly();
const phaseRead = storageObject( phaseBufferAttribute, 'float', phaseBufferAttribute.count ).toReadOnly();

Copy link

github-actions bot commented Nov 14, 2024

📦 Bundle size

Full ESM build, minified and gzipped.

Before After Diff
WebGL 339.37
79.06
339.37
79.06
+0 B
+0 B
WebGPU 478.22
132.63
479.06
132.87
+847 B
+235 B
WebGPU Nodes 477.68
132.51
478.53
132.74
+847 B
+226 B

🌳 Bundle size after tree-shaking

Minimal build including a renderer, camera, empty scene, and dependencies.

Before After Diff
WebGL 464.82
112.02
464.82
112.02
+0 B
+0 B
WebGPU 546.95
148.2
547.04
148.2
+93 B
-1 B
WebGPU Nodes 502.83
137.91
502.93
137.88
+93 B
-24 B

@cmhhelgeson
Copy link
Contributor

This is a great encapsulation of the existing storage buffer functionality. Maybe you're still planning on adding this, but would users still have the ability to specify their storage node as an atomic?

@sunag
Copy link
Collaborator Author

sunag commented Nov 14, 2024

The PR does not remove the functionality of storage(), as array is storage, it could be used like: array().toAtomic().

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants