-3

Link to JSFiddle for entire code: https://jsfiddle.net/u4mk0gdt/

I read the Mozilla docs on save() and restore() and I thought that "save" saved the current state of the entire canvas and "restore" restored the canvas to the most recent "save" state. Hence I placed the saves and restores in such a way that it should clear the white line that is drawn to canvas after is is drawn. However when I run this code the white line is never cleared from the canvas and is drawn continually without clearing.

ctx.restore();
ctx.save(); // <--should save blank canvas

//DRAW LINE
ctx.moveTo(tMatrix.x1, tMatrix.y1);
ctx.lineTo(w/2,h/2);
ctx.strokeStyle = "white";
ctx.stroke();
ctx.restore(); // <-- should restore to the "save()" above
ctx.save(); // <-- <--should save blank canvas again
Ghoyos
  • 604
  • 2
  • 7
  • 18
  • 1
    _"saves the entire state of the canvas by pushing the current state onto a stack. The drawing state that gets saved onto a stack consists of: The current **transformation matrix**. The current **clipping region**. The current **dash list**. The current **values of the following attributes**: `strokeStyle`, `fillStyle`, `globalAlpha`, `lineWidth`, `lineCap`, `lineJoin`, `miterLimit`, `lineDashOffset`, `shadowOffsetX`, `shadowOffsetY`, `shadowBlur`, `shadowColor`, `globalCompositeOperation`, `font`, `textAlign`, `textBaseline`, `direction`, `imageSmoothingEnabled`"_ – Andreas Oct 25 '21 at 16:20
  • [How to clear the canvas for redrawing](https://stackoverflow.com/questions/2142535/how-to-clear-the-canvas-for-redrawing) – Andreas Oct 25 '21 at 16:24
  • 1
    `save` does not store the canvas content, only the canvas properties. – Sebastian Simon Oct 25 '21 at 16:38

1 Answers1

1

As you can see, I made a lot of modifications to your code:

console.log("rotating_recs");
// create canvas and add resize
var canvas, ctx;

function createCanvas() {
  canvas = document.createElement("canvas");
  canvas.style.position = "absolute";
  canvas.style.left = "0px";
  canvas.style.top = "0px";
  canvas.style.zIndex = 1000;
  document.body.appendChild(canvas);
}

function resizeCanvas() {
  if (canvas === undefined) {
    createCanvas();
  }
  canvas.width = window.innerWidth;
  canvas.height = window.innerHeight;
  ctx = canvas.getContext("2d");
}

resizeCanvas();
window.addEventListener("resize", resizeCanvas);



var Player = function(x, y, height, width, rot) {
  this.x = x;
  this.y = y;
  this.width = width;
  this.height = height;
  this.rot = rot;
  this.objWinX = 0; //translate the window object and then apply to this
  this.objWinY = 0;

  this.draw = function() {

    //rotate by user.rot degrees, from the players center
    ctx.translate(this.x + this.width / 2, this.y + this.height / 2)
    ctx.rotate(this.rot * Math.PI / 180)
    ctx.translate(-this.x - this.width / 2, -this.y - this.height / 2)

    ctx.fillStyle = "grey";
    ctx.fillRect(this.x, this.y, this.height, this.width);

    ctx.translate(this.x + this.width / 2, this.y + this.height / 2)
    ctx.rotate(-this.rot * Math.PI / 180)
    ctx.translate(-this.x - this.width / 2, -this.y - this.height / 2)
  }
}

var user = new Player(0, 0, 40, 40, 0);

var user2 = new Player(0, 0, 40, 40, 0);

let rot = 0;


function update(time) {

  var w, h;
  w = canvas.width; // get canvas size incase there has been a resize
  h = canvas.height;
  ctx.clearRect(0, 0, w, h); // clear the canvas

  //MIDDLE RECT
  /*
  if you don't want this you can just translate by w/2 and h/2, but I would recommend just making the p     layers position the middle
  */

  user.x = w / 2 - 20;
  user.y = h / 2 - 20;

  user.rot += 0.5 // or whatever speed
  user.draw(); //draw player -- look at the draw function I added some stuff

  //LINE
  /*
  I don't know what you are trying to do, but I just drew the line to the user2's position,
  if this doesn't work for your scenario you can change it back
  */
  ctx.beginPath()
  ctx.moveTo(user2.x + user2.width/2, user2.y + user2.height/2);
  ctx.lineTo(w / 2, h / 2);
  ctx.strokeStyle = "white";
  ctx.stroke();

  //FAST SPIN RECT

  /*
  There are multiple ways to do this, the one that I think you should do, is actually change the position of user two, this uses some very simple trigonometry, if you know this, this is a great way to do this, if not, you can do it how you did previously, and just translate to the center, rotate, and translate back. Similar to what I did with the player draw function. I am going to demonstrate the trig way here:
  */
  user2.rot += 5
  rot += 2;
  
  user2.x = w/2 + (w/2) * Math.cos(rot * (Math.PI/180))
  user2.y = h/2 + (w/2) * Math.sin(rot * (Math.PI/180))
  user2.draw();

  //RED RECT
  ctx.fillStyle = 'red';
  ctx.fillRect(140, 60, 40, 40);

  requestAnimationFrame(update); // do it all again
}
requestAnimationFrame(update);

While I think you should add some of these modifications into you code, they are not super necessary. To fix you line problem, all you had to do was add ctx.beginPath() before you drew it. The demonstration that I made was not very good (hence demonstration), and you probably shouldn't use it exactly, but definitely look over it. The modified code for you line drawing would look like:

    //LINE
    ctx.beginPath()
    ctx.moveTo(tMatrix.x1, tMatrix.y1);
    ctx.lineTo(w/2,h/2);
    ctx.strokeStyle = "white";
    ctx.stroke();
    ctx.restore();
    ctx.save();

Hope this helps :D

Sorry for bad spelling

Ryan Grube
  • 185
  • 1
  • 11