web-dev-qa-db-ja.com

WebGL GLエラー:GL_INVALID_OPERATION:glDrawElements:属性1の範囲外の頂点にアクセスしようとしました

いくつかのカスタムシェーダーを使用してTHREE.jsrev49に基づくコードの既存のバグを修正しようとしています。

私は完全なWebGL初心者なので、他の回答の先頭または末尾は、私が持っていたよりもはるかに多くの知識を前提としているように見えたため、作成できませんでした。何を探すべきかについてのヒントさえもありがたいです! :)コードの最終結果は、半透明のボックスワイヤーフレームを描画し、半透明のテクスチャで面をペイントすることです。

特定のエラーは次のとおりです。

_[.WebGLRenderingContext]GL ERROR :GL_INVALID_OPERATION : glDrawElements: attempt to access out of range vertices in attribute 1_

問題をTHREE.WebGLRenderer.renderBufferの特定の_gl.drawElements( _gl.TRIANGLES, geometryGroup.__webglFaceCount, _gl.UNSIGNED_SHORT, 0 );にトレースしました。

呼び出しコードのスニペットは次のとおりです。

_scene.overrideMaterial = depthMaterial; // shaders below
var ctx = renderer.getContext(); // renderer is a THREE.WebGLRenderer
ctx.disable(ctx.BLEND);
// renderTarget is a THREE.WebGLRenderTarget, _camera, scene is obvious
renderer.render(scene, _camera, renderTarget, true); // error occurs here
_

関連するシェーダーは次のとおりです。

_    uniforms: {},

    vertexShader: [
        "varying vec3 vNormal;",

        "void main() {",

            "vec4 mvPosition = modelViewMatrix * vec4( position, 1.0 );",
            "vNormal = normalMatrix * normal;",

            "gl_Position = projectionMatrix * mvPosition;",

        "}"
    ].join("\n"),

    fragmentShader: [
        "vec4 pack_depth( const in highp float depth ) {",

            "const highp vec4 bit_shift = vec4( 256.0, 256.0*256.0, 256.0*256.0*256.0, 256.0*256.0*256.0*256.0 );",
            "vec4 res = depth * bit_shift;",
            "res.x = min(res.x + 1.0, 255.0);",
            "res = fract(floor(res) / 256.0);",
            "return res;",

        "}",

        "void main() {",
            "gl_FragData[0] = pack_depth( gl_FragCoord.z );",
        "}"
    ].join("\n")
_

ご協力いただきありがとうございます!

11
SapphireSun

WebGLでは、データ(通常は頂点の位置、法線、色、テクスチャ座標)でいっぱいのバッファを設定します。次に、これらのバッファを使用して何かを描画するようにWebGLに要求します。 gl.drawArraysまたはgl.drawElementsで質問できます。 gl.drawElementsは、インデックスでいっぱいの別のバッファを使用して、使用する頂点を決定します。

発生したエラーは、設定したバッファよりも多くの要素を描画またはアクセスするようにWebGLに要求したことを意味します。つまり、3つの頂点に相当するデータのみを提供し、gl.drawArraysを呼び出すときに4つの頂点を描画するように要求すると、そのエラーが発生します。同様に、3つの頂点に相当するデータのみを提供し、2より大きい頂点にアクセスするインデックスを設定すると、そのエラーが発生します。 #0、#1、および#2の番号が付けられた3つの頂点があるため、インデックスのいずれかが2より大きい場合は、指定した3つの頂点の範囲外の何かにアクセスするようにWebGLに要求しています。

だから、あなたのデータを確認してください。インデックスが範囲外ですか?バッファの1つが他のバッファよりも短いですか?等..

22
gman

徹底的にこれを追加しています-インポートされたOBJモデルを使用していて、THREE.ShaderLib ["normalmap"]を介してシェーダーを作成するときにこのエラーが発生していました

修正は、メッシュのジオメトリオブジェクトでcomputeTangents()を呼び出すだけでした。

model.geometry.computeTangents();

答えをアーカイブしました ここ

3
neoRiley