WebGL使用gl.TRIANGLES绘制正方形失败,求提示(附代码)
WebGL 同一缓冲区存储顶点位置与颜色,使用gl.TRIANGLES绘制正方形仅显示三角形的问题
我尝试在WebGL中将顶点位置与颜色数据存入同一缓冲区,用gl.TRIANGLES绘制正方形,但最终只显示出三角形。不清楚代码哪里出错,同时对drawArrays中的count参数作用有疑问,希望得到相关提示而非直接答案。
相关代码片段:
缓冲区数据配置
gl.bufferData(gl.ARRAY_BUFFER, new Float32Array([ // position -0.9, 0.9, 0.9, 0.9, -0.9, -0.9, 0.9, 0.9, // color 1, 0, 0, 1, 0, 1, 0, 1, 1, 0, 1, 1, 1, 0, 0, 1 ]), gl.STATIC_DRAW);
顶点属性指针配置
gl.enableVertexAttribArray(positionLocation); gl.enableVertexAttribArray(colorLocation); var size = 2; var type = gl.FLOAT; var normalize = false; var stride = 0; var offset = 0; gl.vertexAttribPointer(positionLocation, size, type, normalize, stride, offset); var size = 4; var type = gl.FLOAT; var normalize = false; var stride = 0; var offset = Float32Array.BYTES_PER_ELEMENT * 8; gl.vertexAttribPointer(colorLocation, size, type, normalize, stride, offset);
绘制代码
// Draw the geometry. var offset = 0; var count = 3; gl.drawArrays(gl.TRIANGLES, offset, count);
完整代码
<!DOCTYPE html> <html> <head> <title>CS299 - Assignment 1.1</title> <link type="text/css" href="https://webgl2fundamentals.org/webgl/resources/webgl-tutorials.css" rel="stylesheet" /> <!-- css override --> <style type="text/css"> body { background-color: #CCCCCC; } #group {background-color: #E8F49F;} canvas { background-color: #4DC72F; width: 300px; height: 300px; border: 0px; } .gman-widget-slider {min-width: 200px;} </style> </head> <body> <canvas id="canvas"></canvas> </body> <!-- util functions --> <script src="https://webgl2fundamentals.org/webgl/resources/webgl-utils.js"></script> <!-- main WebGL2 code --> <script> "use strict"; var vs = `#version 300 es // an attribute is an input (in) to a vertex shader. // It will receive data from a buffer in vec2 a_position; in vec4 a_color; // color output from vertex shader to fragment shader out vec4 v_color; // all shaders have a main function. void main() { // default position output variable // convert vec2 to vec4 gl_Position = vec4(a_position, 0, 1); // color passthrough v_color = a_color; } `; var fs = `#version 300 es precision highp float; // color passthrough in vec4 v_color; // outout color out vec4 outColor; void main() { outColor = v_color; } `; function main() { // Get A WebGL context /** @type {HTMLCanvasElement} */ var canvas = document.querySelector("#canvas"); var gl = canvas.getContext("webgl2"); if (!gl) { return; } // setup GLSL program var program = webglUtils.createProgramFromSources(gl, [vs, fs]); // look up where the vertex data needs to go. var positionLocation = gl.getAttribLocation(program, "a_position"); var colorLocation = gl.getAttribLocation(program, "a_color"); // Create set of attributes var vao = gl.createVertexArray(); gl.bindVertexArray(vao); // Create a buffer (formerly called "vertex buffer object", now just "buffer"). var vbo = gl.createBuffer(); // Set Geometry. gl.bindBuffer(gl.ARRAY_BUFFER, vbo); // [40%] Modify the code to draw a square instead of a triangle. // Assign C,M,Y, and K colors to the 4 vertices of the square. gl.bufferData(gl.ARRAY_BUFFER, new Float32Array([ // position -0.9, 0.9, 0.9, 0.9, -0.9, -0.9, 0.9, 0.9, // color 1, 0, 0, 1, 0, 1, 0, 1, 1, 0, 1, 1, 1, 0, 0, 1 ]), gl.STATIC_DRAW); // tell the position attribute how to pull data out of the current ARRAY_BUFFER gl.enableVertexAttribArray(positionLocation); gl.enableVertexAttribArray(colorLocation); var size = 2; var type = gl.FLOAT; var normalize = false; var stride = 0; var offset = 0; gl.vertexAttribPointer(positionLocation, size, type, normalize, stride, offset); var size = 4; var type = gl.FLOAT; var normalize = false; var stride = 0; var offset = Float32Array.BYTES_PER_ELEMENT * 8; // must be in bytes gl.vertexAttribPointer(colorLocation, size, type, normalize, stride, offset); // Draw the scene. function drawScene() { webglUtils.resizeCanvasToDisplaySize(gl.canvas); gl.viewport(0, 0, gl.canvas.width, gl.canvas.height); // Clear the canvas gl.clearColor(0.15, 0.15, 0.15, 1.0); gl.clear(gl.COLOR_BUFFER_BIT | gl.DEPTH_BUFFER_BIT); // Tell it to use our program (pair of shaders) gl.useProgram(program); // Bind the attribute/buffer set we want. gl.bindVertexArray(vao); // Draw the geometry. var offset = 0; var count = 3; // [1.5 points] Use gl.TRIANGLE_STRIP instead of gl.TRIANGLES gl.drawArrays(gl.TRIANGLES, offset, count); } drawScene(); } main(); </script> <p id="group">Group: 4DC72F</p> </html>
提示方向
- 回忆
gl.TRIANGLES的绘制逻辑:每3个连续顶点构成一个独立三角形,绘制正方形需要多少个顶点才能组成两个三角形? - 确认
drawArrays的count参数含义:它指定的是参与绘制的顶点总个数,而非三角形的数量。 - 检查缓冲区的数据布局:当前你把所有位置数据放在前面,所有颜色数据放在后面,这种布局下,
vertexAttribPointer的stride参数设置是否匹配?当stride=0时,WebGL会认为每个顶点的所有属性是连续存放的。 - 检查顶点完整性:你准备的位置顶点是否包含正方形的四个顶点?当前的位置数组里有没有重复或缺失的顶点?
内容的提问来源于stack exchange,提问作者Powzer
相关产品推荐
相关产品推荐

