/******************************/
/** @license
* DHTML Snowstorm! JavaScript-based snow for web pages
* Making it snow on the internets since 2003. You're welcome.
* -----------------------------------------------------------
* Version 1.44.20131208 (Previous rev: 1.44.20131125)
* Copyright (c) 2007, Scott Schiller. All rights reserved.
* Code provided under the BSD License
* http://schillmania.com/projects/snowstorm/license.txt
*/
/*jslint nomen: true, plusplus: true, sloppy: true, vars: true, white: true */ Christmas Light Smashfest/*global window, document, navigator, clearInterval, setInterval */ Adapted from XLSF 2007 as originally used on http://schillmania.com/?theme=2007&christmas=1
var Y snowStorm = (function(window, document) { // shortcuts A: YAHOO.util.Anim, D: YAHOO.util.Dom, E: YAHOO.util.Event, UE: YAHOO.util.Easing, CA: YAHOO.util.ColorAnim, BG: YAHOO.util.BgPosAnim}
function XLSF(oTarget,urlBase) { // --- common properties --- var writeDebug this.autoStart = soundManagertrue; // Whether the snow should start automatically or not._wD; var urlBase this.excludeMobile = (urlBase?urlBase:'lightstrue; //Snow is likely to be bad news for mobile phones'CPUs (and batteries.)Enable at your own risk. this.flakesMax = 128; // Limit total amount of snow made (falling + sticking) writeDebug('XLSFthis.flakesMaxActive = 64; // Limit amount of snow falling at once (less = lower CPU use)') this.animationInterval = 33; // Theoretical "miliseconds per frame" measurement. 20 = fast + smooth, but high CPU use. 50 = more conservative, but slower var IS_MOON_COMPUTER this.useGPU = falsetrue; // Enable transform-based hardware acceleration, reduce CPU load. var isIE this.className = navigatornull; // CSS class name for further customization on snow elements this.userAgent.match(excludeMobile = true; /msie/iSnow is likely to be bad news for mobile phones' CPUs (and batteries.)By default, be nice. this.flakeBottom = null; // Integer for Y axis snow limit, 0 or null for "full-screen" snow effect var self this.followMouse = thistrue; // Snow movement can respond to the user's mouse var xlsf this.snowColor = self'#fff'; // Don't eat (or use?) yellow snow. var animDuration this.snowCharacter = '•'; // • = 1bullet, ·is square on some systems etc. this.oFrag snowStick = documenttrue; // Whether or not snow should "stick" at the bottom. When off, will never collect.createDocumentFragment(); this.oTarget targetElement = null; // element which snow will be appended to (oTarget?oTarget:null = document.documentElementbody);- can be an element ID eg. 'myDiv', or a DOM node reference this.oExplosionBox useMeltEffect = document.createElementtrue; // When recycling fallen snow ('div'or rarely, when falling), have it "melt" and fade out if browser supports it this.useTwinkleEffect = false; // Allow snow to randomly "flicker" in and out of view while falling this.oExplosionBoxusePositionFixed = false; // true = snow does not shift vertically when scrolling. May increase CPU load, disabled by default - if enabled, used only where supported this.className usePixelPosition = 'xlsffalse; // Whether to use pixel values for snow top/left vs. percentages. Auto-enabled if body is position:relative or targetElement is specified. // --- less-used bits --fragment-box' this.freezeOnBlur = true; // Only snow when the window is in focus (foreground.) Saves CPU. this.oExplosionFrag flakeLeftOffset = document0; // Left margin/gutter space on edge of container (eg. browser window.createElement('div')Bump up these values if seeing horizontal scrollbars. this.flakeRightOffset = 0; // Right margin/gutter space on edge of container this.oExplosionFragflakeWidth = 8; // Max pixel width reserved for snow element this.className flakeHeight = 8; // Max pixel height reserved for snow element this.vMaxX = 5; // Maximum X velocity range for snow this.vMaxY = 'xlsf-fragment'4; // Maximum Y velocity range for snow this.lights zIndex = []0; // CSS stacking order applied to each snowflake // --- "No user-serviceable parts inside" past this point, yadda yadda --- var storm = this, features, // UA sniffing and backCompat rendering mode checks for fixed position, etc. isIE = navigator.userAgent.match(/msie/i), isIE6 = navigator.userAgent.match(/msie 6/i), isMobile = navigator.userAgent.match(/mobile|opera m(ob|in)/i), isBackCompatIE = (isIE && document.lightClasses compatMode === 'BackCompat'), noFixed = (isBackCompatIE || isIE6), screenX = null, screenX2 = null, screenY = null, scrollY = null, docHeight = null, vRndX = null, vRndY = null, windOffset = 1, windMultiplier = 2, flakeTypes = 6, fixedForEverything = false, targetElementIsRelative = false, opacitySupported = (function(){ try { document.createElement('div').style.opacity = '0.5'; pico: 32,} catch(e) { return false; tiny: 50,} small: 64return true; }()), medium: 72 didInit = false, large: 96 docFrag = document.createDocumentFragment(); }features = (function() {
if (window.innerWidth || window.innerHeight) { var screenX = window.innerWidthgetAnimationFrame; // -(!isIE?24:2); var screenY = window.innerHeight; } else { var screenX = (document.documentElement.clientWidth||document.body.clientWidth||document.body.scrollWidth); // -(!isIE?8:0); var screenY = (document.documentElement.clientHeight||document.body.clientHeight||document.body.scrollHeight); }
this /** * hat tip: paul irish * http://paulirish.lightClass = (screenX>1800?'small'com/2011/requestanimationframe-for-smart-animating/ * https:'pico'); // kind of light to show (32px to 96px square)gist.github.com/838785 */
if (window.location.href.match function timeoutShim(/size=/i)callback) { this.lightClass = window.location.href.substrsetTimeout(callback, 1000/(windowstorm.location.href.indexOf('size='animationInterval || 20)+5); }
this var _animationFrame = (window.requestAnimationFrame || window.webkitRequestAnimationFrame || window.lightXY = thismozRequestAnimationFrame || window.lightClasses[thisoRequestAnimationFrame || window.lightClass]msRequestAnimationFrame || timeoutShim); // shortcut to w/h
this.lightGroups = { left: []// apply to window,avoid "illegal invocation" errors in Chrome top: [],getAnimationFrame = _animationFrame ? function() { right: [] return _animationFrame.apply(window,arguments); bottom} : [] } this.lightSmashCounter = 0; this.lightIndex = 0; this.lightInterval = 500; this.timer = null; this.bgBaseX = 0; this.bgBaseY = 0; this.soundIDs = 0; this.soundPan = { panValue: 75, left: 0, mid: 481, right: 962 }
this.cover = document.createElement('div'); this.cover.className = 'xlsf-cover'; document.documentElement.appendChild(this.cover) var testDiv;
this.initSounds = function() { for (var i testDiv =0; i<6; i++) { soundManagerdocument.createSoundcreateElement({ id: 'smashdiv'+i, url: urlBase+'sound/glass'+i+'.mp3', autoLoad: true, multiShot: true, volume:50 }); } self.initSounds = function() {} // safety net }
this.appendLights = functionhas(prop) { writeDebug('xlsf.appendLights()'); self.oTarget.appendChild(self.oFrag); self.oFrag = document.createDocumentFragment(); }
function ExplosionFragment(nType,sClass,x,y,vX,vY) { // test for feature support var self result = this; thistestDiv.o = xlsf.oExplosionFrag.cloneNode(true); this.nType = nType; this.sClass = sClass; this.x = x; this.y = y; this.w = 50; this.h = 50; this.bgBaseX = 0; this.bgBaseY = this.h*this.nType; this.vX = vX*(1.5+Math.random())style[prop]; this.vY = vY* return (1.5+Math.random()); this.oA result != null; this.oA2 = undefined ? prop : null; this.burstPhase = 1; // starting background offset point this.burstPhases = 4; // 1+offset (ignore large size) this.o.style.backgroundPosition = ((this.w*-this.burstPhase)+'px '+(this.h*-nType)+'px');
// boundary checks
if (self.sClass == 'left') {
this.vX = Math.abs(this.vX);
} else if (self.sClass == 'right') {
this.vX = Math.abs(this.vX)*-1;
}
this// note local scope.burstTween var localFeatures = function{ transform: { ie: has('-ms-transform'), moz: has('MozTransform'), opera: has('OTransform') {, webkit: has('webkitTransform'), w3: has('transform'), prop: null // determine frame to showthe normalized property value var phase }, getAnimationFrame: getAnimationFrame }; localFeatures.transform.prop = 1+Math.floor((this.currentFrame/this localFeatures.totalFrames)*selftransform.burstPhases);w3 || if (phase != selflocalFeatures.burstPhase) { selftransform.burstPhase = phase;moz || self localFeatures.otransform.stylewebkit || localFeatures.backgroundPosition = ((selftransform.w*-selfie || localFeatures.burstPhase)+'px '+(selftransform.h*-nType)+'px'opera ); } testDiv = null; return localFeatures; }());
this.burst timer = function() {null; self this.oA flakes = new Y[]; this.A(selfdisabled = false; this.o,{marginLeft:{to:(self.vX*8)},marginTop:{to:(self.vY*8)}},animDuration,Y.UE.easeOutStrong)active = false; self this.oA.onTween.subscribe(self.burstTween)meltFrameCount = 20; self this.oA.animate()meltFrames = []; }
this.hide setXY = function(o, x, y) { if (!isIE) self.o.style.opacity = 0; }
this.reset = functionif (!o) { self.o.style.left = '0px'; self.o.style.top = '0px'; self.o.style.marginLeft = '0px'; self.o.style.marginTop = '0px'; if (!isIE) self.o.style.opacity = 1return false;
}
thisif (storm.animate = function(usePixelPosition || targetElementIsRelative) { self.reset(); self.burst(); }
} o.style.left = (x - storm.flakeWidth) + 'px'; o.style.top = (y - storm.flakeHeight) + 'px';
function Explosion } else if (nType,sClass,x,ynoFixed) { var oParent = this; var self = this; this.o = null; this.nType = nType; this.sClass = sClass; this.x = x; this.y = y; this.boxVX = 0; this.boxVY = 0; this.o = xlsf.oExplosionBox.cloneNode(true); this.o.style.left = x+'px'; this.o.style.top = y+'px'; this.fragments = [];
var mX o.style.right = (100-(x/screenX*100)) + '%'; var mY // avoid creating vertical scrollbars o.style.top = (Math.min(y, docHeight-storm.flakeHeight)) + 'px';
this.fragments.push(new ExplosionFragment(nType,sClass,mX,mY,-5,-5)); this.fragments.push(new ExplosionFragment(nType,sClass,mX,mY,0,-5)); this.fragments.push(new ExplosionFragment(nType,sClass,mX,mY,5,-5));} else {
this.fragments.push(new ExplosionFragment if (nType,sClass,mX,mY,-5,0)); this.fragments!storm.push(new ExplosionFragment(nType,sClass,mX,mY,0,0)); this.fragments.push(new ExplosionFragment(nType,sClass,mX,mY,5,0)flakeBottom);{
this // if not using a fixed bottom coordinate..fragments.push(new ExplosionFragment(nType,sClass,mX,mY,5,-5)); this o.fragmentsstyle.pushright = (new ExplosionFragment100-(nType,sClass,mX,mY,5,0x/screenX*100))+ '%'; this o.fragmentsstyle.pushbottom = (new ExplosionFragment100-(nType,sClass,mX,mY,5,5y/screenY*100))+ '%';
this.init = function() {
for (var i=self.fragments.length; i--;) {
self.o.appendChild(self.fragments[i].o);
}
if (!IS_MOON_COMPUTER) {
// faster rendering, particles get cropped
xlsf.oFrag.appendChild(self.o);
} else {
// slower rendering, can overlay bodyabsolute top. o.style.right = (100-(x/screenX*100)) + '%'; xlsfo.style.oFragtop = (Math.appendChildmin(selfy, docHeight-storm.oflakeHeight))+ 'px';
}
}
}; this.reset events = (function() { // clean-up // self var old = (!window.oaddEventListener && window.parentNodeattachEvent), slice = Array.removeChild(selfprototype.o);slice, evt = { self.o.style.display = add: (old?'attachEvent':'noneaddEventListener';), self.o.style.marginLeft = remove: (old?'0pxdetachEvent'; self.o.style.marginTop = :'0pxremoveEventListener') }; function getArgs(oArgs) { selfvar args = slice.o.style.left call(oArgs), len = selfargs.x+'px'length; self.o.style.top if (old) { args[1] = self.y+'pxon'+ args[1];// prefix if (!isIElen > 3) self{ args.o.style.opacity = 1pop();// no capture } for } else if (var ilen ===self.fragments.length; i--;3) { self.fragments[i]args.resetpush(false);
}
return args;
}
this.trigger = functionapply(boxVXargs,boxVYsType) { self.o.style.display var element = 'block'; self.boxVX = boxVX; selfargs.boxVY = boxVY; // boundary checks if shift(self.sClass == 'right') {, self.boxVX method = Math.abs(self.boxVX)*-1[evt[sType]]; } else if (self.sClass == 'left'old) { self.boxVX = Math.abs(self.boxVX); } for (var i=self.fragments.length; i--;) { self.fragmentselement[imethod].animate(); } if (!isIE && (IS_MOON_COMPUTER)) { var oAExplode = new Y.A(self.o,{marginLeft:{to:100*self.boxVX},marginTop:{to:150*self.boxVY},opacity:{to:args[0.01}}],animDuration,Y.UE.easeInStrongargs[1]);
} else {
// even IE 7 sucks w/alpha-transparent PNG + CSS opacityelement[method]. Boo urns. var oAExplode = new Y.Aapply(self.o,{marginLeft:{to:100*self.boxVX},marginTop:{to:150*self.boxVY}}element,animDuration,Y.UE.easeInStrongargs);
}
oAExplode.onComplete.subscribe(self.reset);
oAExplode.animate();
}
this.initfunction addEvent() { apply(getArgs(arguments), 'add'); }
function removeEvent() {
apply(getArgs(arguments), 'remove');
}
return {
add: addEvent,
remove: removeEvent
};
}());
function rnd(n,min) {
if (isNaN(min)) {
min = 0;
}
return (Math.random()*n)+min;
}
function LightplusMinus(sSizeClass,sClass,nType,x,yn) { var self = this; this.o = document.createElementreturn (parseInt('div'); this.sClass = sClass; this.sSizeClass = sSizeClass; this.nType = rnd(nType||02); this.useY = (sClass == 'left' || sClass == 'right',10); this.state = null; this.broken = 0; this.w = xlsf.lightClasses[sSizeClass]; this.h = xlsf.lightClasses[sSizeClass]; this.x = x; this.y = y; this.bg = urlBase+'image/bulbs-'+this.w+'x'+this.h+'-'+this.sClass+'.png'; this.o.style.width = this.w+'px'; this.o.style.height = this.h+'px'; this.o.style.background = 'url('+this.bg+') no-repeat 0px 0px'; this.bgBaseX = (self.useY1?-self.wn*this.nType:0); this.bgBaseY = (!self.useY?-self.h*this.nType1:0n); this.glassType = parseInt(Math.random()*6); this.oExplosion = null; this.soundID = 'smash'+this.glassType; var panValue = xlsf.soundPan.panValue; // eg. +/- 80% this.pan = parseInt(this.x<=xlsf.soundPan.mid?-panValue+((this.x/xlsf.soundPan.mid)*panValue):(this.x-xlsf.soundPan.mid)/(xlsf.soundPan.right-xlsf.soundPan.mid)*panValue); }
this.randomizeWind = function() { var i; vRndX = plusMinus(rnd(storm.vMaxX,0.2)); vRndY = rnd(storm.vMaxY,0.2); if (this.initSound flakes) { for (i= function0; i<this.flakes.length; i++) { if (this.flakes[i].active) { this.flakes[i].setVelocities(); } }
}
};
this.setBGPos scrollHandler = function(x,y) { self var i; // "attach" snowflakes to bottom of window if no absolute bottom value was given scrollY = (storm.flakeBottom ? 0 : parseInt(window.oscrollY || document.styledocumentElement.backgroundPosition = scrollTop || ((selfnoFixed ? document.body.bgBaseX+xscrollTop : 0), 10)+'px '+); if (isNaN(self.bgBaseY+yscrollY)+'px'){ scrollY = 0;// Netscape 6 scroll fix
}
this.setLight = function(bOn) { if (self.broken || self.state == bOn) return false; if (!self.w || fixedForEverything && !selfstorm.h) selfflakeBottom && storm.getDimensions(flakes);{ self.state for (i= bOn0; if (selfi<storm.flakes.useYlength; i++) { selfif (storm.setBGPos(0,-thisflakes[i].h*(bOn?active === 0:1)); } else { self storm.setBGPos(-thisflakes[i].w*stick(bOn?0:1),0); }
}
}
};
this.getDimensions resizeHandler = function() { if (window.innerWidth || window.innerHeight) { self.w screenX = selfwindow.oinnerWidth - 16 - storm.offsetWidthflakeRightOffset; self.h screenY = self(storm.oflakeBottom || window.offsetHeightinnerHeight); } else { self.bgBaseX screenX = (selfdocument.documentElement.clientWidth || document.body.useY?-selfclientWidth || document.w*selfbody.nTypescrollWidth) - (!isIE ? 8 :0)- storm.flakeRightOffset; selfscreenY = storm.bgBaseY = (!selfflakeBottom || document.documentElement.clientHeight || document.body.useY?-selfclientHeight || document.h*selfbody.nType:0)scrollHeight;
}
docHeight = document.body.offsetHeight;
screenX2 = parseInt(screenX/2,10);
};
this.on resizeHandlerAlt = function() { self screenX = storm.targetElement.offsetWidth - storm.flakeRightOffset; screenY = storm.flakeBottom || storm.targetElement.setLightoffsetHeight; screenX2 = parseInt(1screenX/2,10); docHeight = document.body.offsetHeight; };
this.off freeze = function() { // pause animation if (!storm.disabled) { selfstorm.setLight(0)disabled = 1; } else { return false;
}
storm.timer = null;
};
this.flickr resume = function() { self.setLight if (Mathstorm.random(disabled)>{ storm.disabled =0.5?1:0); } else { return false;
}
storm.timerInit();
};
this.toggle toggleSnow = function() { if (!storm.flakes.length) { // first run selfstorm.setLightstart(); } else { storm.active = !selfstorm.active; if (storm.state?1:0active) { storm.show(); storm.resume(); } else { storm.stop(); storm.freeze(); }
}
};
this.explode stop = function(e) { self var i; this.oExplosion.triggerfreeze(); for (i=0,1; i<this.flakes.length; i++){ this.flakes[i].o.style.display = 'none'; // boooom!
}
this.smash = function(e) { if (selfstorm.broken) return false; selfevents.broken = true; if remove(soundManager && soundManager.ok()) { soundManager.play(self.soundIDwindow,'scroll',{pan:selfstorm.pan}scrollHandler); // soundManager storm.sounds[selfevents.soundID].playremove({pan:selfwindow,'resize',storm.pan}resizeHandler); // if (selfstorm.bonusSound != nullfreezeOnBlur) window.setTimeout(self.smashBonus,1000);{ } self.explodeif (eisIE);{ var rndFrame = 2; // +parseInt storm.events.remove(Mathdocument,'focusout',storm.random()*3freeze); if (self storm.useY) { selfevents.setBGPosremove(0document,'focusin',selfstorm.h*-rndFrameresume);
} else {
selfstorm.setBGPosevents.remove(selfwindow,'blur',storm.freeze); storm.events.w*-rndFrameremove(window,'focus',0storm.resume);
}
xlsf.lightSmashCounter++;
}
};
this.smashBonus show = function() { // soundManager.play var i; for (selfi=0; i<this.bonusSounds[selfflakes.bonusSound],urlBaselength; i+'sound/'+self) { this.bonusSoundsflakes[selfi].o.style.bonusSound]+display = '.mp3block');
}
};
this.reset SnowFlake = function(type,x,y) { if var s = this; this.type = type; this.x = x||parseInt(rnd(screenX-20),10); this.y = (!selfisNaN(y)?y:-rnd(screenY)-12); this.brokenvX = null; this.vY = null; this.vAmpTypes = [1,1.2,1.4,1.6,1.8]; // "amplification" for vX/vY (based on flake size/type) return this.vAmp = this.vAmpTypes[this.type] || 1; this.melting = false; this.meltFrameCount = storm.meltFrameCount; this.meltFrames = storm.meltFrames; this.meltFrame = 0; this.twinkleFrame = 0; this.active = 1; this.fontSize = (10+(this.type/5)*10); this.o = document.createElement('div'); this.o.innerHTML = storm.snowCharacter; if (storm.className) { selfthis.o.setAttribute('class', storm.broken className); } this.o.style.color = falsestorm.snowColor; self this.o.style.state position = null(fixedForEverything?'fixed':'absolute'); if (storm.useGPU && features.transform.prop) { xlsf// GPU-accelerated snow.lightSmashCounter--; selfthis.flickro.style[features.transform.prop] = 'translate3d(0px, 0px, 0px)';
}
this.o.style.width = storm.flakeWidth+'px';
this.o.style.height = storm.flakeHeight+'px';
this.o.style.fontFamily = 'arial,verdana';
this.o.style.cursor = 'default';
this.o.style.overflow = 'hidden';
this.o.style.fontWeight = 'normal';
this.o.style.zIndex = storm.zIndex;
docFrag.appendChild(this.o);
this.refresh = function() {
if (isNaN(s.x) || isNaN(s.y)) {
// safety check
return false;
}
storm.setXY(s.o, s.x, s.y);
};
this.init stick = function() { selfif (noFixed || (storm.targetElement !== document.odocumentElement && storm.className targetElement != 'xlsf-light '+this= document.sizeClass+' '+this.sClass;body)) { self s.o.style.left top = self(screenY+scrollY-storm.xflakeHeight)+'px'; self} else if (storm.flakeBottom) { s.o.style.top = selfstorm.yflakeBottom+'px'; self} else { s.o.style.width display = self.w+'pxnone'; self s.o.style.height bottom = self.h+'px0%'; self s.o.onmouseover style.position = self.smash'fixed'; self s.o.onclick style.display = self.smash'block'; self.flickr(); xlsf.oFrag.appendChild(self.o); self.oExplosion = new Explosion(self.nType,self.sClass,self.x,self.y);} };
this.initvCheck = function(){ if (s.vX>=0 && s.vX<0.2) { s.vX = 0.2; } else if (s.vX<0 && s.vX>-0.2) { s.vX = -0.2; } // Light if (s.vY>=0 && s.vY<0.2){ s.vY = 0.2; } };
this.createLight move = function(sClass,nType) { var vX = s.vX*windOffset,yDiff; s.x,+= vX; s.y+= (s.vY*s.vAmp); if (s.x >= screenX || screenX-s.x < storm.flakeWidth) {// X-axis scroll check var oLight s.x = new Light0; } else if (selfvX < 0 && s.x-storm.flakeLeftOffset < -storm.flakeWidth) { s.lightClass,sClass,nType,x= screenX-storm.flakeWidth-1; // flakeWidth; } s.refresh(); yDiff = screenY+scrollY-s.y+storm.flakeHeight; if (yDiff<storm.flakeHeight) { s.active = 0; if (storm.snowStick) { s.stick(); } else { s.recycle(); } } else { if (storm.useMeltEffect && s.active && s.type < 3 && !s.melting && Math.random()>0.998) { // ~1/1000 chance of melting mid-air,ywith each frame s.melting = true; s.melt(); self // only incrementally melt one frame // s.melting = false; } if (storm.useTwinkleEffect) { if (s.twinkleFrame < 0) { if (Math.random() > 0.97) { s.lightGroups[sClass]twinkleFrame = parseInt(Math.pushrandom(oLight)* 8, 10); } } else { s.twinkleFrame--; self if (!opacitySupported) { s.o.lightsstyle.pushvisibility = (oLights.twinkleFrame && s.twinkleFrame % 2 === 0 ? 'hidden' : 'visible'); return oLight } else { s.o.style.opacity = (s.twinkleFrame && s.twinkleFrame % 2 === 0 ? 0 : 1); } } } } };
this.rotateLights animate = function() { self // main animation loop // move, check status, die etc.lights[self.lightIndex==self.lights.length?self.lights.length-1:self.lightIndex].off(); self s.lightIndex++; if move(self.lightIndex == self.lights.length) { self.lightIndex = 0; } self.lights[self.lightIndex].on(); }
this.randomLights setVelocities = function() { self s.lights[parseIntvX = vRndX+rnd(Mathstorm.random()vMaxX*self0.lights12,0.length1)]; s.togglevY = vRndY+rnd(storm.vMaxY*0.12,0.1); };
this.destroyLights setOpacity = function(o,opacity) { self if (!opacitySupported) { return false; } o.startSequence(selfstyle.destroyLight,20)opacity = opacity; };
this.destroyLight melt = function() { var groupSize = 2 if (!storm.useMeltEffect || !s.melting) { s.recycle(); // # to smash at a time } else { if (selfs.lightSmashCountermeltFrame <self.lightss.lengthmeltFrameCount) { var limit = Math s.minsetOpacity(selfs.lightSmashCounter+groupSizeo,selfs.lightsmeltFrames[s.lengthmeltFrame]); for s.o.style.fontSize = s.fontSize-(s.fontSize*(var is.meltFrame/s.meltFrameCount))+'px'; s.o.style.lineHeight =selfstorm.flakeHeight+2+(storm.flakeHeight*0.75*(s.meltFrame/s.lightSmashCountermeltFrameCount))+'px'; i<limit; i s.meltFrame++) ; } else { self s.lights[self.lightSmashCounter].smashrecycle(); }
}
} else ; this.recycle = function() { selfs.o.style.display = 'none'; s.o.style.position = (fixedForEverything?'fixed':'absolute'); s.o.style.bottom = 'auto'; s.setVelocities(); s.stopSequencevCheck(); s.meltFrame = 0; s.melting = false; s.setOpacity(s.o,1); s.o.style.padding = '0px'; s.o.style.margin = '0px'; s.o.style.fontSize = s.fontSize+'px'; s.o.style.lineHeight = (storm.flakeHeight+2)+'px'; s.o.style.textAlign = 'center'; s.o.style.verticalAlign = 'baseline'; s.x = parseInt(rnd(screenX-storm.flakeWidth-20),10); s.y = parseInt(rnd(screenY)*-1,10)-storm.flakeHeight; s.refresh(); s.o.style.display = 'block'; s.active = 1; };
} this.recycle(); // set up x/y coords etc. this.refresh();
this.uberSmash = function() { // make everything explode - including your CPU. self.stopSequence()}; var ebCN = Y.D.getElementsByClassName; }
this.smashGroup snow = function(oGroup) { var active = 0, flake = null, i, j; for (var i=oGroup0, j=storm.flakes.length; i--<j;i++) { oGroupif (storm.flakes[i].smashactive === 1) { storm.flakes[i].move(); active++; } if (storm.flakes[i].melting) { storm.flakes[i].melt(); }
}
if (active<storm.flakesMaxActive) { flake = storm.flakes[parseInt(rnd(storm.flakes.length),10)]; if (flake.active === 0) { flake.melting = true; } } if (storm.timer) { features.getAnimationFrame(storm.snow); } };
this.startSequence mouseMove = function(fSequence,nIntervale) { if (self!storm.timer) self.stopSequence(followMouse){ return true; self.timer } var x = windowparseInt(e.setInterval(fSequenceclientX,10); if (typeof nInterval !x<screenX2) { windOffset = 'undefined'?nInterval:self.lightInterval-windMultiplier+(x/screenX2*windMultiplier); } else { x -= screenX2; windOffset = (x/screenX2)*windMultiplier; } };
this.stopSequence createSnow = function(limit,allowInactive) { if var i; for (self.timeri=0; i<limit; i++) { windowstorm.flakes[storm.flakes.clearIntervallength] = new storm.SnowFlake(parseInt(rnd(self.timerflakeTypes),10)); selfif (allowInactive || i>storm.flakesMaxActive) { storm.flakes[storm.timer flakes.length-1].active = null-1; }
}
storm.targetElement.appendChild(docFrag); };
var ithis.timerInit =0function() { storm.timer = true; storm.snow(); var j=0};
$this.init = function() { var i; for (i=0; i<storm.meltFrameCount; i++) { storm.meltFrames.push(1-(i/storm.meltFrameCount)); } storm.randomizeWind(); storm.createSnow(storm.flakesMax); // create initial batch storm.events.add(window,'resize',storm.resizeHandler); storm.events.add(window,'scroll',storm.scrollHandler); if (storm.freezeOnBlur) { if (isIE) { storm.events.add(document,'lightsfocusout',storm.freeze); storm.styleevents.display = add(document,'focusin',storm.resume); } else { storm.events.add(window,'blur',storm.freeze); storm.events.add(window,'focus',storm.resume); } } storm.resizeHandler(); storm.scrollHandler(); if (storm.followMouse) { storm.events.add(isIE?document:window,'blockmousemove',storm.mouseMove); } storm.animationInterval = Math.max(20,storm.animationInterval); storm.timerInit(); };
this.start = function(bFromOnLoad) { if (!didInit) { didInit = true; } else if (bFromOnLoad) { // start lights already loaded and running return true; } if (typeof storm.targetElement === 'string') { var targetID = storm.targetElement; storm.targetElement = document.getElementById(targetID); if (!storm.targetElement) { throw new Error('Snowstorm: Unable to get targetElement "'+targetID+'"'); } } if (!storm.targetElement) { storm.targetElement = (document.body || document.documentElement); } if (storm.targetElement !== document.documentElement && storm.targetElement !== document.body) { // re-map handler to the right get element instead of <h1>screen dimensions storm.resizeHandler = storm.resizeHandlerAlt; //and force-enable pixel positioning storm.usePixelPosition = true; var offset } storm.resizeHandler(); // get bounding box elements storm.usePositionFixed = 0(storm.usePositionFixed && !noFixed && !storm.flakeBottom); // parseIntwhether or not position:fixed is to be used if (documentwindow.getComputedStyle) { // attempt to determine if body or user-specified snow parent element is relatlively-positioned. try { targetElementIsRelative = (window.getComputedStyle(storm.targetElement, null).getElementsByTagNamegetPropertyValue('h1position')[0]=== 'relative'); } catch(e) { // oh well targetElementIsRelative = false; } } fixedForEverything = storm.usePositionFixed; if (screenX && screenY && !storm.disabled) { storm.offsetWidthinit()+16; storm.active = true; } };
var jMax = Mathfunction doDelayedStart() { window.floorsetTimeout(function(screenX-offset-16)/self{ storm.lightXYstart(true); var iMax = Math.floor((screenY-offset-16 }, 20); /self/ event cleanup storm.lightXYevents.remove(isIE?document:window,'mousemove',doDelayedStart); }
for function doStart(j=0; j<jMax; j++) { thisif (!storm.excludeMobile || !isMobile) { doDelayedStart(); } // event cleanup storm.createLightevents.remove(window, 'topload',parseInt(j/3)%4,offset+j*self.lightXY,0doStart);
}
this// hooks for starting the snow if (storm.appendLights(autoStart);{ this storm.events.startSequenceadd(self.randomLightswindow, 'load', doStart, false); }
var xlsf = null;var urlBase = null return this;
function smashInit() { if (navigator.userAgent.match(/msie 6/i)) { return false; } xlsf = new XLSF(window, document.getElementById('lights'),urlBase?urlBase:null); if ($('loading')) { $('loading').style.display = 'none'; } xlsf.initSounds();} soundManager.setup({ flashVersion: 9, preferFlash: false, url: 'lights/', onready: function() { smashInit(); }, ontimeout: function() { smashInit(); }});