0

I've been working on some studies with animation and with the help of some jquery I've created an animation where when a square that is moved by the users mouse through a mousemove jquery event collides with another square on the screen (square2) thats been hit will move a certain length and if the hitbox is struck near its edges than the object is expected to rotate. The problem ive been running into is that when the object rotates it creates a pseudo afterimage of the outline of the square. At first I thought that I could remove the afterImage by using a clearRect() method to encompass a larger area around square2, but doing this not only leaves my problem unresolved, but also makes a part of my first square invisible which is undesired. If anybody could hep me figure out where ive gone wrong in this code, would definitely appreciate it fellas.

    var canvas = document.getElementById('canvas');
    var ctx = canvas.getContext('2d');
    canvas.width = 1000;
    canvas.height = 400;
    var width = canvas.width;
    var height = canvas.height;
    var particles = [];

    var mouseSize = 50;
    var isColliding = false;
    var mouseX;
    var mouseY;
    var animationForward = false;

    function particle() {
      var particle = {
        originX: width / 2,
        originY: height / 2,
        x: width / 2,
        y: height / 2,
        size: 30,
        centerPointX: this.x + this.size / 2,
        centerPointY: this.y + this.size / 2,
        decay: .98,
        vx: 0,
        vy: 0,
        rotate: 0,
        vr: 0,

        draw: function() {
          ctx.fillStyle = "white";
          ctx.fillRect(this.x, this.y, this.size, this.size)

          //           rotation logic
// method found at http://stackoverflow.com/questions/2677671/how-do-i-rotate-a-single-object-on-an-html-5-canvas
          function drawImageRot(x, y, width, height, deg) {
            ctx.clearRect(x, y, width, height);
            //Convert degrees to radian 
            var rad = deg * Math.PI / 180;
            //Set the origin to the center of the image
            ctx.translate(x + width / 2, y + height / 2);
            //Rotate the canvas around the origin
            ctx.rotate(rad);
            //draw the image    
            ctx.fillRect(width / 2 * (-1), height / 2 * (-1), width, height);
            //reset the canvas  
            ctx.rotate(rad * (-1));
            ctx.translate((x + width / 2) * (-1), (y + height / 2) * (-1));
          }

          //check for collision
          if (mouseX < particles[0].x + particles[0].size &&
            mouseX + mouseSize > particles[0].x &&
            mouseY < particles[0].y + particles[0].size &&
            mouseSize + mouseY > particles[0].y) {
            isColliding = true;
          } else {
            isColliding = false;
          }

          //controlling  velocity dependending on location of collision.
          if (isColliding) {
            //x axis
            animationForward = true;

            // checking below to see if mouseRect is hitting near the center of particleRect. 
            // if it hits near center the vy or vx will not be as high depending on direction and if it               //does not than we will make square rotate
            if (mouseX < this.x) {
              this.vr = 3 + Math.random() * 10
              if (mouseX + mouseSize / 2 > this.x) {
                this.vx = 0 + Math.random() * 2;
              } else {
                this.vx = 3 + Math.random() * 3;

              }
            } else {
              this.vr = -3 - Math.random() * 10
              if (mouseX + mouseSize / 2 < this.x + this.size) {
                this.vx = 0 - Math.random() * 2;
              } else {
                this.vx = -3 - Math.random() * 3;
              }
            }

            //y axis checking

            if (mouseY < this.y) {
              if (mouseY + mouseSize / 2 > this.y) {
                this.vy = 0 + Math.random() * 2;
              } else {
                this.vy = 3 + Math.random() * 3;
              }
            } else {
              if (mouseY + mouseSize / 2 < this.y + this.size) {
                this.vy = 0 - Math.random() * 2;
              } else {
                this.vy = -3 - Math.random() * 3;
              }
            }

          }

          //decay all motions each frame while animation is forward
          if (animationForward) {
            this.vx *= this.decay;
            this.vy *= this.decay;
            this.vr *= this.decay;
          }

          //when animation is done, set all velocities to 0
          if (this.x != this.originX && Math.abs(this.vx) < .1 && this.y != this.originY && Math.abs(this.vy) < .1) {
            animationForward = false;
            this.vx = 0;
            this.vy = 0;
            this.vr = 0
          }

          //x check to see if animation over. if it is slowly put square back to original location
          if (this.x != this.originX && !animationForward) {
            if (this.x > this.originX) {
              this.vx = -1;
            }
            if (this.x < this.originX) {
              this.vx = 1;
            }

            if (this.x > this.originX && this.x - this.originX < 1) {
              this.vx = 0;
              this.x = this.originX;
            }
            if (this.x < this.originX && this.originX - this.x < 1) {
              this.vx = 0;
              this.x = this.originX;
            }
          }
          //           end x collison

          //           y check to see if animation over

          if (this.y != this.originX && !animationForward) {
            if (this.y > this.originY) {
              this.vy = -1;
            }
            if (this.y < this.originY) {
              this.vy = 1;
            }

            if (this.y > this.originY && this.y - this.originY < 1) {
              this.vy = 0;
              this.y = this.originY;
            }
            if (this.y < this.originY && this.originY - this.y < 1) {
              this.vy = 0;
              this.y = this.originY;
            }
          }
          //           end y collison

          //check rotation

          if (this.rotate != 0 && !animationForward) {
            this.rotate = Math.round(this.rotate);

            if (this.rotate < 0) {
              if (this.rotate < -300) {
                this.rotate += 10
              } else if (this.rotate < -200) {
                this.rotate += 7
              } else if (this.rotate < -125) {
                this.rotate += 5
              } else if (this.rotate < -50) {
                this.rotate += 3
              } else {
                this.rotate++;
              }
            } else {
              if (this.rotate > 300) {
                this.rotate -= 10;
              } else if (this.rotate > 200) {
                this.rotate -= 7
              } else if (this.rotate > 125) {
                this.rotate -= 5
              } else if (this.rotate > 50) {
                this.rotate -= 3
              } else {
                this.rotate--;
              }
            }

          }

          // move the rect based off of previous set conditions and make square rotate if edges hit

          this.x += this.vx;
          this.y += this.vy;
          this.rotate += this.vr;
          drawImageRot(this.x, this.y, this.size, this.size, this.rotate);

          //           boundary control

          if (this.x + this.size > width || this.x < 0) {
            this.vx = -this.vx * 2
          }
          if (this.y + this.size > height || this.y < 0) {
            this.vy = -this.vy * 2
          }

        }
      }
      return particle;
    }

    function createParticles() {
      particles.push(particle())

      //wouldnt be too hard to put more particles. would have to go back and change the isColliding and animationForward global variable and make each object have their own to check. also would have to go back and implement for loops wherever i mention an element in my array
    }

    createParticles();

    function draw() {
      console.log(particles[0].rotate);
      ctx.clearRect(0, 0, width, height);

      ctx.fillStyle = 'white';
      ctx.fillRect(mouseX, mouseY, mouseSize, mouseSize);

      particles[0].draw();

      requestAnimationFrame(draw);
    }

    $("#canvas").mousemove(function(event) {
      mouseX = event.pageX;
      mouseY = event.pageY;
    })

    window.onload = draw();

1 Answers1

0

I think your problem is right here:

   draw: function() {
      ctx.fillStyle = "white";
      ctx.fillRect(this.x, this.y, this.size, this.size)
      ....

You are drawing 2nd shape here. Comment this lines and pseudo image should be gone.

Vladimir M
  • 4,403
  • 1
  • 19
  • 24
  • hmm now thats interesting, looking back at the code it does make sense that that would need to be removed since i draw the square in the drawImagerot function anyway. thank you so much! – d springer Sep 20 '16 at 07:35