webgl学习笔记四-动画

来源:互联网 发布:美容连锁软件 编辑:程序博客网 时间:2024/05/16 15:24

写在前面

建议先阅读下前面我的三篇文章。

webgl学习笔记一-绘图单点

webgl学习笔记二-绘图多点

webgl学习笔记三-平移旋转缩放

  下面我们将讲解下如何让一个正方形动起来~不断擦除和重绘正方形,并且每次重绘时轻微地改变其角度。

demo

  • 吊下胃口

image

  • html
<!DOCTYPE html><html lang="en"><head>    <meta charset="UTF-8">    <title>Title</title></head><script src="../../lib/cuon-matrix.js"></script><body><canvas id="canvas" width="200px" height="200px"></canvas></body></html>
  • JavaScript
<script>    // 顶点着色器程序    var VSHADER_SOURCE =        'attribute vec4 a_Position;\n' +        'uniform mat4 u_ModelMatrix;\n' +        'void main() {\n' +        '  gl_Position = u_ModelMatrix * a_Position;\n' +        '}\n';    // 片元着色器程序    var FSHADER_SOURCE =        'void main() {\n' +        '  gl_FragColor = vec4(1.0, 0.0, 0.0, 1.0);\n' +        '}\n';    // Rotation angle (degrees/second)    var ANGLE_STEP = 45.0;    function main() {        // init gl        var gl = initCanvas();        // Initialize shaders        var shaderProgram = initShader(gl, VSHADER_SOURCE, FSHADER_SOURCE).program;        // Write the positions of vertices to a vertex shader        var n = initVertexBuffers(gl, shaderProgram);        if (n < 0) {            console.log('Failed to set the positions of the vertices');            return;        }        // Specify the color for clearing <canvas>        gl.clearColor(0, 0, 0, 1);        // Get storage location of u_ModelMatrix        var u_ModelMatrix = gl.getUniformLocation(shaderProgram, 'u_ModelMatrix');        if (!u_ModelMatrix) {            console.log('Failed to get the storage location of u_ModelMatrix');            return;        }        // Current rotation angle        var currentAngle = 0.0;        // Model matrix        var modelMatrix = new Matrix4();        // Start drawing        var tick = function () {            currentAngle = animate(currentAngle);  // Update the rotation angle            draw(gl, n, currentAngle, modelMatrix, u_ModelMatrix);   // Draw the triangle            requestAnimationFrame(tick, canvas); // Request that the browser ?calls tick        };        tick();    }    // init cavas webgl context    function initCanvas() {        //获取canvas元素        var canvas = document.getElementById('canvas');        //获取绘制二维上下文        var gl = canvas.getContext('webgl');        if (!gl) {            console.log("Failed");            return null;        }        return gl;    }    // init shader    function initShader(gl, vshader_source, fshader_source) {        //编译着色器        var vertShader = gl.createShader(gl.VERTEX_SHADER);        gl.shaderSource(vertShader, vshader_source);        gl.compileShader(vertShader);        var fragShader = gl.createShader(gl.FRAGMENT_SHADER);        gl.shaderSource(fragShader, fshader_source);        gl.compileShader(fragShader);        //合并程序        var program = gl.createProgram();        gl.attachShader(program, vertShader);        gl.attachShader(program, fragShader);        gl.linkProgram(program);        gl.useProgram(program);        return {            program: program        }    }    function initVertexBuffers(gl, shaderProgram) {        var vertices = new Float32Array([            -0.5, 0.5, -0.5, -0.5, 0.5, 0.5, 0.5, -0.5        ]);        var n = 4;   // The number of vertices        // Create a buffer object        var vertexBuffer = gl.createBuffer();        if (!vertexBuffer) {            console.log('Failed to create the buffer object');            return -1;        }        // Bind the buffer object to target        gl.bindBuffer(gl.ARRAY_BUFFER, vertexBuffer);        // Write date into the buffer object        gl.bufferData(gl.ARRAY_BUFFER, vertices, gl.STATIC_DRAW);        // Assign the buffer object to a_Position variable        var a_Position = gl.getAttribLocation(shaderProgram, 'a_Position');        if (a_Position < 0) {            console.log('Failed to get the storage location of a_Position');            return -1;        }        gl.vertexAttribPointer(a_Position, 2, gl.FLOAT, false, 0, 0);        // Enable the assignment to a_Position variable        gl.enableVertexAttribArray(a_Position);        return n;    }    function draw(gl, n, currentAngle, modelMatrix, u_ModelMatrix) {        // Set the rotation matrix        modelMatrix.setRotate(currentAngle, 0, 0, 1);        modelMatrix.translate(0.35, 0, 0);        // Pass the rotation matrix to the vertex shader        gl.uniformMatrix4fv(u_ModelMatrix, false, modelMatrix.elements);        // Clear <canvas>        gl.clear(gl.COLOR_BUFFER_BIT);        // Draw the rectangle        gl.drawArrays(gl.TRIANGLE_STRIP, 0, n);    }    // Last time that this function was called    var g_last = Date.now();    function animate(angle) {        // Calculate the elapsed time        var now = Date.now();        var elapsed = now - g_last;        g_last = now;        // Update the current rotation angle (adjusted by the elapsed time)        var newAngle = angle + (ANGLE_STEP * elapsed) / 1000.0;        return newAngle %= 360;    }    main();</script>
原创粉丝点击