Robert Deniro Robert Deniro - 3 months ago 25
HTML Question

Restart Javascript Functions

I have this javascript code that has a few functions. It codes for a simple animation in the html

canvas
element.

I want it so that when I click on the html button with class
one
, the animation restarts.

I am not really sure how to go about this, and have tried a few ways but none seem to work

This is my javascript code:

var canvas = document.getElementById('canvas');
var c = canvas.getContext('2d'),

// Global variables
particles = {},
particleIndex = 0;
particleNum = 1;

// Context properties
c.fillStyle = "white";
c.fillRect(0,0,canvas.width,canvas.height);

// Particle (Square) properties
function Particle(){
this.x = canvas.width / 2;
this.y = canvas.height / 2;
this.vx = Math.random() * 10 - 5;
this.vy = Math.random() * 10 - 5;
this.gravity = 0.2;
particleIndex++;
particles[particleIndex] = this;
this.id = particleIndex;
this.life = 0;
this.maxLife = Math.random() * 100 + 100;
this.color = "hsla("+parseInt(Math.random()*360, 10)+",100%,50%, 0.2)";
}

// Drawing the particle
Particle.prototype.draw = function(){
this.x += this.vx;
this.y += this.vy;

if (Math.random() < 0.00001){
this.vx = Math.random() * 10 - 5;
this.vy = Math.random() * 10 - 5;
}

//Uncomment line below for gravity effect
//this.vy += this.gravity;

// Deletes particle if greater than or equal to its max life
this.life++;
if (this.life >= this.maxLife){
delete particles[this.id];
}
c.fillStyle = this.color;
c.fillRect(this.x, this.y, 10, 10);
};


// Animation Interval
setInterval(function(){
c.globalCompositeOperation = "source-over";
c.fillStyle = "rgba(0,0,0,0.05)";
c.fillRect(0,0,canvas.width,canvas.height);

c.globalCompositeOperation = "lighter";
for (var i = 0; i < particleNum; i++){
new Particle();
}

for (var i in particles){
particles[i].draw();
}
}, 15);


This is the html code for the canvas and button which triggers the canvas to be displayed:

<canvas width="400" height="250" class="canvas" id="canvas"></canvas>
<script src="canvas.js"></script>

<div class="buttons">
<button class="one">Canvas 1</button>
</div>


And this is the jQuery code to show the canvas element:

$('.one').click(function() {
$('.canvas').show();
});


I am wondering also, is there a simple way to do this in jQuery? Something like on click, if the canvas isn't displayed, show the canvas and start the animation, and if displayed, stop the animation and hide the canvas?

Thanks

Mx. Mx.
Answer

Just wrap your code in a function an rerun it when your button is clicked. Remember to clear the interval and other shared variables.

var tick, canvas = document.getElementById('canvas');
var doStuff = function(enable) {

  //clear the interval if set
  tick && clearInterval(tick);

  //dont restart
  if (!enable) return;

  var c = canvas.getContext('2d'),

    // Global variables
    particles = {},
    particleIndex = 0;
  particleNum = 1;

  // Context properties
  c.fillStyle = "white";
  c.fillRect(0, 0, canvas.width, canvas.height);

  // Particle (Square) properties
  function Particle() {
    this.x = canvas.width / 2;
    this.y = canvas.height / 2;
    this.vx = Math.random() * 10 - 5;
    this.vy = Math.random() * 10 - 5;
    this.gravity = 0.2;
    particleIndex++;
    particles[particleIndex] = this;
    this.id = particleIndex;
    this.life = 0;
    this.maxLife = Math.random() * 100 + 100;
    this.color = "hsla(" + parseInt(Math.random() * 360, 10) + ",100%,50%, 0.2)";
  }

  // Drawing the particle
  Particle.prototype.draw = function() {
    this.x += this.vx;
    this.y += this.vy;

    if (Math.random() < 0.00001) {
      this.vx = Math.random() * 10 - 5;
      this.vy = Math.random() * 10 - 5;
    }

    //Uncomment line below for gravity effect
    //this.vy += this.gravity;

    // Deletes particle if greater than or equal to its max life
    this.life++;
    if (this.life >= this.maxLife) {
      delete particles[this.id];
    }
    c.fillStyle = this.color;
    c.fillRect(this.x, this.y, 10, 10);
  };


  // Animation Interval 
  tick = setInterval(function() {
    c.globalCompositeOperation = "source-over";
    c.fillStyle = "rgba(0,0,0,0.05)";
    c.fillRect(0, 0, canvas.width, canvas.height);

    c.globalCompositeOperation = "lighter";
    for (var i = 0; i < particleNum; i++) {
      new Particle();
    }

    for (var i in particles) {
      particles[i].draw();
    }
  }, 15);
}

document.querySelector('button').addEventListener('click', function() {
  if (canvas.style.display === 'block') {
    doStuff();
    canvas.style.display = '';
  } else {
    doStuff(true);
    canvas.style.display = 'block';
  }
});
canvas {
  display: none;
}
<canvas width="400" height="250" class="canvas" id="canvas"></canvas>
<script src="canvas.js"></script>

<div class="buttons">
  <button class="one">Canvas 1</button>
</div>

Comments