StorageBufferNode.js 2.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147
  1. import BufferNode from './BufferNode.js';
  2. import { bufferAttribute } from './BufferAttributeNode.js';
  3. import { nodeObject, varying } from '../tsl/TSLBase.js';
  4. import { storageElement } from '../utils/StorageArrayElementNode.js';
  5. import { GPUBufferBindingType } from '../../renderers/webgpu/utils/WebGPUConstants.js';
  6. class StorageBufferNode extends BufferNode {
  7. static get type() {
  8. return 'StorageBufferNode';
  9. }
  10. constructor( value, bufferType, bufferCount = 0 ) {
  11. super( value, bufferType, bufferCount );
  12. this.isStorageBufferNode = true;
  13. this.access = GPUBufferBindingType.Storage;
  14. this.isAtomic = false;
  15. this.bufferObject = false;
  16. this.bufferCount = bufferCount;
  17. this._attribute = null;
  18. this._varying = null;
  19. this.global = true;
  20. if ( value.isStorageBufferAttribute !== true && value.isStorageInstancedBufferAttribute !== true ) {
  21. // TOOD: Improve it, possibly adding a new property to the BufferAttribute to identify it as a storage buffer read-only attribute in Renderer
  22. if ( value.isInstancedBufferAttribute ) value.isStorageInstancedBufferAttribute = true;
  23. else value.isStorageBufferAttribute = true;
  24. }
  25. }
  26. getHash( builder ) {
  27. if ( this.bufferCount === 0 ) {
  28. let bufferData = builder.globalCache.getData( this.value );
  29. if ( bufferData === undefined ) {
  30. bufferData = {
  31. node: this
  32. };
  33. builder.globalCache.setData( this.value, bufferData );
  34. }
  35. return bufferData.node.uuid;
  36. }
  37. return this.uuid;
  38. }
  39. getInputType( /*builder*/ ) {
  40. return 'storageBuffer';
  41. }
  42. element( indexNode ) {
  43. return storageElement( this, indexNode );
  44. }
  45. setBufferObject( value ) {
  46. this.bufferObject = value;
  47. return this;
  48. }
  49. setAccess( value ) {
  50. this.access = value;
  51. return this;
  52. }
  53. toReadOnly() {
  54. return this.setAccess( GPUBufferBindingType.ReadOnlyStorage );
  55. }
  56. setAtomic( value ) {
  57. this.isAtomic = value;
  58. return this;
  59. }
  60. toAtomic() {
  61. return this.setAtomic( true );
  62. }
  63. generate( builder ) {
  64. if ( builder.isAvailable( 'storageBuffer' ) ) {
  65. return super.generate( builder );
  66. }
  67. const nodeType = this.getNodeType( builder );
  68. if ( this._attribute === null ) {
  69. this._attribute = bufferAttribute( this.value );
  70. this._varying = varying( this._attribute );
  71. }
  72. const output = this._varying.build( builder, nodeType );
  73. builder.registerTransform( output, this._attribute );
  74. return output;
  75. }
  76. }
  77. export default StorageBufferNode;
  78. // Read-Write Storage
  79. export const storage = ( value, type, count ) => nodeObject( new StorageBufferNode( value, type, count ) );
  80. export const storageObject = ( value, type, count ) => nodeObject( new StorageBufferNode( value, type, count ).setBufferObject( true ) );
粤ICP备19079148号