mango 0.1.1 → 0.5.0.beta1
Sign up to get free protection for your applications and to get access to all the features.
- data/.gitignore +6 -0
- data/.yardopts +6 -0
- data/README.mdown +62 -29
- data/Rakefile +62 -0
- data/VERSION +1 -0
- data/bin/mango +5 -0
- data/doc/HISTORY.mdown +71 -0
- data/doc/ROAD-MAP.mdown +10 -0
- data/lib/mango.rb +7 -0
- data/lib/mango/application.rb +334 -0
- data/lib/mango/content_page.rb +193 -0
- data/lib/mango/dependencies.rb +125 -0
- data/lib/mango/flavored_markdown.rb +82 -0
- data/lib/mango/rack/debugger.rb +22 -0
- data/lib/mango/runner.rb +95 -0
- data/lib/mango/templates/Gemfile +4 -0
- data/lib/mango/templates/README.md +1 -0
- data/lib/mango/templates/config.ru +4 -0
- data/lib/mango/templates/content/index.md +5 -0
- data/lib/mango/templates/themes/default/public/images/particles.gif +0 -0
- data/lib/mango/templates/themes/default/public/javascripts/fireworks.js +546 -0
- data/lib/mango/templates/themes/default/public/javascripts/timer.js +5 -0
- data/lib/mango/templates/themes/default/public/robots.txt +5 -0
- data/lib/mango/templates/themes/default/public/styles/fireworks.css +55 -0
- data/lib/mango/templates/themes/default/public/styles/reset.css +54 -0
- data/lib/mango/templates/themes/default/styles/screen.sass +17 -0
- data/lib/mango/templates/themes/default/views/404.haml +21 -0
- data/lib/mango/templates/themes/default/views/layout.haml +20 -0
- data/lib/mango/templates/themes/default/views/page.haml +3 -0
- data/lib/mango/version.rb +6 -0
- data/mango.gemspec +35 -0
- data/spec/app_root/content/about/index.haml +1 -0
- data/spec/app_root/content/about/us.haml +1 -0
- data/spec/app_root/content/engines/haml.haml +7 -0
- data/spec/app_root/content/engines/markdown.markdown +7 -0
- data/spec/app_root/content/engines/md.md +7 -0
- data/spec/app_root/content/engines/mdown.mdown +7 -0
- data/spec/app_root/content/index.haml +1 -0
- data/spec/app_root/content/override.haml +1 -0
- data/spec/app_root/content/page_with_missing_view.haml +4 -0
- data/spec/app_root/content/turner+hooch.haml +1 -0
- data/spec/app_root/security_hole.haml +1 -0
- data/spec/app_root/themes/default/public/default.css +3 -0
- data/spec/app_root/themes/default/public/images/index.html +10 -0
- data/spec/app_root/themes/default/public/images/ripe-mango.jpg +0 -0
- data/spec/app_root/themes/default/public/override +10 -0
- data/spec/app_root/themes/default/public/robots.txt +2 -0
- data/spec/app_root/themes/default/public/styles/override.css +3 -0
- data/spec/app_root/themes/default/public/styles/reset.css +27 -0
- data/spec/app_root/themes/default/public/styles/subfolder/another.css +3 -0
- data/spec/app_root/themes/default/security_hole.sass +1 -0
- data/spec/app_root/themes/default/security_hole.txt +1 -0
- data/spec/app_root/themes/default/styles/override.sass +2 -0
- data/spec/app_root/themes/default/styles/screen.sass +13 -0
- data/spec/app_root/themes/default/styles/subfolder/screen.sass +12 -0
- data/spec/app_root/themes/default/views/404.haml +7 -0
- data/spec/app_root/themes/default/views/layout.haml +7 -0
- data/spec/app_root/themes/default/views/page.haml +4 -0
- data/spec/mango/application/routing_content_pages_spec.rb +357 -0
- data/spec/mango/application/routing_public_files_spec.rb +181 -0
- data/spec/mango/application/routing_style_sheets_spec.rb +286 -0
- data/spec/mango/application_spec.rb +34 -0
- data/spec/mango/content_page/finding_spec.rb +213 -0
- data/spec/mango/content_page/initializing_spec.rb +298 -0
- data/spec/mango/content_page_spec.rb +44 -0
- data/spec/mango/dependencies_spec.rb +189 -0
- data/spec/mango/flavored_markdown_spec.rb +52 -0
- data/spec/mango/rack/debugger_spec.rb +114 -0
- data/spec/mango/version_spec.rb +18 -0
- data/spec/quality_spec.rb +32 -0
- data/spec/spec.opts +3 -0
- data/spec/spec_helper.rb +18 -0
- data/spec/support/matchers/malformed_whitespace_matchers.rb +60 -0
- metadata +304 -17
@@ -0,0 +1 @@
|
|
1
|
+
test readme
|
Binary file
|
@@ -0,0 +1,546 @@
|
|
1
|
+
function FireworksController() {
|
2
|
+
var self = this;
|
3
|
+
this.intervalRate = 20; // rate (ms) to run animation at, general best default = 20
|
4
|
+
this.DEBUG = true; // debug mode disabled by default
|
5
|
+
this.oFW = null;
|
6
|
+
this.isIE = (navigator.appVersion.indexOf('MSIE')+1);
|
7
|
+
this.isOpera = (navigator.userAgent.toLowerCase().indexOf('opera')+1);
|
8
|
+
if (this.isOpera) this.isIE = false; // no impersonation allowed here!
|
9
|
+
this.fireworks = [];
|
10
|
+
this.animator = null;
|
11
|
+
this.gOID = 0; // global object ID counter (for animation queue)
|
12
|
+
this.particleTypes = 6;
|
13
|
+
this.particleXY = 10;
|
14
|
+
this.tweenFade = [100,90,80,70,60,50,40,30,20,10,0];
|
15
|
+
this.isSafari = (navigator.appVersion.toLowerCase().indexOf('safari')+1?1:0);
|
16
|
+
this.canvasX = null;
|
17
|
+
this.canvasY = null;
|
18
|
+
this.screenY = null; // screen area (not entire page)
|
19
|
+
self.scrollY = null;
|
20
|
+
|
21
|
+
self.getWindowCoords = function() {
|
22
|
+
self.canvasX = (document.documentElement.clientWidth||document.body.clientWidth||document.body.scrollWidth);
|
23
|
+
self.canvasY = (document.documentElement.clientHeight||document.body.clientHeight||document.body.scrollHeight);
|
24
|
+
self.screenY = self.canvasY;
|
25
|
+
self.scrollY = parseInt(window.scrollY||document.documentElement.scrollTop||document.body.scrollTop);
|
26
|
+
self.canvasY += self.scrollY;
|
27
|
+
}
|
28
|
+
|
29
|
+
this.getWindowCoordsAlt = function() {
|
30
|
+
self.canvasX = window.innerWidth;
|
31
|
+
self.canvasY = window.innerHeight;
|
32
|
+
self.screenY = self.canvasY;
|
33
|
+
self.scrollY = parseInt(window.scrollY||document.documentElement.scrollTop||document.body.scrollTop);
|
34
|
+
self.canvasY += self.scrollY;
|
35
|
+
}
|
36
|
+
|
37
|
+
this.getPanX = function(x) {
|
38
|
+
x = parseInt(x);
|
39
|
+
var pos = x/self.canvasX;
|
40
|
+
if (pos<0.4) {
|
41
|
+
pos *= -1;
|
42
|
+
} else if (pos >= 0.4 && pos <= 0.6) {
|
43
|
+
pos = 0.5;
|
44
|
+
}
|
45
|
+
pos = parseInt(pos*100);
|
46
|
+
// writeDebug('getPanX('+x+'): '+pos+'%');
|
47
|
+
return pos;
|
48
|
+
}
|
49
|
+
|
50
|
+
this.isEmpty = function(o) {
|
51
|
+
// needs further hacking
|
52
|
+
return (typeof(o)=='undefined'||(o==null&&o!=0)||(o==''&&o!=0)||o=='null');
|
53
|
+
}
|
54
|
+
|
55
|
+
this.init = function() {
|
56
|
+
self.oFW = document.getElementById('fw');
|
57
|
+
self.oFP = document.getElementById('fp');
|
58
|
+
if (typeof(enableDebugMode)!='undefined' && (self.DEBUG||window.location.toString().toLowerCase().indexOf('debug')>=0)) enableDebugMode();
|
59
|
+
self.getWindowCoords();
|
60
|
+
self.animator = new Animator();
|
61
|
+
}
|
62
|
+
|
63
|
+
this.destructor = function() {
|
64
|
+
for (var i=self.fireworks.length; i--;) {
|
65
|
+
self.fireworks[i] = null;
|
66
|
+
}
|
67
|
+
self.fireworks = null;
|
68
|
+
if (soundManager) {
|
69
|
+
soundManager.destructor();
|
70
|
+
soundManager = null;
|
71
|
+
}
|
72
|
+
}
|
73
|
+
|
74
|
+
if (this.isSafari || this.isOpera) this.getWindowCoords = this.getWindowCoordsAlt;
|
75
|
+
|
76
|
+
}
|
77
|
+
|
78
|
+
function Firework(oC,startX,startY,burstX,burstY,burstType,nRadius,nParticles,nCircles,allowRandom,obeyBoundaries) {
|
79
|
+
var self = this;
|
80
|
+
this.oID = 'fp'+(fc.gOID++); // may be unneeded
|
81
|
+
var p = '';
|
82
|
+
for (var i=0; i<arguments.length-1; i++) {
|
83
|
+
p += arguments[i]+',';
|
84
|
+
}
|
85
|
+
p += arguments[i];
|
86
|
+
writeDebug('firework('+p+')');
|
87
|
+
this.oC = oC;
|
88
|
+
this.o = fc.oFW.cloneNode(!fc.isIE?true:false);
|
89
|
+
this.particles = [];
|
90
|
+
this.vX = -1;
|
91
|
+
this.vY = -4;
|
92
|
+
this.x = startX;
|
93
|
+
this.y = startY;
|
94
|
+
this.allowRandom = allowRandom;
|
95
|
+
this.obeyBoundaries = obeyBoundaries;
|
96
|
+
this.frame = 0;
|
97
|
+
this.tween = [];
|
98
|
+
this.active = false;
|
99
|
+
this.moveTo = function(x,y) {
|
100
|
+
self.o.style.left = x+'px';
|
101
|
+
self.o.style.top = y+'px';
|
102
|
+
self.x = x;
|
103
|
+
self.y = y;
|
104
|
+
}
|
105
|
+
|
106
|
+
this.slideTo = function(x,y) {
|
107
|
+
self.tween = [fc.animator.createTween(self.x,x,'blast'),fc.animator.createTween(self.y,y,'blast')];
|
108
|
+
fc.animator.enqueue(self,self.animate,self.aniExplode);
|
109
|
+
}
|
110
|
+
|
111
|
+
self.aniExplode = function() {
|
112
|
+
// called from animation finish
|
113
|
+
self.o.style.background = 'none';
|
114
|
+
self.o.style.border = 'none';
|
115
|
+
for (var i=self.particles.length; --i;) {
|
116
|
+
self.particles[i].o.style.display = 'block';
|
117
|
+
fc.animator.enqueue(self.particles[i],self.particles[i].animate);
|
118
|
+
}
|
119
|
+
// attach oncomplete event handler to last particle
|
120
|
+
self.particles[i].o.style.display = 'block';
|
121
|
+
fc.animator.enqueue(self.particles[i],self.particles[i].animate,self.beginFade);
|
122
|
+
var sID = 'boom'+parseInt(Math.random()*8);
|
123
|
+
soundManager.setPan(sID,fc.getPanX(self.x));
|
124
|
+
soundManager.play(sID);
|
125
|
+
}
|
126
|
+
|
127
|
+
self.beginFade = function() {
|
128
|
+
// writeDebug('beginFade');
|
129
|
+
self.tween = fc.animator.createTween(1,0,'fade');
|
130
|
+
fc.animator.enqueue(self,self.aniFade,self.destructor);
|
131
|
+
}
|
132
|
+
|
133
|
+
this.aniFade = function() {
|
134
|
+
// writeDebug('firework.aniFade('+self.tween[self.frame].data+')');
|
135
|
+
for (var i=self.particles.length; i--;) {
|
136
|
+
self.particles[i].moveRel();
|
137
|
+
self.particles[i].nextState();
|
138
|
+
self.particles[i].setOpacity(fc.tweenFade[self.frame]);
|
139
|
+
}
|
140
|
+
if (self.frame++>=self.tween.length) {
|
141
|
+
self.active = false;
|
142
|
+
self.frame = 0;
|
143
|
+
if (self._oncomplete) self._oncomplete();
|
144
|
+
self._oncomplete = null;
|
145
|
+
return false;
|
146
|
+
}
|
147
|
+
return true;
|
148
|
+
}
|
149
|
+
|
150
|
+
this.destructor = function() {
|
151
|
+
writeDebug('firework.destructor()');
|
152
|
+
// for (var i=0; i<self.particles.length; i++) {
|
153
|
+
for (var i=self.particles.length; i--;) {
|
154
|
+
self.particles[i].destructor();
|
155
|
+
self.particles[i] = null;
|
156
|
+
}
|
157
|
+
self.particles = null;
|
158
|
+
self.oC.removeChild(self.o);
|
159
|
+
self.o = null;
|
160
|
+
self.oC = null;
|
161
|
+
}
|
162
|
+
|
163
|
+
this.animate = function() {
|
164
|
+
// generic animation method
|
165
|
+
self.moveTo(self.tween[0][self.frame].data,self.tween[1][self.frame].data,'burst');
|
166
|
+
if (self.frame++>=self.tween[0].length-1) {
|
167
|
+
self.active = false;
|
168
|
+
self.frame = 0;
|
169
|
+
if (self._oncomplete) self._oncomplete();
|
170
|
+
self._oncomplete = null;
|
171
|
+
return false;
|
172
|
+
}
|
173
|
+
return true;
|
174
|
+
}
|
175
|
+
|
176
|
+
this.createBurst = function(circles,nMax,rMax,type) {
|
177
|
+
// c: # of circles, n: # of particles per circle, r: max radius
|
178
|
+
writeDebug('firework.createBurst('+circles+','+nMax+','+rMax+','+type+')');
|
179
|
+
var i=0, j=0;
|
180
|
+
var tmp = 0;
|
181
|
+
var radiusInc = rMax/circles;
|
182
|
+
var radius = radiusInc;
|
183
|
+
var angle = 0;
|
184
|
+
var angleInc = 0; // per-loop increment
|
185
|
+
var radiusOffset = (self.allowRandom?(0.33+Math.random()):1);
|
186
|
+
var particlesPerCircle = [];
|
187
|
+
var isRandom = Math.random()>0.5;
|
188
|
+
var circleTypes = [type,circles>1?parseInt(Math.random()*fc.particleTypes):type];
|
189
|
+
var thisType = null;
|
190
|
+
|
191
|
+
for (i=0; i<circles; i++) {
|
192
|
+
particlesPerCircle[i] = parseInt(nMax*(i+1)/circles*1/circles)||1; // hack - nMax*(i+1)/circles;
|
193
|
+
angle = angleInc; // could be offset as well
|
194
|
+
angleInc = 360/particlesPerCircle[i];
|
195
|
+
thisType = circleTypes[i%2];
|
196
|
+
for (j=0; j<particlesPerCircle[i]; j++) {
|
197
|
+
self.particles[tmp] = new FireworkParticle(self.o,self.allowRandom,thisType,burstX,burstY,self.obeyBoundaries);
|
198
|
+
self.particles[tmp].slideTo(radius*Math.cos(angle*Math.PI/180),radius*radiusOffset*Math.sin(angle*Math.PI/180));
|
199
|
+
angle += angleInc;
|
200
|
+
tmp++;
|
201
|
+
}
|
202
|
+
radius += radiusInc; // increase blast radius
|
203
|
+
}
|
204
|
+
}
|
205
|
+
|
206
|
+
// startX,startY,burstX,burstY,burstType,nRadius,nParticles,nCircles
|
207
|
+
|
208
|
+
self.oC.appendChild(self.o);
|
209
|
+
self.moveTo(self.x,self.y);
|
210
|
+
self.createBurst(nCircles,nParticles,nRadius,burstType); // create an explosion
|
211
|
+
self.slideTo(burstX,burstY);
|
212
|
+
var sID = 'fire'+parseInt(Math.random()*2);
|
213
|
+
soundManager.setPan(sID,fc.getPanX(self.x));
|
214
|
+
soundManager.play(sID);
|
215
|
+
fc.animator.start();
|
216
|
+
|
217
|
+
}
|
218
|
+
|
219
|
+
function FireworkParticle(oC,isRandom,type,baseX,baseY,obeyBoundaries) {
|
220
|
+
var self = this;
|
221
|
+
this.oC = oC;
|
222
|
+
this.oID = 'fp'+(fc.gOID++); // may be unneeded
|
223
|
+
this.o = fc.oFP.cloneNode(true);
|
224
|
+
this.obeyBoundaries = obeyBoundaries;
|
225
|
+
// set type: index becomes Y offset (for background image)
|
226
|
+
this.type = null;
|
227
|
+
|
228
|
+
this.oImg = this.o.getElementsByTagName('img')[0];
|
229
|
+
this.oImg._src = this.oImg.src;
|
230
|
+
this.o.style.display = 'none';
|
231
|
+
this.baseX = baseX;
|
232
|
+
this.baseY = baseY;
|
233
|
+
this.x = 0;
|
234
|
+
this.y = 0;
|
235
|
+
this.vx = 0;
|
236
|
+
this.vy = 0;
|
237
|
+
this.frame = 0;
|
238
|
+
this.tween = [];
|
239
|
+
this.active = null;
|
240
|
+
this.tweenType = 'blast';
|
241
|
+
this.states = [];
|
242
|
+
this.state = parseInt(Math.random()*3);
|
243
|
+
this.isRandom = isRandom;
|
244
|
+
this._mt = 5;
|
245
|
+
|
246
|
+
this.moveTo = function(x,y) {
|
247
|
+
self.o.style.left = x+'px';
|
248
|
+
self.o.style.top = y+'px';
|
249
|
+
self.vx = x-self.x;
|
250
|
+
self.vy = y-self.y;
|
251
|
+
self.x = x;
|
252
|
+
self.y = y;
|
253
|
+
}
|
254
|
+
|
255
|
+
this.moveRel = function() {
|
256
|
+
// continue last moveTo() pattern, bouncing off walls if applicable
|
257
|
+
var toX = self.x+self.vx;
|
258
|
+
var toY = self.y+self.vy;
|
259
|
+
if (self.obeyBoundaries) {
|
260
|
+
var xMax = fc.canvasX-self.baseX-fc.particleXY;
|
261
|
+
var yMax = fc.canvasY-self.baseY-fc.particleXY;
|
262
|
+
var yMin = fc.scrollY;
|
263
|
+
if (self.vx>=0) {
|
264
|
+
if (toX>=xMax) self.vx *= -1;
|
265
|
+
} else if (self.vx<0 && toX+self.baseX<=0) self.vx *= -1;
|
266
|
+
if (self.vy>=0) {
|
267
|
+
if (toY>=yMax) self.vy *= -1;
|
268
|
+
} else if (self.vy<0) {
|
269
|
+
if (toY+self.baseY-yMin<=0) self.vy *= -1;
|
270
|
+
}
|
271
|
+
}
|
272
|
+
self.moveTo(self.x+self.vx,self.y+self.vy);
|
273
|
+
}
|
274
|
+
|
275
|
+
this.setOpacity = function(n) { // where n = 0..100
|
276
|
+
self.oImg.style.marginLeft = -100+(n*fc.particleXY/10)+'px';
|
277
|
+
}
|
278
|
+
|
279
|
+
this.nextState = function() {
|
280
|
+
var vis = self.o.style.visibility;
|
281
|
+
if (self.state == 2 && vis != 'hidden') {
|
282
|
+
self.o.style.visibility = 'hidden';
|
283
|
+
} else if (self.state != 2 && vis == 'hidden') {
|
284
|
+
self.o.style.visibility = 'visible';
|
285
|
+
}
|
286
|
+
self.state = parseInt(Math.random()*3);
|
287
|
+
}
|
288
|
+
|
289
|
+
this.slideTo = function(x1,y1) {
|
290
|
+
// writeDebug('slideTo (x/y): '+x1+','+y1);
|
291
|
+
if (self.isRandom) {
|
292
|
+
// randomize a bit
|
293
|
+
x1 += (x1*0.2*(Math.random()>0.5?1:-1));
|
294
|
+
y1 += (y1*0.2*(Math.random()>0.5?1:-1));
|
295
|
+
}
|
296
|
+
self.tween = [fc.animator.createTween(self.x,x1,self.tweenType),fc.animator.createTween(self.y,y1,self.tweenType)];
|
297
|
+
// prevent X overflow (scrolling)
|
298
|
+
var xMax = fc.canvasX-fc.particleXY;
|
299
|
+
var yMax = fc.canvasY-fc.particleXY;
|
300
|
+
var xMin = fc.particleXY-self.baseX;
|
301
|
+
var yMin = fc.scrollY;
|
302
|
+
var toX = null;
|
303
|
+
var toY = null;
|
304
|
+
if (self.obeyBoundaries) {
|
305
|
+
for (var i=self.tween[0].length; i--;) {
|
306
|
+
// bounce off walls where applicable
|
307
|
+
toX = self.tween[0][i].data+self.baseX;
|
308
|
+
toY = self.tween[1][i].data+self.baseY;
|
309
|
+
if (toX>=xMax) {
|
310
|
+
self.tween[0][i].data -= (toX-xMax)*2;
|
311
|
+
// self.tween[0][i].event = 'bounce';
|
312
|
+
} else if (toX<0) {
|
313
|
+
self.tween[0][i].data -= (toX*2);
|
314
|
+
// self.tween[0][i].event = 'bounce';
|
315
|
+
}
|
316
|
+
if (toY>=yMax) {
|
317
|
+
self.tween[1][i].data -= (toY-yMax)*2;
|
318
|
+
// self.tween[1][i].event = 'bounce';
|
319
|
+
} else if (toY-yMin<=0) {
|
320
|
+
self.tween[1][i].data -= (toY-yMin)*2;
|
321
|
+
// self.tween[1][i].event = 'bounce';
|
322
|
+
}
|
323
|
+
}
|
324
|
+
}
|
325
|
+
}
|
326
|
+
|
327
|
+
this.animate = function() {
|
328
|
+
var f0 = self.tween[0][self.frame].data;
|
329
|
+
var f1 = self.tween[1][self.frame].data;
|
330
|
+
self.moveTo(f0,f1);
|
331
|
+
// possible bounce event/sound hooks
|
332
|
+
// if (self.tween[0][self.frame].event) soundManager.play(self.tween[0][self.frame].event);
|
333
|
+
// if (self.tween[1][self.frame].event) soundManager.play(self.tween[1][self.frame].event);
|
334
|
+
if (self.frame++>=self.tween[0].length-1) {
|
335
|
+
if (self._oncomplete) self._oncomplete();
|
336
|
+
self._oncomplete = null;
|
337
|
+
self.active = false;
|
338
|
+
self.frame = 0;
|
339
|
+
return false;
|
340
|
+
} else if (self.frame>10) {
|
341
|
+
self.nextState();
|
342
|
+
}
|
343
|
+
return true;
|
344
|
+
}
|
345
|
+
|
346
|
+
this.destructor = function() {
|
347
|
+
self.oImg = null;
|
348
|
+
self.oC.removeChild(self.o);
|
349
|
+
self.oC = null;
|
350
|
+
self.o = null;
|
351
|
+
}
|
352
|
+
|
353
|
+
this.setType = function(t) {
|
354
|
+
self.type = t;
|
355
|
+
self.oImg.style.marginTop = -(fc.particleXY*t)+'px';
|
356
|
+
}
|
357
|
+
|
358
|
+
self.setType(type);
|
359
|
+
self.oC.appendChild(self.o);
|
360
|
+
}
|
361
|
+
|
362
|
+
function Animator() {
|
363
|
+
var self = this;
|
364
|
+
writeDebug('Animator()');
|
365
|
+
this.tweens = [];
|
366
|
+
this.tweens['default'] = [1,2,3,4,5,6,7,8,9,10,9,8,7,6,5,4,3,2,1];
|
367
|
+
this.tweens['blast'] = [12,12,11,10,10,9,8,7,6,5,4,3,2,1];
|
368
|
+
this.tweens['fade'] = [10,10,10,10,10,10,10,10,10,10];
|
369
|
+
this.queue = [];
|
370
|
+
this.queue.IDs = [];
|
371
|
+
this.active = false;
|
372
|
+
this.timer = null;
|
373
|
+
|
374
|
+
this.createTween = function(start,end,type) {
|
375
|
+
// return array of tween coordinate data (start->end)
|
376
|
+
type = type||'default';
|
377
|
+
var tween = [start];
|
378
|
+
var tmp = start;
|
379
|
+
var diff = end-start;
|
380
|
+
var x = self.tweens[type].length;
|
381
|
+
for (var i=0; i<x; i++) {
|
382
|
+
tmp += diff*self.tweens[type][i]*0.01;
|
383
|
+
tween[i] = new Object();
|
384
|
+
tween[i].data = tmp;
|
385
|
+
tween[i].event = null;
|
386
|
+
}
|
387
|
+
return tween;
|
388
|
+
}
|
389
|
+
|
390
|
+
this.enqueue = function(o,fMethod,fOnComplete) {
|
391
|
+
// add object and associated methods to animation queue
|
392
|
+
// writeDebug('animator.enqueue()');
|
393
|
+
if (!fMethod) {
|
394
|
+
writeDebug('animator.enqueue(): missing fMethod');
|
395
|
+
}
|
396
|
+
if (typeof(self.queue.IDs[o.oID])=='undefined') {
|
397
|
+
// writeDebug('animator.enqueue(): added '+o.oID);
|
398
|
+
var i = self.queue.length;
|
399
|
+
self.queue.IDs[o.oID] = i;
|
400
|
+
self.queue[i] = o;
|
401
|
+
} else {
|
402
|
+
// writeDebug('animator.enqueue(): '+o.oID+' already queued');
|
403
|
+
var i = self.queue.IDs[o.oID]; // retrieve queue index
|
404
|
+
self.queue[i].active = true;
|
405
|
+
self.queue[i].frame = 0;
|
406
|
+
}
|
407
|
+
o.active = true; // flag for animation
|
408
|
+
self.queue[i]._method = fMethod;
|
409
|
+
self.queue[i]._oncomplete = fOnComplete?fOnComplete:null;
|
410
|
+
}
|
411
|
+
|
412
|
+
this.animate = function() {
|
413
|
+
var active = 0;
|
414
|
+
for (var i=self.queue.length; i--;) {
|
415
|
+
if (self.queue[i].active) {
|
416
|
+
self.queue[i]._method();
|
417
|
+
active++;
|
418
|
+
}
|
419
|
+
}
|
420
|
+
if (active==0 && self.timer) {
|
421
|
+
// all animations finished
|
422
|
+
self.stop();
|
423
|
+
} else {
|
424
|
+
// writeDebug(active+' active');
|
425
|
+
}
|
426
|
+
}
|
427
|
+
|
428
|
+
this.start = function() {
|
429
|
+
if (self.timer || self.active) {
|
430
|
+
// writeDebug('animator.start(): already active');
|
431
|
+
return false;
|
432
|
+
}
|
433
|
+
// writeDebug('animator.start()'); // report only if started
|
434
|
+
self.active = true;
|
435
|
+
self.timer = setInterval(self.animate,fc.intervalRate);
|
436
|
+
}
|
437
|
+
|
438
|
+
this.stop = function() {
|
439
|
+
// writeDebug('animator.stop()',true);
|
440
|
+
clearInterval(self.timer);
|
441
|
+
self.timer = null;
|
442
|
+
self.active = false;
|
443
|
+
self.queue = [];
|
444
|
+
self.queue.IDs = [];
|
445
|
+
}
|
446
|
+
|
447
|
+
}
|
448
|
+
|
449
|
+
function createFirework(nRadius,nParticles,nCircles,nBurstType,startX,startY,burstX,burstY,allowRandom,obeyBoundaries) {
|
450
|
+
// check all arguments, supply random defaults if needed
|
451
|
+
var tmp = '';
|
452
|
+
for (var i in arguments) {
|
453
|
+
tmp += i+',';
|
454
|
+
}
|
455
|
+
writeDebug('createFirework('+tmp+')');
|
456
|
+
|
457
|
+
if (fc.isEmpty(startX)) {
|
458
|
+
startX = parseInt(Math.random()*fc.canvasX);
|
459
|
+
} else {
|
460
|
+
startX = parseInt(fc.canvasX*startX/100);
|
461
|
+
}
|
462
|
+
|
463
|
+
if (fc.isEmpty(startY)) {
|
464
|
+
startY = fc.canvasY-fc.particleXY;
|
465
|
+
} else {
|
466
|
+
startY = fc.canvasY-fc.screenY+parseInt(fc.screenY*startY/100);
|
467
|
+
}
|
468
|
+
|
469
|
+
if (fc.isEmpty(burstX)) {
|
470
|
+
burstX = parseInt(fc.canvasX*0.1+(Math.random()*fc.canvasX*0.8));
|
471
|
+
} else {
|
472
|
+
burstX = parseInt(fc.canvasX*burstX/100);
|
473
|
+
}
|
474
|
+
|
475
|
+
if (fc.isEmpty(burstY)) {
|
476
|
+
burstY = fc.canvasY-parseInt(Math.random()*fc.screenY);
|
477
|
+
} else {
|
478
|
+
burstY = fc.canvasY-parseInt(fc.screenY*(100-burstY)/100);
|
479
|
+
}
|
480
|
+
|
481
|
+
if (fc.isEmpty(nBurstType)) {
|
482
|
+
nBurstType = parseInt(Math.random()*fc.particleTypes);
|
483
|
+
}
|
484
|
+
|
485
|
+
if (fc.isEmpty(nRadius)) {
|
486
|
+
nRadius = 64+parseInt(Math.random()*fc.screenY*0.75);
|
487
|
+
} else if (nRadius.toString().indexOf('%')>=0) {
|
488
|
+
nRadius = parseInt(parseInt(nRadius)/100*fc.screenY);
|
489
|
+
} else if (nRadius.toString().indexOf('.')>=0) {
|
490
|
+
nRadius = parseInt(nRadius*fc.screenY);
|
491
|
+
} else {
|
492
|
+
nRadius = parseInt(nRadius*fc.screenY/100);
|
493
|
+
}
|
494
|
+
|
495
|
+
if (fc.isEmpty(nParticles)) {
|
496
|
+
nParticles = 4+parseInt(Math.random()*64);
|
497
|
+
}
|
498
|
+
|
499
|
+
if (fc.isEmpty(nCircles)) {
|
500
|
+
nCircles = Math.random()>0.5?2:1;
|
501
|
+
}
|
502
|
+
|
503
|
+
if (fc.isEmpty(allowRandom)) {
|
504
|
+
allowRandom = Math.random()>0.5;
|
505
|
+
}
|
506
|
+
|
507
|
+
if (fc.isEmpty(obeyBoundaries)) {
|
508
|
+
obeyBoundaries = Math.random()>0.5;
|
509
|
+
}
|
510
|
+
|
511
|
+
// update screen coordinates
|
512
|
+
fc.getWindowCoords();
|
513
|
+
|
514
|
+
fc.fireworks[fc.fireworks.length] = new Firework(document.getElementById('fireContainer'),startX,startY,burstX,burstY,nBurstType,nRadius,nParticles,nCircles,allowRandom,obeyBoundaries);
|
515
|
+
}
|
516
|
+
|
517
|
+
function smNull() {
|
518
|
+
// Null object for unsupported case
|
519
|
+
this.movies = []; // movie references
|
520
|
+
this.container = null;
|
521
|
+
this.unsupported = 1;
|
522
|
+
this.FlashObject = function(url) {}
|
523
|
+
this.addMovie = function(name,url) {}
|
524
|
+
this.setPan = function() {}
|
525
|
+
this.destructor = function() {}
|
526
|
+
this.play = function(movieName,soundID) {return false;}
|
527
|
+
this.defaultName = 'default';
|
528
|
+
}
|
529
|
+
|
530
|
+
var fc = new FireworksController();
|
531
|
+
// create null objects if APIs not present
|
532
|
+
if (typeof(SoundManager)=='undefined') var soundManager = new smNull();
|
533
|
+
if (typeof(writeDebug)=='undefined') var writeDebug = function(){return false;}
|
534
|
+
|
535
|
+
function addEventHandler(o,evtName,evtHandler) {
|
536
|
+
typeof(attachEvent)=='undefined'?o.addEventListener(evtName,evtHandler,false):o.attachEvent('on'+evtName,evtHandler);
|
537
|
+
}
|
538
|
+
|
539
|
+
function removeEventHandler(o,evtName,evtHandler) {
|
540
|
+
typeof(attachEvent)=='undefined'?o.removeEventListener(evtName,evtHandler,false):o.detachEvent('on'+evtName,evtHandler);
|
541
|
+
}
|
542
|
+
|
543
|
+
addEventHandler(window,'resize',fc.getWindowCoords);
|
544
|
+
addEventHandler(window,'scroll',fc.getWindowCoords);
|
545
|
+
addEventHandler(window,'load',fc.init);
|
546
|
+
addEventHandler(window,'unload',fc.destructor);
|