Skip to content

Instantly share code, notes, and snippets.

@tsur
Created August 16, 2015 19:50
Show Gist options
  • Save tsur/639004948e83891b8c13 to your computer and use it in GitHub Desktop.
Save tsur/639004948e83891b8c13 to your computer and use it in GitHub Desktop.
magen-david
<div class="rotation-slider">
<input type="range" min="0" max="10" step="0.1" value="0">
<p></p>
</div>
<canvas/>
function init(){
const [canvas, context] = getCanvas();
setSize(canvas);
setBackground(context);
setListeners();
draw(context, 150);
}
function setListeners(){
document.querySelector('input[type="range"]').addEventListener('change', event => {
setRotationSpeed(parseFloat(event.target.value));
});
}
function draw(context, side){
drawMagenInf(context, side, () => drawMagenSup(context, side, () => drawMagenJoin(context, side, () => drawMagenRotation(context, side))));
}
function getRotationSpeed(){
return window.rotationSpeed || 0.5;
}
function setRotationSpeed(speed){
window.rotationSpeed = speed;
}
function getMagenSup(side){
const center = {x:window.innerWidth/2, y: window.innerHeight/2};
const height = side * (Math.sqrt(3)/2);
//const height = Math.sqrt((3/4)*side*side);
const _side = side/2;
const p1 = {x:center.x+_side, y: center.y};
const p2 = {x:center.x, y: center.y-height};
const p3 = {x:center.x-_side, y: center.y};
return [p1,p2,p3];
}
function getMagenInf(side){
const center = {x:window.innerWidth/2, y: window.innerHeight/2};
const height = side * (Math.sqrt(3)/2);
const _side = side/2;
const p1 = {x:center.x+_side, y: center.y};
const p2 = {x:center.x, y: center.y+height};
const p3 = {x:center.x-_side, y: center.y};
return [p1,p2,p3];
}
function drawMagenSup(context, side, fn){
const [p1,p2,p3] = getMagenSup(side);
drawTriangle(context, p1, p2, p3, fn);
}
function drawMagenInf(context, side, fn){
const [p1,p2,p3] = getMagenInf(side);
drawTriangle(context, p1, p2, p3, fn);
}
function drawMagenRotation(context, side, deg=0){
context.save();
context.translate( window.innerWidth/2, window.innerHeight/2);
context.rotate(deg * 0.0174532925199432957);
context.translate( -window.innerWidth/2, - window.innerHeight/2 );
const [supP1, supP2, supP3] = getMagenSup(side);
const [infP1, infP2, infP3] = getMagenInf(side);
const step = 40;
supP1.y += step;
supP2.y += step;
supP3.y += step;
infP1.y -= step;
infP2.y -= step;
infP3.y -= step;
drawRawTriangle(context, supP1, supP2, supP3);
drawRawTriangle(context, infP1, infP2, infP3);
context.restore();
deg += getRotationSpeed();
window.requestAnimationFrame(()=>{
setBackground(context);
drawMagenRotation(context, side, deg);
});
}
function drawMagenJoin(context, side, fn, step=0){
const [supP1, supP2, supP3] = getMagenSup(side);
const [infP1, infP2, infP3] = getMagenInf(side);
step += 2;
supP1.y += step;
supP2.y += step;
supP3.y += step;
infP1.y -= step;
infP2.y -= step;
infP3.y -= step;
drawRawTriangle(context, supP1, supP2, supP3);
drawRawTriangle(context, infP1, infP2, infP3);
if(step > 40){
return fn();
}
window.requestAnimationFrame(()=>{
setBackground(context);
drawMagenJoin(context, side, fn, step);
});
}
function drawRawTriangle(context, p1, p2, p3){
_drawLine(context, p1.x, p1.y, p2.x, p2.y);
_drawLine(context, p2.x, p2.y, p3.x, p3.y);
_drawLine(context, p3.x, p3.y, p1.x, p1.y);
}
function drawTriangle(context, p1, p2, p3, fn){
drawLine(context, p1, p2, () => {
drawLine(context, p2, p3, () => {
drawLine(context, p3, p1, fn);
});
});
}
function _drawLine(context, x, y, x2, y2){
context.beginPath();
context.moveTo(x, y);
context.lineTo(x2, y2);
context.lineWidth = 1;
context.strokeStyle = 'rgba(255,255,255,0.9)';
context.stroke();
}
function drawLine(context, p1, p2, fn, step = 0){
step += 0.05;
const newX = p1.x + ((p2.x - p1.x) * step);
const newY = p1.y + ((p2.y - p1.y) * step);
_drawLine(context, p1.x, p1.y, newX, newY);
if(step > 1){
_drawLine(context, p1.x, p1.y, p2.x, p2.y);
return fn();
} else{
window.requestAnimationFrame(()=>{
drawLine(context, p1, p2, fn, step);
});
}
}
function setBackground(context){
context.fillStyle = "rgba(0, 0, 0, 0.95)";
context.fillRect (0, 0, window.innerWidth, window.innerHeight);
}
function setSize(canvas){
canvas.width = window.innerWidth;
canvas.height = window.innerHeight;
}
function getCanvas(){
const canvas = document.querySelector('canvas');
return [canvas, canvas.getContext('2d')];
}
window.addEventListener('load', event => init());
body {
margin:0;
padding:0;
background-color: #000;
}
.rotation-slider{
position:absolute;
top:0;
z-index: 10;
padding: 15px;
}
input[type=range] {
/*removes default webkit styles*/
-webkit-appearance: none;
/*fix for FF unable to apply focus style bug */
border: 1px solid white;
/*required for proper track sizing in FF*/
width: 300px;
}
input[type=range]::-webkit-slider-runnable-track {
width: 300px;
height: 5px;
background: #000;
border: none;
border-radius: 3px;
}
input[type=range]::-webkit-slider-thumb {
-webkit-appearance: none;
border: none;
height: 16px;
width: 16px;
border-radius: 50%;
background: white;
margin-top: -4px;
}
input[type=range]:focus {
outline: none;
}
input[type=range]:focus::-webkit-slider-runnable-track {
background: #ccc;
}
input[type=range]::-moz-range-track {
width: 300px;
height: 5px;
background: #ddd;
border: none;
border-radius: 3px;
}
input[type=range]::-moz-range-thumb {
border: none;
height: 16px;
width: 16px;
border-radius: 50%;
background: goldenrod;
}
/*hide the outline behind the border*/
input[type=range]:-moz-focusring{
outline: 1px solid white;
outline-offset: -1px;
}
input[type=range]::-ms-track {
width: 300px;
height: 5px;
/*remove bg colour from the track, we'll use ms-fill-lower and ms-fill-upper instead */
background: transparent;
/*leave room for the larger thumb to overflow with a transparent border */
border-color: transparent;
border-width: 6px 0;
/*remove default tick marks*/
color: transparent;
}
input[type=range]::-ms-fill-lower {
background: #777;
border-radius: 10px;
}
input[type=range]::-ms-fill-upper {
background: #ddd;
border-radius: 10px;
}
input[type=range]::-ms-thumb {
border: none;
height: 16px;
width: 16px;
border-radius: 50%;
background: goldenrod;
}
input[type=range]:focus::-ms-fill-lower {
background: #888;
}
input[type=range]:focus::-ms-fill-upper {
background: #ccc;
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment