<!doctype html>
<html>
<body>
<canvas id ="ctx" width = "300" height = "300"></canvas>
<script>
//Getting Webgl Context
var ctx = document.getElementById("ctx");
var webgl = ctx.getContext("experimental-webgl");
/*Creating Shader*/
//Vertex Code
var vertexCode =
'attribute vec3 coordinates;'+
'attribute vec3 color;'+
'varying vec3 vColor;'+
'void main(void) {' +
' gl_Position = vec4(coordinates, 1.0);' +
'vColor = color;'+
'}';
//Creating Shader Object
var vertexShader = webgl.createShader(webgl.VERTEX_SHADER);
//Assigning the Source
webgl.shaderSource(vertexShader, vertexCode);
//Compiling the Source
webgl.compileShader(vertexShader);
//Fragment Shader Code
var fragmentCode ='precision mediump float;'+
'varying vec3 vColor;'+
'void main(void) {'+
'gl_FragColor = vec4(vColor, 1.);'+
'}';
//Creating Shader Object
var fragmentShader = webgl.createShader(webgl.FRAGMENT_SHADER);
//Assigning the Source
webgl.shaderSource(fragmentShader, fragmentCode);
//Compiling the Source
webgl.compileShader(fragmentShader);
//Creating Program to store Shader
var shaderProgram = webgl.createProgram();
//Attaching the shaders
webgl.attachShader(shaderProgram, vertexShader);
webgl.attachShader(shaderProgram, fragmentShader);
//linking the Program
webgl.linkProgram(shaderProgram);
//using the Program
webgl.useProgram(shaderProgram);
//Defining geometry
var vertices = [
-0.5,0.5,0.0,
-0.5,-0.5,0.0,
0.5,-0.5,0.0,
0.5,0.5,0.0
];
var colors = [0,0,1, 1,0,0, 0,1,0, 1,0,1,];
indices = [3,2,1,3,1,0];
//Creating a Buffer
var VextexBuffer = webgl.createBuffer();
var IndexBuffer = webgl.createBuffer();
var colorBuffer = webgl.createBuffer();
//Binding the Buffer
webgl.bindBuffer(webgl.ARRAY_BUFFER, VextexBuffer);
webgl.bindBuffer(webgl.ELEMENT_ARRAY_BUFFER, IndexBuffer);
webgl.bindBuffer(webgl.ARRAY_BUFFER, colorBuffer);
//Buffer Data
webgl.bufferData(webgl.ARRAY_BUFFER, new Float32Array(vertices), webgl.STATIC_DRAW);
webgl.bufferData(webgl.ELEMENT_ARRAY_BUFFER, new Uint16Array(indices), webgl.STATIC_DRAW);
webgl.bufferData(webgl.ARRAY_BUFFER, new Float32Array(colors), webgl.STATIC_DRAW);
/*Associating the shaders to bufferObject*/
//Getting attribute location
var coord = webgl.getAttribLocation(shaderProgram,"coordinates");
var color = webgl.getAttribLocation(shaderProgram, "color");
//pointing an attribute to the currently bound VBO
webgl.vertexAttribPointer(coord, 3, webgl.FLOAT, false ,0,0);
webgl.vertexAttribPointer(color, 3, webgl.FLOAT, false ,0,0);
//enabling the attributes
webgl.enableVertexAttribArray(coord);
webgl.enableVertexAttribArray(color);
//Unbind Array
/*Drawing the Triangle*/
//Clearing the Colour
webgl.clearColor(.5,.5,.5,1);
//Enabling the depth test
webgl.enable(webgl.DEPTH_TEST);
//Clearing colour nuffer bit
webgl.clear(webgl.COLOR_BUFFER_BIT);
//Setting a viewport
webgl.viewport(0,0,ctx.width,ctx.height);
//Draw the triangle
webgl.drawElements(webgl.TRIANGLES,indices.length,webgl.UNSIGNED_SHORT,0);
</script>
</body>
</html>
如果我删除颜色缓冲区以及与之相关的所有内容,代码会运行但是使用颜色缓冲区,我只看到灰色画布,没有别的。
Chrome控制台也不会显示任何错误或警告。 请帮帮我。
答案 0 :(得分:2)
这里是working fiddle。
代码中最大的错误是使用bindBuffer
方法。 WebGL上下文可以一次绑定缓冲区。一次绑定两个或多个缓冲区导致仅绑定最后一个缓冲区。
当您必须将数据复制到缓冲区时,需要绑定它然后调用bufferData
函数。
同样适用于vertexAttribPointer
功能。首先绑定要绑定属性的缓冲区,然后调用vertexAttribPointer
,依此类推其他缓冲区。
//Getting Webgl Context
var ctx = document.getElementById("ctx");
var webgl = ctx.getContext("experimental-webgl");
/*Creating Shader*/
//Vertex Code
var vertexCode =
'attribute vec3 coordinates;' +
'attribute vec3 color;' +
'varying vec3 vColor;' +
'void main(void) {' +
' gl_Position = vec4(coordinates, 1.0);' +
'vColor = color;' +
'}';
//Creating Shader Object
var vertexShader = webgl.createShader(webgl.VERTEX_SHADER);
//Assigning the Source
webgl.shaderSource(vertexShader, vertexCode);
//Compiling the Source
webgl.compileShader(vertexShader);
//Fragment Shader Code
var fragmentCode = 'precision mediump float;' +
'varying vec3 vColor;' +
'void main(void) {' +
'gl_FragColor = vec4(vColor, 1.);' +
'}';
//Creating Shader Object
var fragmentShader = webgl.createShader(webgl.FRAGMENT_SHADER);
//Assigning the Source
webgl.shaderSource(fragmentShader, fragmentCode);
//Compiling the Source
webgl.compileShader(fragmentShader);
//Creating Program to store Shader
var shaderProgram = webgl.createProgram();
//Attaching the shaders
webgl.attachShader(shaderProgram, vertexShader);
webgl.attachShader(shaderProgram, fragmentShader);
//linking the Program
webgl.linkProgram(shaderProgram);
//using the Program
webgl.useProgram(shaderProgram);
//Defining geometry
var vertices = [
-0.5, 0.5, 0.0,
-0.5, -0.5, 0.0,
0.5, -0.5, 0.0,
0.5, 0.5, 0.0
];
var colors = [0, 0, 1, 1, 0, 0, 0, 1, 0, 1, 0, 1, ];
indices = [3, 2, 1, 3, 1, 0];
var coord = webgl.getAttribLocation(shaderProgram, "coordinates");
var color = webgl.getAttribLocation(shaderProgram, "color");
webgl.enableVertexAttribArray(coord);
webgl.enableVertexAttribArray(color);
//Creating a Buffer
var VextexBuffer = webgl.createBuffer();
var IndexBuffer = webgl.createBuffer();
var colorBuffer = webgl.createBuffer();
//Binding the Buffer
webgl.bindBuffer(webgl.ARRAY_BUFFER, VextexBuffer);
webgl.bufferData(webgl.ARRAY_BUFFER, new Float32Array(vertices), webgl.STATIC_DRAW);
webgl.bindBuffer(webgl.ELEMENT_ARRAY_BUFFER, IndexBuffer);
webgl.bufferData(webgl.ELEMENT_ARRAY_BUFFER, new Uint16Array(indices), webgl.STATIC_DRAW);
webgl.bindBuffer(webgl.ARRAY_BUFFER, colorBuffer);
webgl.bufferData(webgl.ARRAY_BUFFER, new Float32Array(colors), webgl.STATIC_DRAW);
webgl.bindBuffer(webgl.ARRAY_BUFFER, VextexBuffer);
webgl.vertexAttribPointer(coord, 3, webgl.FLOAT, false, 0, 0);
webgl.bindBuffer(webgl.ARRAY_BUFFER, colorBuffer);
webgl.vertexAttribPointer(color, 3, webgl.FLOAT, false, 0, 0);
/*Drawing the Triangle*/
//Clearing the Colour
webgl.clearColor(.5, .5, .5, 1);
//Enabling the depth test
webgl.enable(webgl.DEPTH_TEST);
//Clearing colour nuffer bit
webgl.clear(webgl.COLOR_BUFFER_BIT);
//Setting a viewport
webgl.viewport(0, 0, ctx.width, ctx.height);
//Draw the triangle
webgl.drawElements(webgl.TRIANGLES, indices.length, webgl.UNSIGNED_SHORT, 0);
&#13;
<canvas id ="ctx" width = "300" height = "300"></canvas>
&#13;
答案 1 :(得分:1)
你用你的颜色覆盖你的顶点位置:
webgl.bufferData(webgl.ARRAY_BUFFER, new Float32Array(vertices), webgl.STATIC_DRAW);
webgl.bufferData(webgl.ARRAY_BUFFER, new Float32Array(colors), webgl.STATIC_DRAW);
在任何给定时间,每种类型(ARRAY_BUFFER
和ELEMENT_ARRAY_BUFFER
)只能绑定一个缓冲区,所以
流程是绑定缓冲区并设置其数据,然后设置特定缓冲区的顶点属性指针,然后继续下一个缓冲区:
// setup positions
var VextexBuffer = webgl.createBuffer();
webgl.bindBuffer(webgl.ARRAY_BUFFER, VextexBuffer);
webgl.bufferData(webgl.ARRAY_BUFFER, new Float32Array(vertices), webgl.STATIC_DRAW);
var coord = webgl.getAttribLocation(shaderProgram,"coordinates");
webgl.vertexAttribPointer(coord, 3, webgl.FLOAT, false ,0,0);
// setup indices
var IndexBuffer = webgl.createBuffer();
webgl.bindBuffer(webgl.ELEMENT_ARRAY_BUFFER, IndexBuffer);
webgl.bufferData(webgl.ELEMENT_ARRAY_BUFFER, new Uint16Array(indices), webgl.STATIC_DRAW);
// setup colors
var colorBuffer = webgl.createBuffer();
webgl.bindBuffer(webgl.ARRAY_BUFFER, colorBuffer);
webgl.bufferData(webgl.ARRAY_BUFFER, new Float32Array(colors), webgl.STATIC_DRAW);
var color = webgl.getAttribLocation(shaderProgram, "color");
webgl.vertexAttribPointer(color, 3, webgl.FLOAT, false ,0,0);
对于使用多个不同缓冲区且打算实时的应用程序,流程是在初始化阶段创建和设置缓冲区,然后仅绑定缓冲区并在动画循环期间设置顶点属性指针。
<!doctype html>
<html>
<body>
<canvas id ="ctx" width = "300" height = "300"></canvas>
<script>
//Getting Webgl Context
var ctx = document.getElementById("ctx");
var webgl = ctx.getContext("experimental-webgl");
/*Creating Shader*/
//Vertex Code
var vertexCode =
'attribute vec3 coordinates;'+
'attribute vec3 color;'+
'varying vec3 vColor;'+
'void main(void) {' +
' gl_Position = vec4(coordinates, 1.0);' +
'vColor = color;'+
'}';
//Creating Shader Object
var vertexShader = webgl.createShader(webgl.VERTEX_SHADER);
//Assigning the Source
webgl.shaderSource(vertexShader, vertexCode);
//Compiling the Source
webgl.compileShader(vertexShader);
//Fragment Shader Code
var fragmentCode ='precision mediump float;'+
'varying vec3 vColor;'+
'void main(void) {'+
'gl_FragColor = vec4(vColor, 1.);'+
'}';
//Creating Shader Object
var fragmentShader = webgl.createShader(webgl.FRAGMENT_SHADER);
//Assigning the Source
webgl.shaderSource(fragmentShader, fragmentCode);
//Compiling the Source
webgl.compileShader(fragmentShader);
//Creating Program to store Shader
var shaderProgram = webgl.createProgram();
//Attaching the shaders
webgl.attachShader(shaderProgram, vertexShader);
webgl.attachShader(shaderProgram, fragmentShader);
//linking the Program
webgl.linkProgram(shaderProgram);
//using the Program
webgl.useProgram(shaderProgram);
//Defining geometry
var vertices = [
-0.5,0.5,0.0,
-0.5,-0.5,0.0,
0.5,-0.5,0.0,
0.5,0.5,0.0
];
var colors = [0,0,1, 1,0,0, 0,1,0, 1,0,1,];
indices = [3,2,1,3,1,0];
// setup positions
var VextexBuffer = webgl.createBuffer();
webgl.bindBuffer(webgl.ARRAY_BUFFER, VextexBuffer);
webgl.bufferData(webgl.ARRAY_BUFFER, new Float32Array(vertices), webgl.STATIC_DRAW);
var coord = webgl.getAttribLocation(shaderProgram,"coordinates");
webgl.vertexAttribPointer(coord, 3, webgl.FLOAT, false ,0,0);
// setup indices
var IndexBuffer = webgl.createBuffer();
webgl.bindBuffer(webgl.ELEMENT_ARRAY_BUFFER, IndexBuffer);
webgl.bufferData(webgl.ELEMENT_ARRAY_BUFFER, new Uint16Array(indices), webgl.STATIC_DRAW);
// setup colors
var colorBuffer = webgl.createBuffer();
webgl.bindBuffer(webgl.ARRAY_BUFFER, colorBuffer);
webgl.bufferData(webgl.ARRAY_BUFFER, new Float32Array(colors), webgl.STATIC_DRAW);
var color = webgl.getAttribLocation(shaderProgram, "color");
webgl.vertexAttribPointer(color, 3, webgl.FLOAT, false ,0,0);
//enabling the attributes
webgl.enableVertexAttribArray(coord);
webgl.enableVertexAttribArray(color);
//Unbind Array
/*Drawing the Triangle*/
//Clearing the Colour
webgl.clearColor(.5,.5,.5,1);
//Enabling the depth test
webgl.enable(webgl.DEPTH_TEST);
//Clearing colour nuffer bit
webgl.clear(webgl.COLOR_BUFFER_BIT);
//Setting a viewport
webgl.viewport(0,0,ctx.width,ctx.height);
//Draw the triangle
webgl.drawElements(webgl.TRIANGLES,indices.length,webgl.UNSIGNED_SHORT,0);
</script>
</body>
</html>
&#13;