JSFiddle - React, Tailwind, and code Playground
by Shriken
HTML
<canvas id="canvas" width=200 height=200></canvas>
CSS
canvas {
border-style: solid;
border-color: black;
border-width: 1px;
}
JavaScript
var arc = function (ctx, a, b, o, r) {
var t1 = Math.atan2(a[1] - o[1], a[0] - o[0]);
var t2 = Math.atan2(b[1] - o[1], b[0] - o[0]);
ctx.beginPath();
ctx.arc(o[0], o[1], r, t1, t2);
ctx.stroke();
};
var canvas = document.getElementById("canvas");
var ctx = canvas.getContext("2d");
ctx.fillStyle = "rgb(255,0,0)";
ctx.strokeStyle = "rgb(0,150,0)";
ctx.lineWidth = 4;
var STEPS = 60;
var PAUSE = 30;
var PAUSE_PT = STEPS * 5 / 12;
var R = 60;
var CNTPT = [100, 80];
var ancpt = [100, 20];
var varpt = [160, 80];
var animate = function (i) {
ctx.clearRect(0, 0, 200, 200);
var I;
if (i < PAUSE_PT) I = i;
else if (i < PAUSE_PT + PAUSE) I = PAUSE_PT;
else I = i - PAUSE;
var t = Math.PI * 2 * (I / STEPS - 1/4);
var cntpt = null;
var r = null;
varpt = [CNTPT[0] + Math.cos(t) * R, CNTPT[1] + Math.sin(t) * R];
if (I > PAUSE_PT) {
var q = Math.sqrt(Math.pow(ancpt[0] - varpt[0], 2) +
Math.pow(ancpt[1] - varpt[1], 2));
r = (q / 2) / Math.sin(Math.PI * 2 / 6);
var dir = [(varpt[1] - ancpt[1]) / q, (ancpt[0] - varpt[0]) / q];
var avg = [(ancpt[0] + varpt[0]) / 2, (ancpt[1] + varpt[1]) / 2];
cntpt = [avg[0] - Math.sqrt(r * r - q * q / 4) * dir[0],
avg[1] - Math.sqrt(r * r - q * q / 4) * dir[1]];
}
arc(ctx, ancpt, varpt, cntpt == null ? CNTPT : cntpt, r == null ? R : r);
setTimeout(function () {
animate((i + 1) % (STEPS + PAUSE))
}, 15);
}
animate(0);