WebGL

WebGL 3D(绘制点)

2018-12-15  本文已影响4人  WebGiser
image.png image.png image.png image.png

示例:在鼠标点击位置绘制点,并根据点的象限,设置不同的颜色。

<!DOCTYPE HTML>
<head>
    
</head>
<html>
    <body onload="main()">
        <canvas id="webgl" width="500" height="500" style="border: 1px solid #ff0000;">
            
        </canvas>

        <script type="text/javascript">
            //顶点着色器程序
            var VSHADER_SOURCE = 
                    'attribute vec4 a_Position;\n'+
                    'attribute float a_PointSize;\n'+
                    'void main(){\n'+
                        'gl_Position = a_Position;\n'+
                        'gl_PointSize = a_PointSize;\n'+
                    '}\n';

            //片元着色器程序
            var FSHADER_SOURCE =
                    'precision mediump float;\n'+
                    'uniform vec4 u_FragColor;\n'+
                    'void main(){'+
                        'gl_FragColor = u_FragColor;\n'+
                    '}\n';

            function main(){
                //获取<canvas>元素
                var canvas = document.getElementById("webgl");
                if(!canvas){
                    console.log('error');
                    return;
                }

                //获取绘制三维图形的绘图上下文
                var gl = canvas.getContext('webgl');

                // 创建着色器对象
                const fShader = gl.createShader(gl.FRAGMENT_SHADER);
                const vShader = gl.createShader(gl.VERTEX_SHADER);

                // 将着色器源码写入对象
                gl.shaderSource(vShader, VSHADER_SOURCE);
                gl.shaderSource(fShader, FSHADER_SOURCE);

                // 编译着色器
                gl.compileShader(vShader);
                gl.compileShader(fShader);

                // 创建程序
                const program = gl.createProgram();

                // 程序绑定着色器
                gl.attachShader(program, vShader);
                gl.attachShader(program, fShader);

                // 链接程序
                gl.linkProgram(program);

                // 使用程序
                gl.useProgram(program);


                //获取attribute变量的存储位置
                var a_Position = gl.getAttribLocation(program,'a_Position');
                var a_PointSize = gl.getAttribLocation(program,'a_PointSize');
                if(a_Position < 0 ){
                    console.log('Failed to get the storage location of a_Position');
                    return;
                }
                if(a_PointSize < 0 ){
                    console.log('Failed to get the storage location of a_PointSize');
                    return;
                }

                //获取uniform变量的存储位置
                var u_FragColor = gl.getUniformLocation(program, 'u_FragColor');
                if(!u_FragColor){
                    console.log('Failed to get the storage location of u_FragColor');
                    return;
                }
                

                //监听鼠标单击事件的响应函数
                canvas.onmousedown = function(ev){
                    click(ev, gl, canvas, a_Position, a_PointSize, u_FragColor);
                };

                
                var g_points = [];  //存储鼠标点击位置数组
                var g_colors = [];  //存储颜色数组

                function click(ev, gl, canvas, a_Position, a_PointSize, u_FragColor){
                    gl.clear(gl.COLOR_BUFFER_BIT);

                    //浏览器客户区坐标
                    var x = ev.clientX;
                    var y = ev.clientY;

                    //canvas坐标
                    var rect = ev.target.getBoundingClientRect();
                    var canvas_x = x - rect.left;
                    var canvas_y = y - rect.top;

                    //WebGL坐标
                    var gl_x = (canvas_x - canvas.width/2)/(canvas.width/2);
                    var gl_y = (canvas.height/2 - canvas_y)/(canvas.height/2);

                    g_points.push([gl_x,gl_y]);

                    //根据象限位置设置不同的颜色
                    if(gl_x > 0.0 && gl_y > 0.0){
                        g_colors.push([1.0, 0.0, 0.0, 1.0]);
                    }else if(gl_x < 0.0 && gl_y > 0.0){
                        g_colors.push([0.0, 1.0, 0.0, 1.0]);
                    }else if(gl_x < 0.0 && gl_y < 0.0){
                        g_colors.push([0.0, 0.0, 1.0, 1.0]);
                    }else{
                        g_colors.push([0.5, 0.5, 0.5, 1.0]);
                    }

                    for(var i=0; i<g_points.length; i++){
                        var xy_position = g_points[i];
                        var rgba = g_colors[i];

                        //将顶点位置传输给attribute变量
                        gl.vertexAttrib3f(a_Position, xy_position[0], xy_position[1], 0.0);
                        gl.vertexAttrib1f(a_PointSize,10.0);

                        //将片元颜色传输给uniform变量
                        gl.uniform4f(u_FragColor, rgba[0], rgba[1], rgba[2], rgba[3]);

                        // 绘制点
                        gl.drawArrays(gl.POINTS, 0, 1);
                    }
                };
            }
        </script>
    </body>
</html>
image.png
上一篇 下一篇

猜你喜欢

热点阅读