WebGLObjects.js 4.6 KB
Newer Older
M
Mr.doob 已提交
1 2 3 4
/**
* @author mrdoob / http://mrdoob.com/
*/

5
THREE.WebGLObjects = function ( gl, properties, info ) {
M
Mr.doob 已提交
6

7
	var geometries = new THREE.WebGLGeometries( gl, properties, info );
8

M
Mr.doob 已提交
9 10
	//

11
	function update( object ) {
12 13

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

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

17
		if ( object.geometry instanceof THREE.Geometry ) {
18

19
			geometry.updateFromObject( object );
20 21

		}
22

23
		var attributes = geometry.attributes;
M
Mr.doob 已提交
24

25
		for ( var name in attributes ) {
M
Mr.doob 已提交
26

M
Mr.doob 已提交
27
			updateAttribute( attributes[ name ] );
M
Mr.doob 已提交
28

29
		}
30

31 32 33 34
		// morph targets

		var morphAttributes = geometry.morphAttributes;

35
		for ( var name in morphAttributes ) {
36

37 38 39 40
			var array = morphAttributes[ name ];

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

M
Mr.doob 已提交
41
				updateAttribute( array[ i ] );
42 43

			}
44 45 46

		}

47 48
		return geometry;

49
	}
M
Mr.doob 已提交
50

M
Mr.doob 已提交
51
	function updateAttribute( attribute ) {
52

M
Mr.doob 已提交
53 54 55 56 57 58 59 60 61 62 63
		var bufferType;

		if ( attribute instanceof THREE.IndexBufferAttribute ) {

			bufferType = gl.ELEMENT_ARRAY_BUFFER;

		} else {

			bufferType = gl.ARRAY_BUFFER;

		}
M
Mr.doob 已提交
64

65
		var data = ( attribute instanceof THREE.InterleavedBufferAttribute ) ? attribute.data : attribute;
M
Mr.doob 已提交
66

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

69
		if ( attributeProperties.__webglBuffer === undefined ) {
M
Mr.doob 已提交
70

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

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

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

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

D
dubejf 已提交
79
	}
M
Mr.doob 已提交
80

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

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

D
dubejf 已提交
86
		var usage = gl.STATIC_DRAW;
M
Mr.doob 已提交
87

D
dubejf 已提交
88 89 90
		if ( data instanceof THREE.DynamicBufferAttribute
			 || ( data instanceof THREE.InstancedBufferAttribute && data.dynamic === true )
			 || ( data instanceof THREE.InterleavedBuffer && data.dynamic === true ) ) {
M
Mr.doob 已提交
91

D
dubejf 已提交
92
			usage = gl.DYNAMIC_DRAW;
M
Mr.doob 已提交
93

D
dubejf 已提交
94
		}
M
Mr.doob 已提交
95

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

98
		attributeProperties.version = data.version;
M
Mr.doob 已提交
99

D
dubejf 已提交
100
	}
M
Mr.doob 已提交
101

102
	function updateBuffer( attributeProperties, data, bufferType ) {
103

D
dubejf 已提交
104
		gl.bindBuffer( bufferType, attributeProperties.__webglBuffer );
105

G
gero3 已提交
106 107 108
		if ( data.updateRange === undefined || data.updateRange.count === - 1 ) {

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

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

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

M
Mr.doob 已提交
114
			console.error( 'THREE.WebGLObjects.updateBuffer: using updateRange for THREE.DynamicBufferAttribute and marked as needsUpdate but count is 0, ensure you are using set methods or updating manually.' );
D
dubejf 已提交
115 116 117 118 119

		} else {

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

D
dubejf 已提交
121 122 123
			data.updateRange.count = 0; // reset range

		}
124

125
		attributeProperties.version = data.version;
D
dubejf 已提交
126 127

	}
M
Mr.doob 已提交
128

129
	function getAttributeBuffer( attribute ) {
130

131 132
		if ( attribute instanceof THREE.InterleavedBufferAttribute ) {

D
dubejf 已提交
133
			return properties.get( attribute.data ).__webglBuffer;
134 135 136

		}

137
		return properties.get( attribute ).__webglBuffer;
138

139 140 141 142
	}

	function getWireframeAttribute( geometry ) {

143
		var property = properties.get( geometry );
144

145 146 147
		if ( property.wireframe !== undefined ) {

			return property.wireframe;
148 149 150 151 152

		}

		var indices = [];

153 154
		var attributes = geometry.attributes;

155 156 157
		var index = attributes.index;
		var position = attributes.position;

M
Mr.doob 已提交
158
		// console.time( 'wireframe' );
159 160 161 162 163 164

		if ( index !== undefined ) {

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

165
			for ( var i = 0, l = array.length; i < l; i += 3 ) {
166 167 168 169 170 171 172 173 174 175 176 177 178 179 180

				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 {

			var array = position.array;

181
			for ( var i = 0, l = ( array.length / 3 ) - 1; i < l; i += 3 ) {
182 183 184 185 186 187 188 189 190 191 192

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

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

			}

		}

M
Mr.doob 已提交
193
		// console.timeEnd( 'wireframe' );
194

M
Mr.doob 已提交
195
		var TypeArray = position.count > 65535 ? Uint32Array : Uint16Array;
M
Mr.doob 已提交
196
		var attribute = new THREE.IndexBufferAttribute( new TypeArray( indices ), 1 );
197

M
Mr.doob 已提交
198
		updateAttribute( attribute );
199

200
		property.wireframe = attribute;
201 202 203 204 205 206 207

		return attribute;

	}

	function checkEdge( edges, a, b ) {

M
Mr.doob 已提交
208
		var hash = a < b ? a + '_' + b : b + '_' + a;
209

M
Mr.doob 已提交
210 211 212
		if ( edges.hasOwnProperty( hash ) ) return false;

		edges[ hash ] = 1;
213 214 215 216 217 218 219

		return true;

	}

	this.getAttributeBuffer = getAttributeBuffer;
	this.getWireframeAttribute = getWireframeAttribute;
220

221 222
	this.update = update;

M
Mr.doob 已提交
223
};