• canvas图形库


    总结了一些canvas绘制2d图形的方法,记录在博客中,以便需要的同学参考,也便于日后加深记忆。

    1. 圆角矩形:

    如上图:w表示矩形的宽,h表示矩形的高,r表示矩形圆角的半径。整个矩形在画布中,(0,0)点相对于画布的位置平移了(x,y)的距离。

    方法:

    1. 分别先算出每一段圆弧的圆心的位置、起点和终点; (圆弧:context.arc(x, y, r, sAngle, eAngle, counterclockwise))

    2. 然后再分别计算每一条线段终点的位置; (线段:起context.moveTo(x, y),始context.lineTo(x, y))

    3. 最后将这些圆弧和线段链接起来; (由于先绘制的圆弧,若不设置线段的起点,将使用圆弧的终点作为线段的起点)

    4. 在将圆弧平移至画布中心; (平移:context.translate(x, y))

    5. 设置矩形的轮廓颜色; (轮廓颜色:context.strokeStyle = "color")

    6. 绘制矩形。

    <!DOCTYPE html>
    <html>
        <head>
            <meta charset="UTF-8">
            <title>画多个不同形状的圆弧</title>
        </head>
        <body>
            <canvas id="canvas" style="border: 1px solid #70ad47; margin: 50px auto; display: block;">
                您的浏览器不支持canvas标签,请更换更新的浏览器。
            </canvas>
            <script type="text/javascript">
                window.onload = function() {
                    var canvas = document.getElementById("canvas"); // 先获取画布
                    canvas.width = 800; // 将画布设置为800px宽
                    canvas.height = 800; // 将画布设置为800px高
                    var context = canvas.getContext("2d"); // 获取画布的上下文环境,进行2d绘图
                    drawRadiusRect(context, 150, 150, 500, 500, 50); // 调用drawRadiusRect()函数
                }            
                
                /*
                 * 传入六个参数:
                 * 第一个参数表示格式化上下文,只是为了便于简写
                 * 第二个参数和第三个参数设置平移的位置,为了把这个圆角矩形放置在画布中心的位置
                 * 第四个参数和第五个参数分别设置了矩形的宽和高
                 * 第六个参数设置了圆角的半径
                 */
                function drawRadiusRect(ctx, x, y, width, height, r) {
                    ctx.save(); // 保存绘图状态
                    ctx.translate(x, y); // 相对于画布的原点,矩形的原点平移了(x,y)
                    // 将矩形平移后,只剩下四个参数
                    pathRadiusRect(ctx, width, height, r); // 调用pathRadiusRect()函数
                    ctx.strokeStyle = "#ff2d2d"; // 设置绘图的轮廓颜色(设置绘图状态)
                    ctx.stroke();  // 进行绘制
                    ctx.restore(); // 恢复绘图状态
                }
                
                /*
                 * 分别先算出每一段圆弧的圆心的位置、起点和终点
                 * 然后再分别计算每一条线段终点的位置
                 * 最后将这些圆弧和线段链接起来
                 * */
                function pathRadiusRect(ctx, w, h, r) {
                    ctx.beginPath(); // 开始绘图的路径
                    ctx.arc(w - r, h - r, r, 0, Math.PI*0.5);
                    ctx.lineTo(r, h);
                    ctx.arc(r, h - r, r, Math.PI*0.5, Math.PI);
                    ctx.lineTo(0, r);
                    ctx.arc(r, r, r, Math.PI, Math.PI*1.5);
                    ctx.lineTo(w - r, 0);
                    ctx.arc(w - r, r, r, Math.PI*1.5, Math.PI*2);
                    ctx.lineTo(w, h - r);
                    ctx.closePath(); // 关闭绘图路径(好进行下一次绘制,使其不收影响)
                }
                
                /*window.onload = function() {
                    var canvas = document.getElementById("canvas");
                    canvas.width = 800;
                    canvas.height = 800;
                    var context = canvas.getContext("2d");context.beginPath();
                    
                    // 使用最原始的方法,分别画出这些线段和弧(缺点是如果要更改半径或尺寸,要更改很多值,不便于复用)
                    context.arc(150, 150, 50, Math.PI, Math.PI*1.5);
                    context.lineTo(650, 100);
                    context.strokeStyle = "#ccc"
                    context.stroke();
                    
                    context.beginPath();
                    context.arc(650, 150, 50, Math.PI*1.5, Math.PI*2);
                    context.lineTo(700, 650);
                    context.strokeStyle = "#ccc"
                    context.stroke();
                    
                    context.beginPath();
                    context.arc(650, 650, 50, 0, Math.PI*0.5);
                    context.lineTo(150, 700);
                    context.strokeStyle = "#ccc"
                    context.stroke();
                    
                    context.beginPath();
                    context.arc(150, 650, 50, Math.PI*0.5, Math.PI);
                    context.lineTo(100, 150);
                    context.strokeStyle = "#ccc"
                    context.stroke();
                }*/
            </script>
        </body>
    </html>

    说明:在这端代码中,有arc()方法,此方法用于绘制圆弧,一共六个参数,分别是:(圆弧圆心的)横坐标,纵坐标,(圆弧)半径,起点,终点,(圆弧绘制)方向。方向为可选参数,若省略,则为 false,表示按照顺时针绘制,当为true时,表示逆时针绘制。

    对canvas绘图中单位圆的分析:

    图中分别示意了0-1.5π的一段圆弧,和0.5π-π的一段圆弧。

    其中0-1.5π的一段圆弧为逆时针,方向为true.0.5π-π的一段圆弧为顺时针,方向为false。

    2. 五角星:

    对五角星进行分析:

    1. 五角星的五个外点在大的外圆上,五个内点在小的内圆上。

    2. 每两个相邻内点与圆心的夹角为72deg。

    3. 根据上面对单位圆的分析,从0位置开始,第一个内点为54deg,第一个外点为18deg。

    4. 由上面的分析可以使用循环得出每一个点的位置(依然从0位置开始逆时针开始算为第一个点)。

    <!DOCTYPE html>
    <html>
        <head>
            <meta charset="utf-8" />
            <title>画五角星</title>
        </head>
        <body>
            <canvas id="canvas" width="800" height="800" style="border: 1px solid #999; margin: 50px auto; display: block;">
                您的浏览器不支持canvas标签,请更换浏览器。
            </canvas>
            <script>                        
                window.onload = function() {
                    var canvas = document.getElementById("canvas");
                    var context = canvas.getContext("2d");
                    /* 参数的意思分别为"上下文环境",
                     * "五角星外面五个点所在圆的半径","五角星里面五个点所在圆的半径",
                     * "五角星两个圆的圆心在画布中的偏移量横坐标(为正)","五角星两个圆的圆心在画布中的偏移量纵坐标(为负)",
                     * "五角星的旋转角度(顺时针,即为负)"
                     * */
                    drawStar(context, 300, 150, 400, 400, 72);
                }
                function drawStar(ctx, R, r, x, y, rot) {
                    // 五角星路径的开始
                    ctx.beginPath();
                    for (var i = 0; i < 5; i++) {
                        /* 以i=0,即第一个点为例:
                         * 大圆的点相对于正x轴偏移了18deg,Math.sin和Math.cos计算的是弧度,所以要将角度转换为弧度。
                         * 再分别乘以R,计算出相对于画布左上角位置的x和y坐标,
                         * 再分别加上x,和y作为距离画布左上角的偏移
                         * */
                        ctx.lineTo(Math.cos((18 + 72 * i - rot) / 180 * Math.PI) * R + x,
                                   -Math.sin((18 + 72 * i - rot) / 180 * Math.PI) * R + y);
                        ctx.lineTo(Math.cos((54 + 72 * i - rot) / 180 * Math.PI) * r + x,
                                   -Math.sin((54 + 72 * i - rot) / 180 * Math.PI) * r + y);                               
                        
                    }
                    // 闭合五角星路径
                    ctx.closePath();
                    // 为五角星路径设置宽和颜色
                    ctx.lineWidth = 5;
                    ctx.strokeStyle = "#000";
                    // 绘制五角星
                    ctx.stroke();
                }
            </script>
        </body>
    </html>

    3. 箭头

    箭头由六条线段顺次连接而成,一共七个点,可将七个点标出,便能组合成一个箭头。

    <!DOCTYPE html>
    <html>
        <head>
            <meta charset="utf-8" />
            <title>画箭头</title>
        </head>
        <body>
            <canvas id="canvas" style="border: 1px solid #999; margin: 50px auto; display: block;">
                您的浏览器不支持canvas标签,请更换浏览器。
            </canvas>
            <script>
                window.onload = function() {
                    var canvas = document.getElementById("canvas");
                    var context = canvas.getContext("2d");
                    canvas.width = 200;
                    canvas.height = 200;
                    drawArrow(context, 100)
                }
                /*
                 * drawArrow一共四个参数
                 * 第一个表示上下文环境的变量名,第二个参数表示箭头第一条线段的长度
                 * 第三个参数为可选参数,表示轮廓的宽度,第四个参数是可选参数,表示轮廓的颜色
                 */
                function drawArrow(ctx, w, lineWidth/*optional*/, strokeColor/*optional*/) {
                    ctx.save();
                    ctx.beginPath();
                    ctx.translate((2*canvas.width - 3*w)/4, (3*canvas.height + w)/6);
                    drawPathArrow(ctx, w, lineWidth/*optional*/, strokeColor/*optional*/)
                    ctx.closePath();
                    ctx.restore();
                    
                }
                function drawPathArrow(ctx, w, lineWidth/*optional*/, strokeColor/*optional*/) {
                    ctx.moveTo(0, 0);
                    ctx.lineTo(w, 0);
                    ctx.lineTo(w, w/3);
                    ctx.lineTo(3*w/2, -w/6);
                    ctx.lineTo(w, -2*w/3);
                    ctx.lineTo(w, -w/3);
                    ctx.lineTo(0, -w/3);
                    
                    ctx.lineWidth = lineWidth || 5;
                    ctx.strokeStyle = strokeColor || "#000";
                    ctx.stroke();
                }
            </script>
        </body>
    </html>

    总结:

    以上三个实例用到了 canvas 的三个属性和方法,canvas.width, canvas.height, canvas.getContext("2d")。

    也用到了上下文环境 context 的诸多属性和方法,context.beginPath(), context.closePath(), context.save(), context.restore(), context.moveTo(), context.lineTo(), context.lineWidth, context.strokeStyle, context.stroke(), context.translate(), context.arc(x, y ,r, sAngle, eAngle, counterclockwise);

    后面将持续更新...

  • 相关阅读:
    ASP.NET MVC 3.0(八): MVC 3.0 传递和保存你的Model
    ASP.NET MVC 3.0(十九): MVC 3.0 实例之使用开源控件实现表格排序和分页
    ASP.NET MVC 3.0(十二): MVC 3.0 使用自定义的Html控件
    ASP.NET MVC 3.0(十七): MVC 3.0 实例之表格中数据的筛选
    ASP.NET MVC 3.0 学习系列
    ASP.NET MVC 3.0(五): 入手Controller/Action
    ASP.NET MVC 3.0(十五): MVC 3.0 实例系列之表格的排序
    ASP.NET MVC 3.0(十): MVC 3.0 使用 Forms身份验证
    ASP.NET MVC 3.0(九): MVC 3.0 验证你的Model
    设计功能与界面的测试
  • 原文地址:https://www.cnblogs.com/xinjie-just/p/6485586.html
Copyright © 2020-2023  润新知