diff --git a/packages/core/src/context/ContextSystem.js b/packages/core/src/context/ContextSystem.js index dc6243d..6487683 100644 --- a/packages/core/src/context/ContextSystem.js +++ b/packages/core/src/context/ContextSystem.js @@ -163,6 +163,7 @@ vertexArrayObject: gl.getExtension('OES_vertex_array_object') || gl.getExtension('MOZ_OES_vertex_array_object') || gl.getExtension('WEBKIT_OES_vertex_array_object'), + uint32ElementIndex: gl.getExtension('OES_element_index_uint'), }); } diff --git a/packages/core/src/context/ContextSystem.js b/packages/core/src/context/ContextSystem.js index dc6243d..6487683 100644 --- a/packages/core/src/context/ContextSystem.js +++ b/packages/core/src/context/ContextSystem.js @@ -163,6 +163,7 @@ vertexArrayObject: gl.getExtension('OES_vertex_array_object') || gl.getExtension('MOZ_OES_vertex_array_object') || gl.getExtension('WEBKIT_OES_vertex_array_object'), + uint32ElementIndex: gl.getExtension('OES_element_index_uint'), }); } diff --git a/packages/core/src/geometry/GeometrySystem.js b/packages/core/src/geometry/GeometrySystem.js index 3b83a89..3c56989 100644 --- a/packages/core/src/geometry/GeometrySystem.js +++ b/packages/core/src/geometry/GeometrySystem.js @@ -39,6 +39,13 @@ this.hasInstance = true; /** + * `true` if support `gl.UNSIGNED_INT` in `gl.drawElements` or `gl.drawElementsInstanced` + * @member {boolean} + * @readonly + */ + this.canUseUInt32ElementIndex = false; + + /** * A cache of currently bound buffer, * contains only two members with keys ARRAY_BUFFER and ELEMENT_ARRAY_BUFFER * @member {Object.} @@ -69,6 +76,7 @@ this.disposeAll(true); const gl = this.gl = this.renderer.gl; + const context = this.renderer.context; this.CONTEXT_UID = this.renderer.CONTEXT_UID; @@ -134,6 +142,8 @@ this.hasInstance = false; } } + + this.canUseUInt32ElementIndex = context.webGLVersion === 2 || !!context.extensions.uint32ElementIndex; } /** @@ -593,15 +603,27 @@ if (geometry.indexBuffer) { - if (geometry.instanced) + const byteSize = geometry.indexBuffer.data.BYTES_PER_ELEMENT; + const glType = byteSize === 2 ? gl.UNSIGNED_SHORT : gl.UNSIGNED_INT; + + if (byteSize === 2 || (byteSize === 4 && this.canUseUInt32ElementIndex)) { - /* eslint-disable max-len */ - gl.drawElementsInstanced(type, size || geometry.indexBuffer.data.length, gl.UNSIGNED_SHORT, (start || 0) * 2, instanceCount || 1); - /* eslint-enable max-len */ + if (geometry.instanced) + { + /* eslint-disable max-len */ + gl.drawElementsInstanced(type, size || geometry.indexBuffer.data.length, glType, (start || 0) * byteSize, instanceCount || 1); + /* eslint-enable max-len */ + } + else + { + /* eslint-disable max-len */ + gl.drawElements(type, size || geometry.indexBuffer.data.length, glType, (start || 0) * byteSize); + /* eslint-enable max-len */ + } } else { - gl.drawElements(type, size || geometry.indexBuffer.data.length, gl.UNSIGNED_SHORT, (start || 0) * 2); + console.warn('unsupported index buffer type: uint32'); } } else if (geometry.instanced)