【问题标题】:Rotate arrow, that is drawing on mousemove旋转箭头,即在 mousemove 上绘图
【发布时间】:2013-06-27 09:55:57
【问题描述】:

我想在 mousemove 上画一个箭头,下面的代码画了一个水平箭头。但我希望它从开始绘图点旋转到结束绘图点。我搜索了很多,但没有找到解决方案,可能是因为我不熟悉在画布上绘图。

drawArrowMove: function(e, _self)
    {
      var width    = e.w ;
      var height   = e.h ;
      var arrowW   = 0.35 * width;
      var arrowH   = 0.75 * height;
      var p1       = {x: 0,              y: (height-arrowH)/2};
      var p2       = {x: (width-arrowW), y: (height-arrowH)/2};
      var p3       = {x: (width-arrowW), y: 0};
      var p4       = {x: width,          y: height/2};
      var p5       = {x: (width-arrowW), y: height};
      var p6       = {x: (width-arrowW), y: height-((height-arrowH)/2)};
      var p7       = {x: 0,              y: height-((height-arrowH)/2)};

      _self.ctxTemp.beginPath();
      _self.ctxTemp.moveTo(p1.x, p1.y);
      _self.ctxTemp.lineTo(p2.x, p2.y); // end of main block
      _self.ctxTemp.lineTo(p3.x, p3.y); // topmost point
      _self.ctxTemp.lineTo(p4.x, p4.y); // endpoint
      _self.ctxTemp.lineTo(p5.x, p5.y); // bottommost point
      _self.ctxTemp.lineTo(p6.x, p6.y); // end at bottom point
      _self.ctxTemp.lineTo(p7.x, p7.y);
      _self.ctxTemp.fillStyle = 'black';
      _self.ctxTemp.fill();
      _self.ctxTemp.stroke();
    }

【问题讨论】:

    标签: html canvas mousemove


    【解决方案1】:

    这是在斜线上绘制箭头的方法

    以任意角度绘制箭头的最简单方法是使用画布的旋转功能。

    您使用Math.atan 函数根据直线的斜率计算适当的角度。

    // calculate the radian angle of the line from [x1,y1] to [x2,y2]
    var radianAngle=Math.atan((y2-y1)/(x2-x1));
    
    // adjust the angle based on line slope 
    radianAngle+=((x2>x1)?90:-90)*Math.PI/180;
    

    然后就可以画线了:

    // draw the line
    ctx.beginPath();
    ctx.moveTo(x1,y1);
    ctx.lineTo(x2,y2);
    ctx.stroke();
    

    最后通过旋转上下文来附加箭头。

    // rotate the canvas context to the appropriate angle
    ctx.rotate(radianAngle);
    

    请注意,由于您已经旋转了画布本身,因此您只需将箭头绘制成水平的。简单的!

    // save the un-transformed state of the context
    ctx.save();
    
    ctx.beginPath();
    
    // translate to the end of the line
    ctx.translate(x2,y2);
    
    // rotate to the appropriate angle
    ctx.rotate(radianAngle);
    
    // draw the arrowhead
    ctx.moveTo(0,0);
    ctx.lineTo(8,20);
    ctx.lineTo(-8,20);
    ctx.closePath();
    ctx.fill();
    
    // when done drawing on the rotated context, set it back to its untransformed state
    ctx.restore();
    

    这是代码和小提琴:http://jsfiddle.net/m1erickson/CQDww/

    <!doctype html>
    <html>
    <head>
    <link rel="stylesheet" type="text/css" media="all" href="css/reset.css" /> <!-- reset css -->
    <script type="text/javascript" src="http://code.jquery.com/jquery.min.js"></script>
    
    <style>
        body{ background-color: ivory; }
        canvas{border:1px solid red;}
    </style>
    
    <script>
    $(function(){
    
        var canvas=document.getElementById("canvas");
        var context=canvas.getContext("2d");
    
        function Line(x1,y1,x2,y2){
            this.x1=x1;
            this.y1=y1;
            this.x2=x2;
            this.y2=y2;
        }
        Line.prototype.drawWithArrowheads=function(ctx){
    
            // arbitrary styling
            ctx.strokeStyle="blue";
            ctx.fillStyle="blue";
            ctx.lineWidth=3;
    
            // draw the line
            ctx.beginPath();
            ctx.moveTo(this.x1,this.y1);
            ctx.lineTo(this.x2,this.y2);
            ctx.stroke();
    
            // draw the starting arrowhead
            var startRadians=Math.atan((this.y2-this.y1)/(this.x2-this.x1));
            startRadians+=((this.x2>this.x1)?-90:90)*Math.PI/180;
            this.drawArrowhead(ctx,this.x1,this.y1,startRadians);
            // draw the ending arrowhead
            var endRadians=Math.atan((this.y2-this.y1)/(this.x2-this.x1));
            endRadians+=((this.x2>this.x1)?90:-90)*Math.PI/180;
            this.drawArrowhead(ctx,this.x2,this.y2,endRadians);
    
        }
        Line.prototype.drawArrowhead=function(ctx,x,y,radians){
            ctx.save();
            ctx.beginPath();
            ctx.translate(x,y);
            ctx.rotate(radians);
            ctx.moveTo(0,0);
            ctx.lineTo(8,20);
            ctx.lineTo(-8,20);
            ctx.closePath();
            ctx.fill();
            ctx.restore();
        }
    
        // create a new line object
        var line=new Line(50,50,150,150);
        // draw the line
        line.drawWithArrowheads(context);
    
    }); // end $(function(){});
    </script>
    
    </head>
    
    <body>
        <canvas id="canvas" width=300 height=300></canvas>
    </body>
    </html>
    

    【讨论】:

      猜你喜欢
      • 2021-01-27
      • 1970-01-01
      • 2013-07-05
      • 1970-01-01
      • 1970-01-01
      • 2023-04-03
      • 1970-01-01
      • 1970-01-01
      • 2018-05-06
      相关资源
      最近更新 更多