曲线

路径也可能会包含曲线。绘制曲线更加复杂。

quadraticCurveTo方法绘制到某一个点的曲线。为了确定一条线段的曲率,需要设定一个控制点以及一个目标点。设想这个控制点会吸引这条线段,使其成为曲线。线段不会穿过控制点。但是,它起点与终点的方向会与两个点到控制点的方向平行。见下例:

  1. <canvas></canvas>
  2. <script>
  3. let cx = document.querySelector("canvas").getContext("2d");
  4. cx.beginPath();
  5. cx.moveTo(10, 90);
  6. // control=(60,10) goal=(90,90)
  7. cx.quadraticCurveTo(60, 10, 90, 90);
  8. cx.lineTo(60, 10);
  9. cx.closePath();
  10. cx.stroke();
  11. </script>

我们从左到右绘制一个二次曲线,曲线的控制点坐标为(60,10),然后画出两条穿过控制点并且回到线段起点的线段。绘制的结果类似一个星际迷航的图章。你可以观察到控制点的效果:从下端的角落里发出的线段朝向控制点并向他们的目标点弯曲。

bezierCurve(贝塞尔曲线)方法可以绘制一种类似的曲线。不同的是贝塞尔曲线需要两个控制点而不是一个,线段的每一个端点都需要一个控制点。下面是描述贝塞尔曲线的简单示例。

  1. <canvas></canvas>
  2. <script>
  3. let cx = document.querySelector("canvas").getContext("2d");
  4. cx.beginPath();
  5. cx.moveTo(10, 90);
  6. // control1=(10,10) control2=(90,10) goal=(50,90)
  7. cx.bezierCurveTo(10, 10, 90, 10, 50, 90);
  8. cx.lineTo(90, 10);
  9. cx.lineTo(10, 10);
  10. cx.closePath();
  11. cx.stroke();
  12. </script>

两个控制点规定了曲线两个端点的方向。两个控制点相对两个端点的距离越远,曲线就会越向这个方向凸出。

由于我们没有明确的方法,来找出我们希望绘制图形所对应的控制点,所以这种曲线还是很难操控。有时候你可以通过计算得到他们,而有时候你只能通过不断的尝试来找到合适的值。

arc方法是一种沿着圆的边缘绘制曲线的方法。 它需要弧的中心的一对坐标,半径,然后是起始和终止角度。

我们可以使用最后两个参数画出部分圆。角度是通过弧度来测量的,而不是度数。这意味着一个完整的圆拥有的弧度,或者2*Math.PI(大约为 6.28)的弧度。弧度从圆心右边的点开始并以顺时针的方向计数。你可以以 0 起始并以一个比大的数值(比如 7)作为终止值,画出一个完整的圆。

  1. <canvas></canvas>
  2. <script>
  3. let cx = document.querySelector("canvas").getContext("2d");
  4. cx.beginPath();
  5. // center=(50,50) radius=40 angle=0 to 7
  6. cx.arc(50, 50, 40, 0, 7);
  7. // center=(150,50) radius=40 angle=0 to ½π
  8. cx.arc(150, 50, 40, 0, 0.5 * Math.PI);
  9. cx.stroke();
  10. </script>

上面这段代码绘制出的图形包含了一条从完整圆(第一次调用arc)的右侧到四分之一圆(第二次调用arc)的左侧的直线。arc与其他绘制路径的方法一样,会自动连接到上一个路径上。你可以调用moveTo或者开启一个新的路径来避免这种情况。