A. Mehlen
A. Mehlen

Reputation: 135

HTML Canvas draw shapes

I am trying to create a little paint component in a Vue project. Actually I can draw free hand lines and live rectangles. My problem is how and where to correctly save the current shape and to redraw the entire canvas with all shapes.

HTML Canvas

<div id="app">
  <canvas id="editCanvas" width="400px" height="400px" style="border: 1px solid black;"></canvas>
</div>

Vue Application

clearCanvas() {
  // clear canvas
  this.canvas.editCanvasContext.clearRect(
    0,
    0,
    this.canvas.editCanvas.width,
    this.canvas.editCanvas.height
  );
},
handleMouseEvent(e) {
  if (e.type === "mousedown") {
    this.canvas.prevX = this.canvas.currX;
    this.canvas.prevY = this.canvas.currY;
    this.canvas.currX = e.offsetX;
    this.canvas.currY = e.offsetY;
    this.canvas.mouseClicked = true;
    this.draw(true);
  }
  if (e.type === "mouseup") {
    this.canvas.mouseClicked = false;
  }
  if (e.type === "mouseout") {
    this.canvas.mouseClicked = false;
  }
  if (e.type === "mousemove") {
    if (this.canvas.mouseClicked) {
      this.canvas.prevX = this.canvas.currX;
      this.canvas.prevY = this.canvas.currY;
      this.canvas.currX = e.offsetX;
      this.canvas.currY = e.offsetY;
      this.draw();
    }
  }
},
draw(dot) {
  this.canvas.editCanvasContext.beginPath();
  this.canvas.editCanvasContext.globalCompositeOperation = this.canvas.globalCompositeOperation;
  if (dot) {
    this.start = {
      x: this.canvas.currX,
      y: this.canvas.currY
    };
    this.canvas.editCanvasContext.fillStyle = this.canvas.fillStyle;
    this.canvas.editCanvasContext.fillRect(
      this.canvas.currX,
      this.canvas.currY,
      2,
      2
    );
  } else {
    this.canvas.editCanvasContext.beginPath();
    switch (this.canvas.currentShape) {
      case "line":
        this.drawLine(
          this.canvas.prevX,
          this.canvas.prevY,
          this.canvas.currX,
          this.canvas.currY
        );
        break;
      case "rectangle":
        this.drawRectangle(
          this.start.x,
          this.start.y,
          this.canvas.currX - this.start.x,
          this.canvas.currY - this.start.y
        );
        break;
      case "fillrectangle":
        this.drawFillRectangle(
          this.start.x,
          this.start.y,
          this.canvas.currX - this.start.x,
          this.canvas.currY - this.start.y
        );
        break;
    }
    this.canvas.editCanvasContext.strokeStyle = this.canvas.fillStyle;
    this.canvas.editCanvasContext.lineWidth = this.canvas.lineWidth;
    this.canvas.editCanvasContext.stroke();
  }
  this.canvas.editCanvasContext.closePath();
},
drawLine(startX, startY, endX, endY) {
  this.canvas.editCanvasContext.moveTo(startX, startY);
  this.canvas.editCanvasContext.lineTo(endX, endY);
},
drawRectangle(startX, startY, endX, endY) {
  this.clearCanvas();
  this.canvas.editCanvasContext.rect(startX, startY, endX, endY);
},
drawFillRectangle(startX, startY, endX, endY) {
  this.clearCanvas();
  this.canvas.editCanvasContext.fillRect(startX, startY, endX, endY);
}

}

The entire code

Thanks for your help :-)

Best Regards, AMehlen

Upvotes: 2

Views: 136

Answers (1)

Mark Redman
Mark Redman

Reputation: 24515

Looking at your code, you are drawing directly to the canvas on various user events, directly to the canvas. This is similar to adding paint to a real canvas, where "once it's on its on". What really needs to happen is your user actions should create objects that describe what those actions should do, eg create a rectangle object with all the coordinates and colours then paint that to the canvas.. you would need manage all these objects in code conceptually and paint all the objects when required and if you wanted to save your work, you would need to save those object for re-drawing later.

You best bet would be to re-use a library that does this eg: fabric.js http://fabricjs.com

This will enable you to concentrate on your vue.js component/app rather than the basic drawing tools and object model concepts that will take a lot of time?

Upvotes: 1

Related Questions