Difference between revisions of "Template:Marburg/confetti"

Line 1: Line 1:
$(document).ready(function(){
+
var currentConfettiScript=document.scripts[document.scripts.length-1];$(document).ready(function(){var t=document.createElement("canvas");t.style.position="absolute",t.style.left="0",t.style.top="0",t.style.width="100%",t.style.height="100%",currentConfettiScript.parentElement.insertBefore(t,currentConfettiScript);var e=t.getContext("2d"),i=Date.now(),a=i,o=0,n=40;t.width=t.parentNode.clientWidth,t.height=t.parentNode.clientHeight;var r=!1;var l=[],s=.15,d=5.2,p=15.2,c=30;function h(t){t.radius=u(10,20),t.position=f(t.radius),t.rotation=u(0,360),t.velocity={x:u(d,p)*(1==u(0,2)?-1:1),y:u(d,p)*(1==u(0,2)?-1:1)},t.lifetime=u(3,5),t.spawnTime=i,t.color="rgb("+u(0,255)+", "+u(0,255)+", "+u(0,255)+")",t.alpha=0,t.fadeState=-1}function f(e){for(var i,a,o,n,r={x:u(0,t.width),y:u(0,15)},s=!0,d=0;d<l.length;d++){var p=l[d];(i=p.position,a=r,void 0,void 0,o=i.x-a.x,n=i.y-a.y,Math.sqrt(o*o+n*n))<e+p.radius+c&&(s=!1)}return s?r:-1}function u(t,e){return Math.floor(Math.random()*(e-t+1))+t}!function d(){if(n>0){if(requestAnimationFrame(d),u=t.getBoundingClientRect(),v=u.top,y=u.bottom,v<window.innerHeight&&y>=0&&!r){for(var p=0;p<40;p++){var c={id:p,enabled:!0};h(c),l.push(c)}r=!0}var u,v,y;r&&(t.width=t.parentNode.clientWidth,t.height=t.parentNode.clientHeight,e.clearRect(0,0,e.width,e.height),function(){for(var a=0;a<l.length;a++){var r=l[a];if(r.enabled){if(-1==r.position){if(r.position=f(r.radius),-1==r.position)continue;r.fadeState=0}switch(r.position.x+=r.velocity.x*o*.1,r.position.y+=r.velocity.y*o,(i-r.spawnTime)/1e3>=r.lifetime&&(r.fadeState=1),r.rotation+=.1*o,r.fadeState){case 0:r.alpha<1&&(r.alpha+=s*o),r.alpha>=1&&(r.alpha=1,r.fadeState=-1);break;case 1:r.alpha>0&&(r.alpha-=s*o),r.alpha<=0&&(r.enabled=!1,0==--n&&(l=[],t.parentNode.removeChild(t)))}e.globalAlpha=.2*r.alpha,e.translate(r.position.x,r.position.y),e.rotate(r.rotation),d=r,e.fillStyle=d.color,e.fillRect(-d.radius/2,-d.radius/2/2,d.radius,d.radius/2),e.rotate(-1*r.rotation),e.translate(-r.position.x,-r.position.y)}}var d}()),i=Date.now(),o=.01*(i-a),a=i}}()});
function isScrolledIntoView(e) {
+
    var rect = e.getBoundingClientRect();
+
    var elemTop = rect.top;
+
    var elemBottom = rect.bottom;
+
    var isVisible = elemTop < window.innerHeight && elemBottom >= 0;
+
    return isVisible;
+
}
+
 
+
// basic render loop
+
var script = document.scripts[document.scripts.length - 1];
+
var canvas = document.createElement("canvas");  
+
canvas.style.position = "absolute"; canvas.style.left = "0"; canvas.style.top = "0";
+
canvas.style.width = "100%"; canvas.style.height = "100%";
+
script.parentElement.insertBefore(canvas, script);
+
var c = canvas.getContext("2d");
+
var time = Date.now(), last = time, deltaTime = 0;
+
var alive = 40;
+
canvas.width = canvas.parentNode.clientWidth;
+
canvas.height = canvas.parentNode.clientHeight;
+
 
+
 
+
var ready = false;
+
function loop(){
+
if(alive > 0) requestAnimationFrame(loop);
+
else return;
+
if(isScrolledIntoView(canvas) && !ready){
+
for(var i = 0; i < 40; i++){
+
var particle = {id: i, enabled:true};
+
randomizeParticle(particle);
+
particles.push(particle);
+
}
+
ready = true;
+
}
+
if(ready){
+
canvas.width = canvas.parentNode.clientWidth;
+
canvas.height = canvas.parentNode.clientHeight;
+
c.clearRect(0, 0, c.width, c.height);
+
update();
+
}
+
time = Date.now();
+
deltaTime = (time - last) * 0.01;
+
last = time;
+
}
+
 
+
// create all particles
+
var particles = [];
+
var fadeSpeed = 0.15;
+
var minSpeed = 5.2;
+
var maxSpeed = 15.2;
+
var minDist = 30;
+
 
+
function randomizeParticle(particle){
+
particle.radius = rnd(10, 20);
+
particle.position = rndPosition(particle.radius);
+
particle.rotation = rnd(0, 360);
+
particle.velocity = {x: rnd(minSpeed,maxSpeed) * (rnd(0,2) == 1 ? -1 : 1), y: rnd(minSpeed,maxSpeed) * (rnd(0,2) == 1 ? -1 : 1)};
+
particle.lifetime = rnd(3,5);
+
particle.spawnTime = time;
+
particle.color = "rgb("+rnd(0,255)+", " + rnd(0,255)+", " + rnd(0,255) + ")";
+
particle.alpha = 0.0;
+
particle.fadeState = -1; // -1 = NONE, 0 = IN, 1 = OUT
+
}
+
 
+
function respawnParticle(particle){
+
randomizeParticle(particle);
+
particle.alpha = 0.0;
+
particle.fadeState = particle.position == -1 ? -1 : 0;
+
}
+
 
+
function rndPosition(radius){
+
var pos = {x: rnd(0, canvas.width), y: rnd(0, 15)};
+
var valid = true;
+
for(var i = 0; i < particles.length; i++){
+
var obj = particles[i];
+
var d = dist(obj.position, pos);
+
if(d < radius + obj.radius + minDist) valid = false;
+
}
+
if(valid) return pos;
+
else return -1;
+
}
+
 
+
 
+
// update particles each frame
+
function update(){
+
for(var i = 0; i < particles.length; i++){
+
var e = particles[i];
+
if(!e.enabled) continue;
+
// only draw particles without overlapping positions
+
if(e.position == -1){
+
e.position = rndPosition(e.radius);
+
if(e.position == -1) continue;
+
else e.fadeState = 0;
+
}
+
+
// apply velocity
+
e.position.x += e.velocity.x * deltaTime *0.1;
+
e.position.y += e.velocity.y * deltaTime;
+
+
// despawn
+
if((time - e.spawnTime) / 1000 >= e.lifetime) e.fadeState = 1;
+
 
+
e.rotation += deltaTime * 0.1;
+
 
+
switch(e.fadeState){
+
case 0:
+
if(e.alpha < 1.0) e.alpha += fadeSpeed * deltaTime;
+
if(e.alpha >= 1.0){
+
e.alpha = 1.0;
+
e.fadeState = -1;
+
}
+
break;
+
case 1:
+
if(e.alpha > 0.0) e.alpha -= fadeSpeed * deltaTime;
+
if(e.alpha <= 0.0){
+
e.enabled = false;
+
alive--;
+
if(alive == 0){
+
particles = [];canvas.parentNode.removeChild(canvas);
+
}
+
}
+
break;
+
}
+
 
+
// render
+
c.globalAlpha = e.alpha * 0.2;
+
c.translate(e.position.x, e.position.y);
+
c.rotate(e.rotation);
+
drawParticle(e);
+
c.rotate(e.rotation * -1);
+
c.translate(-e.position.x, -e.position.y);
+
}
+
}
+
 
+
 
+
function drawParticle(e){
+
c.fillStyle = e.color;
+
c.fillRect(-e.radius/2,-e.radius/2/2, e.radius, e.radius/2);
+
}
+
 
+
function rnd(min, max) {
+
    return Math.floor(Math.random() * (max - min + 1) ) + min;
+
}
+
 
+
function dist(pos1, pos2){
+
var a = pos1.x - pos2.x;
+
var b = pos1.y - pos2.y;
+
return Math.sqrt(a*a + b*b);
+
}
+
 
+
function clamp(v, min, max){
+
return v < min ? min : v > max ? max : v;
+
}
+
 
+
loop();
+
});
+

Revision as of 03:09, 27 November 2018

var currentConfettiScript=document.scripts[document.scripts.length-1];$(document).ready(function(){var t=document.createElement("canvas");t.style.position="absolute",t.style.left="0",t.style.top="0",t.style.width="100%",t.style.height="100%",currentConfettiScript.parentElement.insertBefore(t,currentConfettiScript);var e=t.getContext("2d"),i=Date.now(),a=i,o=0,n=40;t.width=t.parentNode.clientWidth,t.height=t.parentNode.clientHeight;var r=!1;var l=[],s=.15,d=5.2,p=15.2,c=30;function h(t){t.radius=u(10,20),t.position=f(t.radius),t.rotation=u(0,360),t.velocity={x:u(d,p)*(1==u(0,2)?-1:1),y:u(d,p)*(1==u(0,2)?-1:1)},t.lifetime=u(3,5),t.spawnTime=i,t.color="rgb("+u(0,255)+", "+u(0,255)+", "+u(0,255)+")",t.alpha=0,t.fadeState=-1}function f(e){for(var i,a,o,n,r={x:u(0,t.width),y:u(0,15)},s=!0,d=0;d<l.length;d++){var p=l[d];(i=p.position,a=r,void 0,void 0,o=i.x-a.x,n=i.y-a.y,Math.sqrt(o*o+n*n))<e+p.radius+c&&(s=!1)}return s?r:-1}function u(t,e){return Math.floor(Math.random()*(e-t+1))+t}!function d(){if(n>0){if(requestAnimationFrame(d),u=t.getBoundingClientRect(),v=u.top,y=u.bottom,v<window.innerHeight&&y>=0&&!r){for(var p=0;p<40;p++){var c={id:p,enabled:!0};h(c),l.push(c)}r=!0}var u,v,y;r&&(t.width=t.parentNode.clientWidth,t.height=t.parentNode.clientHeight,e.clearRect(0,0,e.width,e.height),function(){for(var a=0;a<l.length;a++){var r=l[a];if(r.enabled){if(-1==r.position){if(r.position=f(r.radius),-1==r.position)continue;r.fadeState=0}switch(r.position.x+=r.velocity.x*o*.1,r.position.y+=r.velocity.y*o,(i-r.spawnTime)/1e3>=r.lifetime&&(r.fadeState=1),r.rotation+=.1*o,r.fadeState){case 0:r.alpha<1&&(r.alpha+=s*o),r.alpha>=1&&(r.alpha=1,r.fadeState=-1);break;case 1:r.alpha>0&&(r.alpha-=s*o),r.alpha<=0&&(r.enabled=!1,0==--n&&(l=[],t.parentNode.removeChild(t)))}e.globalAlpha=.2*r.alpha,e.translate(r.position.x,r.position.y),e.rotate(r.rotation),d=r,e.fillStyle=d.color,e.fillRect(-d.radius/2,-d.radius/2/2,d.radius,d.radius/2),e.rotate(-1*r.rotation),e.translate(-r.position.x,-r.position.y)}}var d}()),i=Date.now(),o=.01*(i-a),a=i}}()});