WebGLObjects.js 4.6 KB
Newer Older
R
Rich Harris 已提交
1 2 3
import { BufferAttribute } from '../../core/BufferAttribute';
import { WebGLGeometries } from './WebGLGeometries';

M
Mr.doob 已提交
4 5 6 7
/**
* @author mrdoob / http://mrdoob.com/
*/

M
Mr.doob 已提交
8
function WebGLObjects( gl, properties, info ) {
M
Mr.doob 已提交
9

R
Rich Harris 已提交
10
	var geometries = new WebGLGeometries( gl, properties, info );
11

M
Mr.doob 已提交
12 13
	//

14
	function update( object ) {
15 16

		// TODO: Avoid updating twice (when using shadowMap). Maybe add frame counter.
M
Mr.doob 已提交
17

18
		var geometry = geometries.get( object );
M
Mr.doob 已提交
19

R
Rich Harris 已提交
20
		if ( (object.geometry && object.geometry.isGeometry) ) {
21

22
			geometry.updateFromObject( object );
23 24

		}
25

26
		var index = geometry.index;
27
		var attributes = geometry.attributes;
M
Mr.doob 已提交
28

29 30 31 32 33 34
		if ( index !== null ) {

			updateAttribute( index, gl.ELEMENT_ARRAY_BUFFER );

		}

35
		for ( var name in attributes ) {
M
Mr.doob 已提交
36

37
			updateAttribute( attributes[ name ], gl.ARRAY_BUFFER );
M
Mr.doob 已提交
38

39
		}
40

41 42 43 44
		// morph targets

		var morphAttributes = geometry.morphAttributes;

45
		for ( var name in morphAttributes ) {
46

47 48 49 50
			var array = morphAttributes[ name ];

			for ( var i = 0, l = array.length; i < l; i ++ ) {

51
				updateAttribute( array[ i ], gl.ARRAY_BUFFER );
52 53

			}
54 55 56

		}

57 58
		return geometry;

59
	}
M
Mr.doob 已提交
60

61
	function updateAttribute( attribute, bufferType ) {
M
Mr.doob 已提交
62

R
Rich Harris 已提交
63
		var data = ( (attribute && attribute.isInterleavedBufferAttribute) ) ? attribute.data : attribute;
M
Mr.doob 已提交
64

65
		var attributeProperties = properties.get( data );
M
Mr.doob 已提交
66

67
		if ( attributeProperties.__webglBuffer === undefined ) {
M
Mr.doob 已提交
68

D
dubejf 已提交
69
			createBuffer( attributeProperties, data, bufferType );
M
Mr.doob 已提交
70

71
		} else if ( attributeProperties.version !== data.version ) {
M
Mr.doob 已提交
72

D
dubejf 已提交
73
			updateBuffer( attributeProperties, data, bufferType );
M
Mr.doob 已提交
74

D
dubejf 已提交
75
		}
M
Mr.doob 已提交
76

D
dubejf 已提交
77
	}
M
Mr.doob 已提交
78

79
	function createBuffer( attributeProperties, data, bufferType ) {
M
Mr.doob 已提交
80

D
dubejf 已提交
81 82
		attributeProperties.__webglBuffer = gl.createBuffer();
		gl.bindBuffer( bufferType, attributeProperties.__webglBuffer );
M
Mr.doob 已提交
83

M
Mr.doob 已提交
84
		var usage = data.dynamic ? gl.DYNAMIC_DRAW : gl.STATIC_DRAW;
M
Mr.doob 已提交
85

D
dubejf 已提交
86
		gl.bufferData( bufferType, data.array, usage );
M
Mr.doob 已提交
87

88
		attributeProperties.version = data.version;
M
Mr.doob 已提交
89

D
dubejf 已提交
90
	}
M
Mr.doob 已提交
91

92
	function updateBuffer( attributeProperties, data, bufferType ) {
93

D
dubejf 已提交
94
		gl.bindBuffer( bufferType, attributeProperties.__webglBuffer );
95

M
Mr.doob 已提交
96
		if ( data.dynamic === false || data.updateRange.count === - 1 ) {
G
gero3 已提交
97 98

			// Not using update ranges
M
Mr.doob 已提交
99

D
dubejf 已提交
100
			gl.bufferSubData( bufferType, 0, data.array );
101

D
dubejf 已提交
102
		} else if ( data.updateRange.count === 0 ) {
M
Mr.doob 已提交
103

M
Mr.doob 已提交
104
			console.error( 'THREE.WebGLObjects.updateBuffer: dynamic THREE.BufferAttribute marked as needsUpdate but updateRange.count is 0, ensure you are using set methods or updating manually.' );
D
dubejf 已提交
105 106 107 108 109

		} else {

			gl.bufferSubData( bufferType, data.updateRange.offset * data.array.BYTES_PER_ELEMENT,
							  data.array.subarray( data.updateRange.offset, data.updateRange.offset + data.updateRange.count ) );
110

D
dubejf 已提交
111 112 113
			data.updateRange.count = 0; // reset range

		}
114

115
		attributeProperties.version = data.version;
D
dubejf 已提交
116 117

	}
M
Mr.doob 已提交
118

119
	function getAttributeBuffer( attribute ) {
120

R
Rich Harris 已提交
121
		if ( (attribute && attribute.isInterleavedBufferAttribute) ) {
122

D
dubejf 已提交
123
			return properties.get( attribute.data ).__webglBuffer;
124 125 126

		}

127
		return properties.get( attribute ).__webglBuffer;
128

129 130 131 132
	}

	function getWireframeAttribute( geometry ) {

133
		var property = properties.get( geometry );
134

135 136 137
		if ( property.wireframe !== undefined ) {

			return property.wireframe;
138 139 140 141 142

		}

		var indices = [];

143
		var index = geometry.index;
144
		var attributes = geometry.attributes;
145 146
		var position = attributes.position;

M
Mr.doob 已提交
147
		// console.time( 'wireframe' );
148

149
		if ( index !== null ) {
150 151 152 153

			var edges = {};
			var array = index.array;

154
			for ( var i = 0, l = array.length; i < l; i += 3 ) {
155 156 157 158 159 160 161 162 163 164 165 166 167

				var a = array[ i + 0 ];
				var b = array[ i + 1 ];
				var c = array[ i + 2 ];

				if ( checkEdge( edges, a, b ) ) indices.push( a, b );
				if ( checkEdge( edges, b, c ) ) indices.push( b, c );
				if ( checkEdge( edges, c, a ) ) indices.push( c, a );

			}

		} else {

168
			var array = attributes.position.array;
169

170
			for ( var i = 0, l = ( array.length / 3 ) - 1; i < l; i += 3 ) {
171 172 173 174 175 176 177 178 179 180 181

				var a = i + 0;
				var b = i + 1;
				var c = i + 2;

				indices.push( a, b, b, c, c, a );

			}

		}

M
Mr.doob 已提交
182
		// console.timeEnd( 'wireframe' );
183

M
Mr.doob 已提交
184
		var TypeArray = position.count > 65535 ? Uint32Array : Uint16Array;
R
Rich Harris 已提交
185
		var attribute = new BufferAttribute( new TypeArray( indices ), 1 );
186

187
		updateAttribute( attribute, gl.ELEMENT_ARRAY_BUFFER );
188

189
		property.wireframe = attribute;
190 191 192 193 194 195 196

		return attribute;

	}

	function checkEdge( edges, a, b ) {

M
Mr.doob 已提交
197
		if ( a > b ) {
198

A
Alexander Rose 已提交
199 200 201
			var tmp = a;
			a = b;
			b = tmp;
M
Mr.doob 已提交
202

A
Alexander Rose 已提交
203 204 205 206
		}

		var list = edges[ a ];

M
Mr.doob 已提交
207
		if ( list === undefined ) {
A
Alexander Rose 已提交
208 209 210 211

			edges[ a ] = [ b ];
			return true;

M
Mr.doob 已提交
212
		} else if ( list.indexOf( b ) === -1 ) {
A
Alexander Rose 已提交
213 214 215 216 217

			list.push( b );
			return true;

		}
218

A
Alexander Rose 已提交
219
		return false;
220 221 222 223 224

	}

	this.getAttributeBuffer = getAttributeBuffer;
	this.getWireframeAttribute = getWireframeAttribute;
225

226 227
	this.update = update;

M
Mr.doob 已提交
228
};
R
Rich Harris 已提交
229 230


231
export { WebGLObjects };