Look at the code
<style>
canvas{
width: 100%;
max-width: 370px;
}
</style>
<div>
<button id="startAnimationButton">Start animation</button>
<button id="stopAnimationButton">Stop animation</button>
</div>
<canvas id="canvas" width="370" height="310"></canvas>
<script>
let canvas, ctx, startButton, stopButton, w, h, requestId;
let animationIncrement = 1/100, animationDirection = -1, scaleValue = 1, translateValueW = 0, translateValueH = 0;
const load = () => {
//event listeners
startButton = document.querySelector("#startAnimationButton");
startButton.addEventListener('click', start, false);
stopButton = document.querySelector("#stopAnimationButton");
stopButton.addEventListener('click', stop, false);
//canvas settingd
canvas = document.querySelector("#canvas");
ctx = canvas.getContext("2d");
w = canvas.width;
h = canvas.height;
requestId = requestAnimationFrame(animateLadybird);
}
window.onload = load;
const animateLadybird = (timestamp) => {
//clear canvas
//ctx.fillRect(0, 0, w, h);
ctx.clearRect(0, 0, w, h);
//draw stuff
drawLogo(scaleValue, translateValueW, translateValueH);
//animate the bug
if(scaleValue < 0 || scaleValue > 1){
animationDirection = -animationDirection;
}
scaleValue += animationDirection*animationIncrement;
translateValueW += (-animationDirection)*w*animationIncrement/2;
translateValueH += (-animationDirection)*h*animationIncrement/2;
console.log(translateValueW);
//recursive call
//if(requestId) cancelAnimationFrame(requestId);
requestId = requestAnimationFrame(animateLadybird);
}
//callbacks
const start = (event) => {
if(requestId) cancelAnimationFrame(requestId);
requestId = requestAnimationFrame(animateLadybird);
}
const stop = (event) => {
if(requestId) cancelAnimationFrame(requestId);
}
const drawLogo = (s=1,x=0,y=0) => {//drawing the logo
//console.log("drawing logo");
//save first and restore at the end
ctx.save();
//scale animation
ctx.translate(x,y);
ctx.scale(s,s);
// #body
ctx.save();
ctx.beginPath();
ctx.fillStyle = 'rgb(221, 148, 32)';
ctx.moveTo(184.427000, 35.014000);
ctx.bezierCurveTo(242.917269, 35.014000, 290.333000, 94.109279, 290.333000, 167.007000);
ctx.bezierCurveTo(290.333000, 239.904721, 242.917269, 299.000000, 184.427000, 299.000000);
ctx.bezierCurveTo(125.936731, 299.000000, 78.521000, 239.904721, 78.521000, 167.007000);
ctx.bezierCurveTo(78.521000, 94.109279, 125.936731, 35.014000, 184.427000, 35.014000);
ctx.fill();
ctx.restore();
// #separator_body
ctx.save();
ctx.beginPath();
ctx.strokeStyle = 'rgb(255, 255, 255)';
ctx.lineWidth = 16.000000;
ctx.lineCap = 'round';
ctx.miterLimit = 10;
ctx.moveTo(110.969000, 84.500000);
ctx.bezierCurveTo(110.969000, 102.462000, 145.031000, 121.000000, 185.893000, 121.000000);
ctx.lineTo(185.161000, 121.000000);
ctx.bezierCurveTo(226.019000, 121.000000, 257.970000, 103.211000, 257.970000, 85.250000);
ctx.stroke();
ctx.restore();
// #separator_head
ctx.save();
ctx.beginPath();
ctx.strokeStyle = 'rgb(255, 255, 255)';
ctx.lineWidth = 16.000000;
ctx.lineCap = 'round';
ctx.miterLimit = 10;
ctx.moveTo(184.000000, 292.000000);
ctx.lineTo(184.000000, 130.000000);
ctx.stroke();
ctx.restore();
// #legs
// #leg_1
ctx.save();
ctx.beginPath();
ctx.strokeStyle = 'rgb(221, 148, 32)';
ctx.lineWidth = 16.000000;
ctx.lineCap = 'round';
ctx.lineJoin = 'bevel';
ctx.miterLimit = 10;
ctx.moveTo(39.250000, 89.820000);
ctx.lineTo(80.500000, 107.191000);
ctx.lineTo(88.750000, 132.463000);
ctx.stroke();
ctx.restore();
// #leg_2
ctx.save();
ctx.beginPath();
ctx.strokeStyle = 'rgb(221, 148, 32)';
ctx.lineWidth = 16.000000;
ctx.lineCap = 'round';
ctx.lineJoin = 'bevel';
ctx.miterLimit = 10;
ctx.moveTo(331.004000, 89.820000);
ctx.lineTo(289.754000, 107.191000);
ctx.lineTo(281.504000, 132.463000);
ctx.stroke();
ctx.restore();
// #leg_3
ctx.save();
ctx.beginPath();
ctx.strokeStyle = 'rgb(221, 148, 32)';
ctx.lineWidth = 16.000000;
ctx.lineCap = 'round';
ctx.lineJoin = 'bevel';
ctx.miterLimit = 10;
ctx.moveTo(61.042000, 298.726000);
ctx.lineTo(61.238000, 253.951000);
ctx.lineTo(93.956000, 236.299000);
ctx.stroke();
ctx.restore();
// #leg_4
ctx.save();
ctx.beginPath();
ctx.strokeStyle = 'rgb(221, 148, 32)';
ctx.lineWidth = 16.000000;
ctx.lineCap = 'round';
ctx.lineJoin = 'bevel';
ctx.miterLimit = 10;
ctx.moveTo(308.945000, 298.726000);
ctx.lineTo(308.750000, 253.951000);
ctx.lineTo(276.032000, 236.299000);
ctx.stroke();
ctx.restore();
// #leg_5
ctx.save();
ctx.beginPath();
ctx.strokeStyle = 'rgb(221, 148, 32)';
ctx.lineWidth = 16.000000;
ctx.lineCap = 'round';
ctx.lineJoin = 'bevel';
ctx.miterLimit = 10;
ctx.moveTo(359.834000, 193.660000);
ctx.lineTo(325.649000, 164.742000);
ctx.lineTo(290.982000, 178.170000);
ctx.stroke();
ctx.restore();
// #leg_6
ctx.save();
ctx.beginPath();
ctx.strokeStyle = 'rgb(221, 148, 32)';
ctx.lineWidth = 16.000000;
ctx.lineCap = 'round';
ctx.lineJoin = 'bevel';
ctx.miterLimit = 10;
ctx.moveTo(9.982000, 193.660000);
ctx.lineTo(44.167000, 164.742000);
ctx.lineTo(78.834000, 178.170000);
ctx.stroke();
ctx.restore();
// #aerials
// #aerialleft
ctx.save();
ctx.beginPath();
ctx.strokeStyle = 'rgb(221, 148, 32)';
ctx.lineWidth = 16.000000;
ctx.lineCap = 'round';
ctx.lineJoin = 'bevel';
ctx.miterLimit = 10;
ctx.moveTo(169.250000, 38.014000);
ctx.lineTo(132.250000, 20.080000);
ctx.lineTo(98.000000, 10.335000);
ctx.stroke();
ctx.restore();
// #aerial_right
ctx.save();
ctx.beginPath();
ctx.strokeStyle = 'rgb(221, 148, 32)';
ctx.lineWidth = 16.000000;
ctx.lineCap = 'round';
ctx.lineJoin = 'bevel';
ctx.miterLimit = 10;
ctx.moveTo(202.000000, 38.014000);
ctx.lineTo(239.000000, 20.080000);
ctx.lineTo(273.250000, 10.335000);
ctx.stroke();
ctx.restore();
//restore the context after drawing on the canvas
ctx.restore();
}
</script>