为什么即使将填充设置为“ rgba(0,0,0,0)”,最近绘制的圆弧仍具有黑色填充?

时间:2019-05-20 22:40:02

标签: javascript html5-canvas

我正在尝试添加一个边框为40px(笔触)且没有背景(填充)的圆

我已经开始使用它-即使我将其(以及所有其他像素)设置为“ rbg(0,0,0,0)”,它也是最近绘制的圆圈,其填充为黑色。 >

  public animate(milliseconds: any) {
    const elapsed = milliseconds - this.Configs.lastStep;
    this.Configs.lastStep = milliseconds;
    if (this.canvas) {
      this.ctx.clearRect(0, 0, this.canvas.width, this.canvas.height);
    }
    this.update(elapsed);
    this.ctx.fill();
    window.requestAnimationFrame(this.animate.bind(this));
  }

  public draw(milliseconds: number) {
    const colors = ["#270f36", "#632b6c", "#c76b98", "#f09f9c", "#fcc3a3"];

    this.ctx.save();
    for (let ring of this.rings) {
      this.ctx.beginPath();
      this.ctx.fillStyle = "rgba(255, 255, 255, 0)";
      this.ctx.strokeStyle = randomItemFromArray(colors);
      this.ctx.arc(ring.getOrigin.x, ring.getOrigin.y, ring.getRadius, 0, Math.PI * 2, false);
      this.ctx.lineWidth = 10;
      this.ctx.fill();
      this.ctx.stroke();
    }
   this.ctx.restore();
  }
  public update(elapsed: number) {
        this.draw(elapsed);
}

我希望所有环都是透明的-但是添加到rings数组中的最后一个总是黑色填充。

我很困惑-任何想法都将不胜感激。

Here is an example of what I am talking about

1 个答案:

答案 0 :(得分:2)

您正在通过ctx.fill()函数调用animate。此时,您将上下文的属性restore()修改为调用ctx.save()时的属性,并且fillStyle恢复为'black'。 但是,最后一个ctx.beginPath()之后所有笔操作所执行的当前activePath仍处于活动状态。这就是为什么它仅填充最后一个弧。

现在,如果您只想要笔触,只需删除所有,对fill()的调用,对fillStyle的任何引用现在都变得无关紧要。

最后要注意的是,ctx.save()ctx.restore()在这里只会造成伤害。 另外,由于lineWidth不变,因此只能在开始动画之前设置一次。
因此,您在draw方法中所需的就是

draw(milliseconds) {
  const colors = ["#270f36", "#632b6c", "#c76b98", "#f09f9c", "#fcc3a3"];

  for (let ring of this.rings) {
    this.ctx.beginPath();
    this.ctx.strokeStyle = randomItemFromArray(colors);
    this.ctx.arc(ring.getOrigin.x, ring.getOrigin.y, ring.getRadius, 0, Math.PI * 2, false);
    this.ctx.stroke();
  }
}

class Ring {
  constructor() {
    this.getOrigin = {
      x: (Math.random() * innerWidth / 4) + (innerWidth / 2),
      y: (Math.random() * innerHeight / 4) + (innerHeight / 2)
    };
    this.getRadius = (Math.random() * Math.min(innerHeight, innerWidth) / 4) + 50;
  }
}
class Drawer {
  constructor() {
    this.rings = Array.from({length: 8}, ()=>new Ring());
    this.canvas = document.querySelector('canvas');
    this.canvas.width = innerWidth;
    this.canvas.height = innerHeight;
    this.ctx = this.canvas.getContext('2d');
    this.ctx.lineWidth = 10;    
  }
animate(milliseconds) {
//    const elapsed = milliseconds - this.Configs.lastStep;
//    this.Configs.lastStep = milliseconds;
    if (this.canvas) {
      this.ctx.clearRect(0, 0, this.canvas.width, this.canvas.height);
    }
    this.update(0);    window.requestAnimationFrame(this.animate.bind(this));
  }
  draw(milliseconds) {
    const colors = ["#270f36", "#632b6c", "#c76b98", "#f09f9c", "#fcc3a3"];

    for (let ring of this.rings) {
      this.ctx.beginPath();
      this.ctx.strokeStyle = randomItemFromArray(colors);
      this.ctx.arc(ring.getOrigin.x, ring.getOrigin.y, ring.getRadius, 0, Math.PI * 2, false);
      this.ctx.stroke();
    }
  }
  update(elapsed) {
    this.draw(elapsed);
  }
}
const drawer = new Drawer();
drawer.animate();


function randomItemFromArray(arr) {
  return arr[(arr.length * Math.random()) | 0];
}
<canvas></canvas>