使用Javascript Math以圆形图案创建破折号

时间:2015-11-11 04:58:41

标签: javascript loops math canvas trigonometry

我对下面的代码了解不多,我希望有人一点一点地分解它。



$(function() {
  var centerX = 200,
    centerY = 200,
    radius = 100,
    width = 15,
    angles = []

  function draw() {
    var ctx = document.getElementById("canvas").getContext("2d");
    var angle;
    //why 180 
    for (var i = 0; i < 180; i += 10) {
      //is the "angle" increasing on every iteration? can you demostrate this please
      angle = 2.1 + (i * Math.PI / 90);
      angles.push(angle)
      ctx.beginPath();
      ctx.moveTo(
        centerX + Math.sin(angle) * radius,
        centerY + Math.cos(angle) * radius
      );
      ctx.lineTo(
        centerX + Math.sin(angle) * (radius + width),
        centerY + Math.cos(angle) * (radius + width)
      );
      ctx.closePath();
      ctx.stroke();
    }
  }
  draw()
  console.log(angles)
  var str = "";
  angles.forEach(function(e, i) {
    str += " " + i + " : " + e + "|| Math.sin = " + Math.sin(e) + "|| Math.sin * radius = " + Math.sin(e) * radius
    $(".display").html(str)
  })

})
&#13;
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.0.2/jquery.min.js"></script>
<canvas id="canvas" width="400" height="400"></canvas>
<div class="display"></div>
&#13;
&#13;
&#13;

对于此部分angle = 2.1 + (i * Math.PI / 90);,我看到i递增10,作者将其乘以Math.PI / 90,等于0.0348888888888889。我知道Math.PI是180度,但没有180/90。我们将数量增加2.1。我无法将所有部分组合在一起。

并且在for(var i = 0; i < 180; i += 10){为什么作者选择了180.我知道180度是半圈是他们为什么选择它?

我总是在其他代码中看到人们使用cos作为x坐标,使用sin作为y坐标。看起来作者并没有像我刚才描述的那样使用它。你能详细说明吗?

任何帮助将不胜感激!

编辑:我也想知道我们何时使用for(var i = 0; i < 180; i += 10){我们在一个完整的圆圈中得到破折号,当我i < 90时,我们得到一个圆圈,但半圆不直就像在x或y轴上的角度一样。为什么它不在轴上?为什么它是一个角度?

2 个答案:

答案 0 :(得分:3)

让我们从 SOH CAH TOA link)开始。

给定直角三角形(一边是90度)..

  • 三角形有一个角度。
  • 三角形的一侧与角度相反( O )。
  • 三角形有接触角度和直角的一面,称为( A )相邻边。
  • Triangle有一个叫做Hypotenuse( H )的一面。这也是接触角度的一侧,但与对面不成直角。

enter image description here

现在找到你需要知道的任何一方,最小角度和另一侧。

Ex:你知道角度Q是40度,而斜边是10.那么相邻是什么;

查看 SOH CAH TOA 。我看到我知道H,需要知道A. CAH有两者。所以我选择了CAH。

Cos Q = Adj/Hyp

现在,如果你把这个三角形放在圈内。然后Hyp将成为半径,如下所示:

enter image description here

Cos Q = Adj/radius

现在要画一条从圆圈向外的线,我需要知道一条线的起点和终点,我需要让这些点与圆角对齐。

要获得起点,我可以使用圆的边界。

所以为了获得x,y得到圆边界上的一个点,我进一步求解这个等式。

Cos Q * radius = Adj

Cos Q * radius = x //adj is x

&安培;为... ...

SOH
Sin Q = Opp/Hyp
Sin Q = Opp/radius
Sin Q * radius = Opp
Sin Q * radius = y

所以

x = Cos Q * radius
y = Sin Q * radius

or in js..

var x = Math.cos(angle) * radius;
var y = Math.sin(angle) * radius;

现在我们有一个跟随圆圈边界的点。但是为了像我们想要的那样,我们需要两点。

这段代码只是放入一个更大的半径,这会产生更大的圆圈,从而得到我们需要的第二点。

 ctx.lineTo(
        centerX + Math.sin(angle) * (radius + width),
        centerY + Math.cos(angle) * (radius + width));

代码格式化为明确:

var centerX = 200,
    centerY = 200,
    radius = 100,
    width = 15,
    angles = [],
    ctx = document.getElementById("canvas").getContext("2d");

function draw() {
    var angle;

    for (var i = 0; i < 180; i += 10) {

        angle = 2.1 + (i * Math.PI / 90);

        ctx.beginPath();

        ctx.moveTo(
        centerX + Math.sin(angle) * radius,
        centerY + Math.cos(angle) * radius);

        ctx.lineTo(
        centerX + Math.sin(angle) * (radius + width),
        centerY + Math.cos(angle) * (radius + width));

        ctx.closePath();
        ctx.stroke();
    }

}

draw();

答案 1 :(得分:1)

你引用的代码有点尴尬。

要围绕一个圆圈进行导航,将i从0增加到360(如360度)会更加清晰。

for(var i=0; i<360; i++){

相反,编码器从0增加到180,但是他们通过将将度数转换为弧度的公式加倍来补偿将360度减半。

// this is the usual conversion of degrees to radians
var radians = degrees * Math.PI / 180;

// This "compensating" conversion is used by the coder
// This doubling of the conversion compensates for halving "i" to 180
var radians = degrees * Math.PI / 90;

更清晰的迭代因子看起来像这样:

// the conversion factor to turn degrees into radians
var degreesToRadians = Math.PI / 180;

// navigate 360 degrees around a circle
for(var i=0; i<360; i++){

    // use the standard degrees-to-radians conversion factor
    var angle = i * degreesToRadians;

    // This roughly rotates the angle so that it starts
    // at the 12 o'clock position on the circle
    // This is unnecessary if you're navigating completely
    // around the circle anyway (then it doesn't matter where you start)
    angle += 2.1;

    ....

}

和...

代码是有意绘制从圆周向外辐射的线条。编码器根本没有试图跟随周长。