import { Vector3 } from '../math/Vector3.js'; import { BufferAttribute } from './BufferAttribute.js'; import { denormalize, normalize } from '../math/MathUtils.js'; const _vector = /*@__PURE__*/ new Vector3(); class InterleavedBufferAttribute { constructor( interleavedBuffer, itemSize, offset, normalized = false ) { this.isInterleavedBufferAttribute = true; this.name = ''; this.data = interleavedBuffer; this.itemSize = itemSize; this.offset = offset; this.normalized = normalized === true; } get count() { return this.data.count; } get array() { return this.data.array; } set needsUpdate( value ) { this.data.needsUpdate = value; } applyMatrix4( m ) { for ( let i = 0, l = this.data.count; i < l; i ++ ) { _vector.fromBufferAttribute( this, i ); _vector.applyMatrix4( m ); this.setXYZ( i, _vector.x, _vector.y, _vector.z ); } return this; } applyNormalMatrix( m ) { for ( let i = 0, l = this.count; i < l; i ++ ) { _vector.fromBufferAttribute( this, i ); _vector.applyNormalMatrix( m ); this.setXYZ( i, _vector.x, _vector.y, _vector.z ); } return this; } transformDirection( m ) { for ( let i = 0, l = this.count; i < l; i ++ ) { _vector.fromBufferAttribute( this, i ); _vector.transformDirection( m ); this.setXYZ( i, _vector.x, _vector.y, _vector.z ); } return this; } setX( index, x ) { if ( this.normalized ) x = normalize( x, this.array ); this.data.array[ index * this.data.stride + this.offset ] = x; return this; } setY( index, y ) { if ( this.normalized ) y = normalize( y, this.array ); this.data.array[ index * this.data.stride + this.offset + 1 ] = y; return this; } setZ( index, z ) { if ( this.normalized ) z = normalize( z, this.array ); this.data.array[ index * this.data.stride + this.offset + 2 ] = z; return this; } setW( index, w ) { if ( this.normalized ) w = normalize( w, this.array ); this.data.array[ index * this.data.stride + this.offset + 3 ] = w; return this; } getX( index ) { let x = this.data.array[ index * this.data.stride + this.offset ]; if ( this.normalized ) x = denormalize( x, this.array ); return x; } getY( index ) { let y = this.data.array[ index * this.data.stride + this.offset + 1 ]; if ( this.normalized ) y = denormalize( y, this.array ); return y; } getZ( index ) { let z = this.data.array[ index * this.data.stride + this.offset + 2 ]; if ( this.normalized ) z = denormalize( z, this.array ); return z; } getW( index ) { let w = this.data.array[ index * this.data.stride + this.offset + 3 ]; if ( this.normalized ) w = denormalize( w, this.array ); return w; } setXY( index, x, y ) { index = index * this.data.stride + this.offset; if ( this.normalized ) { x = normalize( x, this.array ); y = normalize( y, this.array ); } this.data.array[ index + 0 ] = x; this.data.array[ index + 1 ] = y; return this; } setXYZ( index, x, y, z ) { index = index * this.data.stride + this.offset; if ( this.normalized ) { x = normalize( x, this.array ); y = normalize( y, this.array ); z = normalize( z, this.array ); } this.data.array[ index + 0 ] = x; this.data.array[ index + 1 ] = y; this.data.array[ index + 2 ] = z; return this; } setXYZW( index, x, y, z, w ) { index = index * this.data.stride + this.offset; if ( this.normalized ) { x = normalize( x, this.array ); y = normalize( y, this.array ); z = normalize( z, this.array ); w = normalize( w, this.array ); } this.data.array[ index + 0 ] = x; this.data.array[ index + 1 ] = y; this.data.array[ index + 2 ] = z; this.data.array[ index + 3 ] = w; return this; } clone( data ) { if ( data === undefined ) { console.log( 'THREE.InterleavedBufferAttribute.clone(): Cloning an interleaved buffer attribute will deinterleave buffer data.' ); const array = []; for ( let i = 0; i < this.count; i ++ ) { const index = i * this.data.stride + this.offset; for ( let j = 0; j < this.itemSize; j ++ ) { array.push( this.data.array[ index + j ] ); } } return new BufferAttribute( new this.array.constructor( array ), this.itemSize, this.normalized ); } else { if ( data.interleavedBuffers === undefined ) { data.interleavedBuffers = {}; } if ( data.interleavedBuffers[ this.data.uuid ] === undefined ) { data.interleavedBuffers[ this.data.uuid ] = this.data.clone( data ); } return new InterleavedBufferAttribute( data.interleavedBuffers[ this.data.uuid ], this.itemSize, this.offset, this.normalized ); } } toJSON( data ) { if ( data === undefined ) { console.log( 'THREE.InterleavedBufferAttribute.toJSON(): Serializing an interleaved buffer attribute will deinterleave buffer data.' ); const array = []; for ( let i = 0; i < this.count; i ++ ) { const index = i * this.data.stride + this.offset; for ( let j = 0; j < this.itemSize; j ++ ) { array.push( this.data.array[ index + j ] ); } } // deinterleave data and save it as an ordinary buffer attribute for now return { itemSize: this.itemSize, type: this.array.constructor.name, array: array, normalized: this.normalized }; } else { // save as true interleaved attribtue if ( data.interleavedBuffers === undefined ) { data.interleavedBuffers = {}; } if ( data.interleavedBuffers[ this.data.uuid ] === undefined ) { data.interleavedBuffers[ this.data.uuid ] = this.data.toJSON( data ); } return { isInterleavedBufferAttribute: true, itemSize: this.itemSize, data: this.data.uuid, offset: this.offset, normalized: this.normalized }; } } } export { InterleavedBufferAttribute };