contentflow 0.0.2

Sign up to get free protection for your applications and to get access to all the features.
@@ -0,0 +1,17 @@
1
+ *.gem
2
+ *.rbc
3
+ .bundle
4
+ .config
5
+ .yardoc
6
+ Gemfile.lock
7
+ InstalledFiles
8
+ _yardoc
9
+ coverage
10
+ doc/
11
+ lib/bundler/man
12
+ pkg
13
+ rdoc
14
+ spec/reports
15
+ test/tmp
16
+ test/version_tmp
17
+ tmp
data/Gemfile ADDED
@@ -0,0 +1,4 @@
1
+ source 'https://rubygems.org'
2
+
3
+ # Specify your gem's dependencies in contentflow.gemspec
4
+ gemspec
@@ -0,0 +1,22 @@
1
+ Copyright (c) 2012 sergio1990
2
+
3
+ MIT License
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining
6
+ a copy of this software and associated documentation files (the
7
+ "Software"), to deal in the Software without restriction, including
8
+ without limitation the rights to use, copy, modify, merge, publish,
9
+ distribute, sublicense, and/or sell copies of the Software, and to
10
+ permit persons to whom the Software is furnished to do so, subject to
11
+ the following conditions:
12
+
13
+ The above copyright notice and this permission notice shall be
14
+ included in all copies or substantial portions of the Software.
15
+
16
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
17
+ EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
18
+ MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
19
+ NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
20
+ LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
21
+ OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
22
+ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
@@ -0,0 +1,29 @@
1
+ # Contentflow
2
+
3
+ TODO: Write a gem description
4
+
5
+ ## Installation
6
+
7
+ Add this line to your application's Gemfile:
8
+
9
+ gem 'contentflow'
10
+
11
+ And then execute:
12
+
13
+ $ bundle
14
+
15
+ Or install it yourself as:
16
+
17
+ $ gem install contentflow
18
+
19
+ ## Usage
20
+
21
+ TODO: Write usage instructions here
22
+
23
+ ## Contributing
24
+
25
+ 1. Fork it
26
+ 2. Create your feature branch (`git checkout -b my-new-feature`)
27
+ 3. Commit your changes (`git commit -am 'Add some feature'`)
28
+ 4. Push to the branch (`git push origin my-new-feature`)
29
+ 5. Create new Pull Request
@@ -0,0 +1 @@
1
+ require "bundler/gem_tasks"
@@ -0,0 +1,24 @@
1
+ # -*- encoding: utf-8 -*-
2
+ lib = File.expand_path('../lib', __FILE__)
3
+ $LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
4
+ require 'contentflow/version'
5
+
6
+ Gem::Specification.new do |gem|
7
+ gem.name = "contentflow"
8
+ gem.version = Contentflow::VERSION
9
+ gem.authors = ["sergio1990"]
10
+ gem.email = ["sergeg1990@gmail.com"]
11
+ gem.description = "ContentFlow is a flexible CoverflowTM / ImageFlow like flow written in javascript, which can handle any kind of content for the Rails 3.1+ asset pipeline"
12
+ gem.summary = "ContentFlow for the Rails 3.1+ asset pipeline"
13
+ gem.homepage = "https://github.com/sergio1990/contentflow"
14
+
15
+ gem.add_dependency "railties", ">= 3.0"
16
+ gem.add_dependency "sass", ">= 3.2"
17
+ gem.add_development_dependency "bundler", ">= 1.0"
18
+ gem.add_development_dependency "rails", ">= 3.1"
19
+
20
+ gem.files = `git ls-files`.split($/)
21
+ gem.executables = gem.files.grep(%r{^bin/}).map{ |f| File.basename(f) }
22
+ gem.test_files = gem.files.grep(%r{^(test|spec|features)/})
23
+ gem.require_paths = ["lib"]
24
+ end
@@ -0,0 +1,6 @@
1
+ require "rails"
2
+ require "contentflow/version"
3
+
4
+ module Contentflow
5
+ require "contentflow/engine"
6
+ end
@@ -0,0 +1,9 @@
1
+ module Contentflow
2
+ class Engine < ::Rails::Engine
3
+ initializer 'contentflow-setup', :group => :all do |app|
4
+ if config.respond_to? :sass
5
+ config.sass.load_paths << File.join(config.root, 'vendor')
6
+ end
7
+ end
8
+ end
9
+ end
@@ -0,0 +1,3 @@
1
+ module Contentflow
2
+ VERSION = "0.0.2"
3
+ end
@@ -0,0 +1,2584 @@
1
+ /* ContentFlow, version 1.0.2
2
+ * (c) 2007 - 2010 Sebastian Kutsch
3
+ * <http://www.jacksasylum.eu/ContentFlow/>
4
+ *
5
+ * ContentFlow is distributed under the terms of the MIT license.
6
+ * (see http://www.jacksasylum.eu/ContentFlow/LICENSE)
7
+ *
8
+ *--------------------------------------------------------------------------*/
9
+ /*
10
+ * ============================================================
11
+ * Global configutaion and initilization object
12
+ * ============================================================
13
+ */
14
+ var ContentFlowGlobal = {
15
+ Flows: new Array,
16
+ AddOns: {},
17
+ scriptName: 'contentflow.js',
18
+ scriptElement: null,
19
+ Browser: new (function () {
20
+ this.Opera = window.opera ? true : false;
21
+ this.IE = document.all && !this.Opera ? true : false;
22
+ this.IE6 = this.IE && typeof(window.XMLHttpRequest) == "undefined" ? true : false;
23
+ this.IE8 = this.IE && typeof(document.querySelectorAll) != "undefined" ? true : false;
24
+ this.IE7 = this.IE && ! this.IE6 && !this.IE8 ? true : false;
25
+ this.WebKit = /WebKit/i.test(navigator.userAgent) ? true : false,
26
+ this.iPhone = /iPhone|iPod/i.test(navigator.userAgent)? true : false;
27
+ this.Chrome = /Chrome/i.test(navigator.userAgent) ? true : false;
28
+ this.Safari = /Safari/i.test(navigator.userAgent) && !this.Chrome ? true : false;
29
+ this.Konqueror = navigator.vendor == "KDE" ? true : false;
30
+ this.Konqueror4 = this.Konqueror && /native code/.test(document.getElementsByClassName) ? true : false;
31
+ this.Gecko = !this.WebKit && navigator.product == "Gecko" ? true : false;
32
+ this.Gecko19 = this.Gecko && Array.reduce ? true : false;
33
+ })(),
34
+
35
+ getAddOnConf: function(name) {
36
+ if(this.AddOns[name])
37
+ return this.AddOns[name].conf;
38
+ else
39
+ return {};
40
+ },
41
+
42
+ setAddOnConf: function (name, conf) {
43
+ this.AddOns[name].setConfig(conf);
44
+ },
45
+
46
+ getScriptElement:function (scriptName) {
47
+ var regex = new RegExp(scriptName);
48
+ var scripts = document.getElementsByTagName('script');
49
+ for (var i=0; i<scripts.length; i++) {
50
+ if (scripts[i].src && regex.test(scripts[i].src))
51
+ return scripts[i];
52
+ }
53
+ return '';
54
+ },
55
+
56
+ getScriptPath: function (scriptElement, scriptName) {
57
+ var regex = new RegExp(scriptName+".*");
58
+ return scriptElement.src.replace(regex, '');
59
+ },
60
+
61
+ addScript: function (path) {
62
+ if (this.Browser.IE || this.Browser.WebKit || this.Browser.Konqueror) {
63
+ document.write('<script type="text/javascript" src="'+path+'"><\/script>');
64
+ }
65
+ else {
66
+ var script = document.createElement('script');
67
+ script.src = path;
68
+ script.setAttribute('type', 'text/javascript');
69
+ document.getElementsByTagName('head')[0].appendChild(script);
70
+ }
71
+ },
72
+
73
+ addScripts: function (basePath, filenames) {
74
+ for (var i=0; i<filename.length; i++)
75
+ this.addScript(basepath+filenames[i]);
76
+ },
77
+
78
+ addStylesheet: function (path) {
79
+ if (this.Browser.Gecko19) {
80
+ var link = document.createElement('link');
81
+ link.setAttribute('rel', 'stylesheet');
82
+ link.setAttribute('href', path);
83
+ link.setAttribute('type', 'text/css');
84
+ link.setAttribute('media', 'screen');
85
+ document.getElementsByTagName('head')[0].appendChild(link);
86
+ }
87
+ else {
88
+ document.write('<link rel="stylesheet" href="'+path+'" type="text/css" media="screen" />');
89
+ }
90
+
91
+ },
92
+
93
+ addStylesheets: function (basePath, filenames) {
94
+ for (var i=0; i<filename.length; i++)
95
+ this.addStylesheet(basepath+filenames[i]);
96
+ },
97
+
98
+ initPath: function () {
99
+ /* get / set basic values */
100
+ this.scriptElement = this.getScriptElement(this.scriptName);
101
+ if (!this.scriptElement) {
102
+ this.scriptName = 'contentflow_src.js';
103
+ this.scriptElement = this.getScriptElement(this.scriptName);
104
+ }
105
+
106
+ this.BaseDir = this.getScriptPath(this.scriptElement, this.scriptName) ;
107
+ if (!this.AddOnBaseDir) this.AddOnBaseDir = this.BaseDir;
108
+ if (!this.CSSBaseDir) this.CSSBaseDir = this.BaseDir;
109
+ },
110
+
111
+ init: function () {
112
+ /* add default stylesheets */
113
+ this.addStylesheet(this.CSSBaseDir+'contentflow.css');
114
+ this.addStylesheet(this.CSSBaseDir+'mycontentflow.css'); // FF2: without adding a css-file FF2 hangs on a reload.
115
+ // I don't have the slidest idea why
116
+ // Could be timing problem
117
+ this.loadAddOns = new Array();
118
+ /* add AddOns scripts */
119
+ if (this.scriptElement.getAttribute('load')) {
120
+ var AddOns = this.loadAddOns = this.scriptElement.getAttribute('load').replace(/\ +/g,' ').split(' ');
121
+ for (var i=0; i<AddOns.length; i++) {
122
+ if (AddOns[i] == '') continue;
123
+ //if (AddOns[i] == 'myStyle') {
124
+ //this.addStylesheet(this.BaseDir+'mycontentflow.css');
125
+ //continue;
126
+ //}
127
+ this.addScript(this.AddOnBaseDir+'ContentFlowAddOn_'+AddOns[i]+'.js');
128
+ }
129
+ }
130
+
131
+ /* ========== ContentFlow auto initialization on document load ==========
132
+ * thanks to Dean Edwards
133
+ * http://dean.edwards.name/weblog/2005/02/order-of-events/
134
+ */
135
+ var CFG = this;
136
+
137
+ /* for Mozilla, Opera 9, Safari */
138
+ if (document.addEventListener) {
139
+ /* for Safari */
140
+ if (this.Browser.WebKit) {
141
+ var _timer = setInterval(function() {
142
+ if (/loaded|complete/.test(document.readyState)) {
143
+ clearInterval(_timer);
144
+ CFG.onloadInit(); // call the onload handler
145
+ }
146
+ }, 10);
147
+ }
148
+ else {
149
+ document.addEventListener("DOMContentLoaded", CFG.onloadInit, false);
150
+ }
151
+ }
152
+ else if (this.Browser.IE) {
153
+ document.write("<script id=__ie_cf_onload defer src=javascript:void(0)><\/script>");
154
+ var script = document.getElementById("__ie_cf_onload");
155
+ script.onreadystatechange = function() {
156
+ if (this.readyState == "complete") {
157
+ CFG.onloadInit(); // call the onload handler
158
+ }
159
+ };
160
+ }
161
+
162
+ /* for all other browsers */
163
+ window.addEvent('load', CFG.onloadInit, false);
164
+
165
+ /* ================================================================== */
166
+
167
+ },
168
+
169
+ onloadInit: function () {
170
+ // quit if this function has already been called
171
+ if (arguments.callee.done) return;
172
+ for (var i=0; i< ContentFlowGlobal.loadAddOns.length; i++) {
173
+ var a = ContentFlowGlobal.loadAddOns[i];
174
+ if (!ContentFlowGlobal.AddOns[a]) {
175
+ var CFG = ContentFlowGlobal;
176
+ window.setTimeout( CFG.onloadInit, 10);
177
+ return;
178
+ }
179
+ }
180
+ // flag this function so we don't do the same thing twice
181
+ arguments.callee.done = true;
182
+
183
+ /* fix for mootools */
184
+ if (window.Element && Element.implement && document.all && !window.opera) {
185
+ for (var prop in window.CFElement.prototype) {
186
+ if(!window.Element.prototype[prop]) {
187
+ var implement = {};
188
+ implement[prop] = window.CFElement.prototype[prop];
189
+ Element.implement(implement);
190
+ }
191
+ }
192
+ }
193
+
194
+ /* init all manualy created flows */
195
+ for (var i=0; i< ContentFlowGlobal.Flows.length; i++) {
196
+ ContentFlowGlobal.Flows[i].init();
197
+ }
198
+
199
+ /* init the rest */
200
+ var divs = document.getElementsByTagName('div');
201
+ DIVS: for (var i = 0; i < divs.length; i++) {
202
+ if (divs[i].className.match(/\bContentFlow\b/)) {
203
+ for (var j=0; j<ContentFlowGlobal.Flows.length; j++) {
204
+ if (divs[i] == ContentFlowGlobal.Flows[j].Container) continue DIVS;
205
+ }
206
+ var CF = new ContentFlow(divs[i],{}, false);
207
+ CF.init();
208
+ }
209
+ }
210
+ }
211
+
212
+ };
213
+
214
+ ContentFlowGlobal.initPath();
215
+
216
+
217
+ /*
218
+ * ============================================================
219
+ * ContentFlowAddOn
220
+ * ============================================================
221
+ */
222
+ var ContentFlowAddOn = function (name, methods, register) {
223
+ if (typeof register == "undefined" || register != false)
224
+ ContentFlowGlobal.AddOns[name] = this;
225
+
226
+ this.name = name;
227
+ if (!methods) methods = {};
228
+ this.methods = methods;
229
+ this.conf = {};
230
+ if (this.methods.conf) {
231
+ this.setConfig(this.methods.conf);
232
+ delete this.methods.conf;
233
+ }
234
+
235
+
236
+ this.scriptpath = ContentFlowGlobal.AddOnBaseDir;
237
+ if (methods.init) {
238
+ var init = methods.init.bind(this);
239
+ init(this);
240
+ }
241
+ };
242
+
243
+ ContentFlowAddOn.prototype = {
244
+ Browser: ContentFlowGlobal.Browser,
245
+
246
+ addScript: ContentFlowGlobal.addScript,
247
+ addScripts: ContentFlowGlobal.addScripts,
248
+
249
+ addStylesheet: function (path) {
250
+ if (!path)
251
+ path = this.scriptpath+'ContentFlowAddOn_'+this.name+'.css';
252
+ ContentFlowGlobal.addStylesheet(path);
253
+ },
254
+ addStylesheets: ContentFlowGlobal.addStylesheets,
255
+
256
+ setConfig: function (conf) {
257
+ for (var c in conf) {
258
+ this.conf[c] = conf[c];
259
+ }
260
+ },
261
+
262
+ _init: function (flow) {
263
+ if (this.methods.ContentFlowConf) {
264
+ flow.setConfig(this.methods.ContentFlowConf);
265
+ }
266
+ }
267
+
268
+
269
+ };
270
+
271
+
272
+
273
+ /*
274
+ * ============================================================
275
+ * ContentFlowGUIElement
276
+ * ============================================================
277
+ */
278
+
279
+ var ContentFlowGUIElement = function (CFobj, element) {
280
+ element.setDimensions = function () {
281
+ this.dimensions = this.getDimensions();
282
+ this.center = {x: this.dimensions.width/2, y:this.dimensions.height/2};
283
+ this.position = this.findPos();
284
+ };
285
+ element.addObserver = function (eventName, method) {
286
+ var m = this.eventMethod = method.bind(CFobj);
287
+ this.observedEvent = eventName;
288
+ this.addEvent(eventName, m, false);
289
+ };
290
+
291
+ element.makeDraggable = function (onDrag, beforeDrag, afterDrag) {
292
+
293
+ this.stopDrag = function(event) {
294
+ if (!event) var event = window.event;
295
+ if (this.Browser.iPhone) {
296
+ window.removeEvent('touchemove', onDrag, false);
297
+ if (!this.ontochmove) {
298
+ var t = event.target;
299
+ if (t.firstChild) t = t.firstChild;
300
+ var e = document.createEvent('MouseEvents');
301
+ e.initEvent('click', true, true);
302
+ t.dispatchEvent(e);
303
+ }
304
+ }
305
+ else {
306
+ window.removeEvent('mousemove', onDrag, false);
307
+ }
308
+ afterDrag(event);
309
+ }.bind(this);
310
+
311
+ this.initDrag = function (event) {
312
+ if (!event) var event = window.event;
313
+ var e = event;
314
+ if (event.touches) e = event.touches[0];
315
+
316
+ this.mouseX = e.clientX;
317
+ this.mouseY = e.clientY;
318
+
319
+ beforeDrag(event);
320
+
321
+ }.bind(this);
322
+
323
+ this.startDrag = function (event) {
324
+ if (!event) var event = window.event;
325
+
326
+ var stopDrag = this.stopDrag;
327
+
328
+ if (this.Browser.iPhone) {
329
+ var s = this;
330
+ s.ontouchmove = false
331
+ window.addEvent('touchmove', function (e) {
332
+ s.ontouchmove = true;
333
+ onDrag(e);
334
+ }, false);
335
+ event.preventDefault();
336
+ window.addEvent('touchend', stopDrag, false);
337
+ }
338
+ else {
339
+ window.addEvent('mousemove', onDrag, false);
340
+ window.addEvent('mouseup', stopDrag, false);
341
+ }
342
+ if(event.preventDefault) { event.preventDefault() }
343
+
344
+ }.bind(this);
345
+
346
+ var startDrag = this.startDrag;
347
+ if (this.Browser.iPhone) {
348
+ this.addEventListener('touchstart', startDrag, false);
349
+ }
350
+ else {
351
+ this.addEvent('mousedown', startDrag, false);
352
+ }
353
+
354
+ };
355
+
356
+ element.Browser = ContentFlowGlobal.Browser;
357
+ $CF(element).setDimensions();
358
+ return element;
359
+ };
360
+
361
+
362
+ /*
363
+ * ============================================================
364
+ * ContentFlowItem
365
+ * ============================================================
366
+ */
367
+ var ContentFlowItem = function (CFobj, element, index) {
368
+ this.CFobj = CFobj;
369
+ this._activeElement = CFobj.conf.activeElement;
370
+ this.pre = null;
371
+ this.next = null;
372
+ /*
373
+ * ==================== item click events ====================
374
+ * handles the click event on an active and none active item
375
+ */
376
+
377
+ this.clickItem = function (event) {
378
+ if(!event) var event = window.event;
379
+ var el = event.target ? event.target : event.srcElement;
380
+ var index = el.itemIndex ? el.itemIndex : el.parentNode.itemIndex;
381
+ var item = this.items[index];
382
+ if (this._activeItem == item) {
383
+ this.conf.onclickActiveItem(item);
384
+ }
385
+ else {
386
+ if (this.conf.onclickInactiveItem(item) != false ) this.moveToIndex(index);
387
+ }
388
+ }.bind(CFobj),
389
+
390
+ this.setIndex = function (index) {
391
+ this.index = index;
392
+ this.element.itemIndex = index;
393
+ };
394
+ this.getIndex = function () {
395
+ return this.index;
396
+ };
397
+
398
+
399
+ /* generate deault HTML structure if item is an image */
400
+ if ($CF(element).nodeName == "IMG") {
401
+ var el = document.createElement('div');
402
+ el.className = "item";
403
+
404
+ var cont = element.parentNode.replaceChild( el, element);
405
+ cont.className = "content";
406
+ el.appendChild(cont);
407
+
408
+ if (element.title) {
409
+ var cap = document.createElement('div');
410
+ cap.className = "caption";
411
+ cap.innerHTML = element.title;
412
+ el.appendChild(cap);
413
+ }
414
+ element = el;
415
+ }
416
+
417
+ /* create item object */
418
+ this.element = $CF(element);
419
+ this.item = element;
420
+ if (typeof index != "undefined") this.setIndex(index);
421
+ this.content = this.element.getChildrenByClassName('content')[0];
422
+ this.caption = this.element.getChildrenByClassName('caption')[0];
423
+ this.label = this.element.getChildrenByClassName('label')[0];
424
+
425
+ /* if content is image set properties */
426
+ if (this.content.nodeName == "IMG") {
427
+ CFobj._imagesToLoad++;
428
+
429
+ var foobar = function () {
430
+ CFobj._imagesToLoad--;
431
+ this.image = this.content;
432
+ this.setImageFormat(this.image);
433
+ if ( CFobj.conf.reflectionHeight > 0) {
434
+ this.addReflection();
435
+ }
436
+ this.initClick();
437
+ CFobj._addItemCueProcess(true);
438
+ }.bind(this);
439
+
440
+ if (this.content.complete && this.content.width > 0)
441
+ window.setTimeout(foobar, 100);
442
+ else if (this.Browser.IE && !this.content.onload) {
443
+ var self = this;
444
+ var t = window.setInterval( function () {
445
+ if (self.content.complete && self.content.width > 0) {
446
+ window.clearInterval(t);
447
+ foobar();
448
+ }
449
+ }, 10);
450
+ }
451
+ else
452
+ this.content.onload = window.setTimeout(foobar, 100);
453
+ }
454
+ else {
455
+ this.initClick();
456
+ CFobj._addItemCueProcess(true);
457
+ }
458
+
459
+ };
460
+
461
+ ContentFlowItem.prototype = {
462
+
463
+ Browser: ContentFlowGlobal.Browser,
464
+
465
+ makeActive: function () {
466
+ this.element.addClassName('active');
467
+ this.CFobj.conf.onMakeActive(this);
468
+ },
469
+
470
+ makeInactive: function () {
471
+ this.element.removeClassName('active');
472
+ this.CFobj.conf.onMakeInactive(this);
473
+ },
474
+
475
+ initClick: function () {
476
+ var cItem = this.clickItem;
477
+ this[this._activeElement].addEvent('click', cItem, false);
478
+ },
479
+
480
+ setImageFormat: function (img) {
481
+ if (this.Browser.IE6 || this.Browser.IE7) img.style.width = "auto";
482
+ img.origProportion = img.width / img.height;
483
+ img.setAttribute('origProportion', img.width / img.height);
484
+ if (this.Browser.IE6 || this.Browser.IE7) img.style.width = "";
485
+ //img.origWidth = img.width;
486
+ //img.origHeight = img.height;
487
+ if (img.origProportion <= 1)
488
+ img.addClassName('portray');
489
+ else
490
+ img.addClassName('landscape');
491
+ },
492
+
493
+ /*
494
+ * add reflection to item
495
+ */
496
+ addReflection: function() {
497
+ var CFobj = this.CFobj;
498
+ var reflection;
499
+ var image = this.content;
500
+
501
+
502
+ if (this.Browser.IE) {
503
+ var filterString = 'progid:DXImageTransform.Microsoft.BasicImage(rotation=2, mirror=1)';
504
+ if (CFobj._reflectionColorRGB) {
505
+ // transparent gradient
506
+ if (CFobj.conf.reflectionColor == "transparent") {
507
+ var RefImg = reflection = this.reflection = document.createElement('img');
508
+ reflection.src = image.src;
509
+ }
510
+ // color gradient
511
+ else {
512
+ reflection = this.reflection = document.createElement('div');
513
+ var RefImg = document.createElement('img');
514
+ RefImg.src = image.src;
515
+ reflection.width = RefImg.width;
516
+ reflection.height = RefImg.height;
517
+ RefImg.style.width = '100%';
518
+ RefImg.style.height = '100%';
519
+ var color = CFobj._reflectionColorRGB;
520
+ reflection.style.backgroundColor = '#'+color.hR+color.hG+color.hB;
521
+ reflection.appendChild(RefImg);
522
+ }
523
+ filterString += ' progid:DXImageTransform.Microsoft.Alpha(opacity=0, finishOpacity=50, style=1, finishX=0, startY='+CFobj.conf.reflectionHeight*100+' finishY=0)';
524
+ } else {
525
+ var RefImg = reflection = this.reflection = document.createElement('img');
526
+ reflection.src = image.src;
527
+ }
528
+ // crop image (streches and crops (clip on default dimensions), original proportions will be restored through CSS)
529
+ filterString += ' progid:DXImageTransform.Microsoft.Matrix(M11=1, M12=0, M21=0, M22='+1/CFobj.conf.reflectionHeight+')';
530
+
531
+ if (ContentFlowGlobal.Browser.IE6) {
532
+ if (image.src.match(/\.png$/) ) {
533
+ image.style.filter = "progid:DXImageTransform.Microsoft.AlphaImageLoader(src='"+image.src+"', sizingMethod=scale )";
534
+ image.filterString = "progid:DXImageTransform.Microsoft.AlphaImageLoader(src='"+image.src+"', sizingMethod=scale )";
535
+ filterString += " progid:DXImageTransform.Microsoft.AlphaImageLoader(src='"+image.src+"', sizingMethod=scale )";
536
+ image.origSrc = image.src;
537
+ image.src='img/blank.gif';
538
+ RefImg.src="img/blank.gif";
539
+ }
540
+ }
541
+
542
+ reflection.filterString = filterString;
543
+ RefImg.style.filter = filterString;
544
+
545
+ } else {
546
+ if (CFobj._reflectionWithinImage)
547
+ var canvas = this.canvas = $CF(document.createElement('canvas'));
548
+ else
549
+ var canvas = reflection = this.reflection = document.createElement('canvas');
550
+
551
+ if (canvas.getContext) {
552
+ if (CFobj._reflectionWithinImage) {
553
+ for (var i=0; i <image.attributes.length; i++) {
554
+ canvas.setAttributeNode(image.attributes[i].cloneNode(true));
555
+ }
556
+ }
557
+
558
+ var context = canvas.getContext("2d");
559
+
560
+ /* calc image size */
561
+ var max = CFobj.maxHeight;
562
+ var size = CFobj._scaleImageSize(this, {width: max, height: max }, max)
563
+ var width = size.width;
564
+ var height = size.height;
565
+
566
+ // overwrite default height and width
567
+ if (CFobj._reflectionWithinImage) {
568
+ canvas.width = width;
569
+ canvas.height = height;
570
+ this.setImageFormat(canvas);
571
+ canvas.height = height * (1 + CFobj.conf.reflectionHeight + CFobj.conf.reflectionGap);
572
+
573
+ }
574
+ else {
575
+ canvas.width = width;
576
+ canvas.height = height * CFobj.conf.reflectionHeight;
577
+ }
578
+
579
+ context.save(); /* save default context */
580
+
581
+ /* draw image into canvas */
582
+ if (CFobj._reflectionWithinImage) {
583
+ context.drawImage(image, 0, 0, width, height);
584
+ }
585
+
586
+ /* mirror image by transformation of context and image drawing */
587
+ if (CFobj._reflectionWithinImage) {
588
+ var contextHeight = height * ( 1 + CFobj.conf.reflectionGap/2) * 2;
589
+ }
590
+ else {
591
+ var contextHeight = image.height;
592
+ }
593
+ // -1 for FF 1.5
594
+ contextHeight -= 1;
595
+
596
+ context.translate(0, contextHeight);
597
+ context.scale(1, -1);
598
+ /* draw reflection image into canvas */
599
+ context.drawImage(image, 0, 0, width, height);
600
+
601
+ /* restore default context for simpler further canvas manupulation */
602
+ context.restore();
603
+
604
+ if (CFobj._reflectionColorRGB) {
605
+ var gradient = context.createLinearGradient(0, 0, 0, canvas.height);
606
+
607
+ var alpha = [0, 0.5, 1];
608
+ if (CFobj._reflectionColor == "transparent") {
609
+ context.globalCompositeOperation = "destination-in";
610
+ alpha = [1, 0.5, 0];
611
+ }
612
+
613
+ var red = CFobj._reflectionColorRGB.iR;
614
+ var green = CFobj._reflectionColorRGB.iG;
615
+ var blue = CFobj._reflectionColorRGB.iB;
616
+ if (CFobj._reflectionWithinImage) {
617
+ gradient.addColorStop(0, 'rgba('+red+','+green+','+blue+','+alpha[0]+')');
618
+ gradient.addColorStop(height/canvas.height, 'rgba('+red+','+green+','+blue+','+alpha[0]+')');
619
+ gradient.addColorStop(height/canvas.height, 'rgba('+red+','+green+','+blue+','+alpha[1]+')');
620
+ }
621
+ else {
622
+ gradient.addColorStop(0, 'rgba('+red+','+green+','+blue+','+alpha[1]+')');
623
+ }
624
+ gradient.addColorStop(1, 'rgba('+red+','+green+','+blue+','+alpha[2]+')');
625
+
626
+ context.fillStyle = gradient;
627
+ context.fillRect(0, 0, canvas.width, canvas.height);
628
+
629
+ }
630
+
631
+ if (CFobj._reflectionWithinImage) {
632
+ image.parentNode.replaceChild(canvas, image);
633
+ this.content = canvas;
634
+ this.origContent = canvas;
635
+ delete this.image;// = true;
636
+
637
+ }
638
+
639
+ } else {
640
+ CFobj._reflectionWithinImage = false;
641
+ delete this.reflection;
642
+ }
643
+
644
+ }
645
+ if (reflection) {
646
+ reflection.className = "reflection";
647
+ this.element.appendChild(reflection);
648
+
649
+ /* be shure that caption is last child */
650
+ if (this.caption) this.element.appendChild(this.caption);
651
+ }
652
+
653
+ }
654
+
655
+
656
+ };
657
+
658
+ /*
659
+ * ============================================================
660
+ * ContentFlow
661
+ * ============================================================
662
+ */
663
+ var ContentFlow = function (container, config) {
664
+
665
+ if (container) {
666
+ ContentFlowGlobal.Flows.push(this);
667
+ this.Container = container;
668
+ this._userConf = config?config:{};
669
+ this.conf = {};
670
+ this._loadedAddOns = new Array();
671
+ } else {
672
+ throw ('ContentFlow ERROR: No flow container node or id given');
673
+ }
674
+
675
+ };
676
+
677
+ ContentFlow.prototype = {
678
+ _imagesToLoad: 0,
679
+ _activeItem: 0,
680
+ _currentPosition: 0,
681
+ _targetPosition: 0,
682
+ _stepLock: false,
683
+ _millisecondsPerStep: 40,
684
+ _reflectionWithinImage: true,
685
+ Browser: ContentFlowGlobal.Browser,
686
+
687
+ _defaultConf: {
688
+ /* pre conf */
689
+ useAddOns: 'all', // all, none, [AddOn1, ... , AddOnN]
690
+
691
+ biggestItemPos: 0,
692
+ loadingTimeout: 30000, //milliseconds
693
+ activeElement: 'content', // item or content
694
+
695
+ maxItemHeight: 0,
696
+ scaleFactor: 1,
697
+ scaleFactorLandscape: 1.33,
698
+ scaleFactorPortrait: 1.0,
699
+ fixItemSize: false,
700
+ relativeItemPosition: "top center", // align top/above, bottom/below, left, right, center of position coordinate
701
+
702
+ circularFlow: true,
703
+ verticalFlow: false,
704
+ visibleItems: -1,
705
+ endOpacity: 1,
706
+ startItem: "center",
707
+ scrollInFrom: "pre",
708
+
709
+ flowSpeedFactor: 1.0,
710
+ flowDragFriction: 1.0,
711
+ scrollWheelSpeed: 1.0,
712
+ keys: {
713
+ 13: function () { this.conf.onclickActiveItem(this._activeItem) },
714
+ 37: function () { this.moveTo('pre') },
715
+ 38: function () { this.moveTo('visibleNext') },
716
+ 39: function () { this.moveTo('next') },
717
+ 40: function () { this.moveTo('visiblePre') }
718
+ },
719
+
720
+ reflectionColor: "transparent", // none, transparent or hex RGB CSS style #RRGGBB
721
+ reflectionHeight: 0.5, // float (relative to original image height)
722
+ reflectionGap: 0.0,
723
+
724
+ /* ==================== actions ==================== */
725
+
726
+ onInit: function () {},
727
+
728
+ onclickInactiveItem: function (item) {},
729
+
730
+ onclickActiveItem: function (item) {
731
+ var url, target;
732
+
733
+ if (url = item.content.getAttribute('href')) {
734
+ target = item.content.getAttribute('target');
735
+ }
736
+ else if (url = item.element.getAttribute('href')) {
737
+ target = item.element.getAttribute('target');
738
+ }
739
+ else if (url = item.content.getAttribute('src')) {
740
+ target = item.content.getAttribute('target');
741
+ }
742
+
743
+ if (url) {
744
+ if (target)
745
+ window.open(url, target).focus();
746
+ else
747
+ window.location.href = url;
748
+ }
749
+ },
750
+
751
+ onMakeInactive: function (item) {},
752
+
753
+ onMakeActive: function (item) {},
754
+
755
+ onReachTarget: function(item) {},
756
+
757
+ onMoveTo: function(item) {},
758
+
759
+ //onDrawItem: function(item, relativePosition, relativePositionNormed, side, size) {},
760
+ onDrawItem: function(item) {},
761
+
762
+ onclickPreButton: function (event) {
763
+ this.moveToIndex('pre');
764
+ return Event.stop(event);
765
+ },
766
+
767
+ onclickNextButton: function (event) {
768
+ this.moveToIndex('next');
769
+ return Event.stop(event);
770
+ },
771
+
772
+ /* ==================== calculations ==================== */
773
+
774
+ calcStepWidth: function(diff) {
775
+ var vI = this.conf.visibleItems;
776
+ var items = this.items.length;
777
+ items = items == 0 ? 1 : items;
778
+ if (Math.abs(diff) > vI) {
779
+ if (diff > 0) {
780
+ var stepwidth = diff - vI;
781
+ } else {
782
+ var stepwidth = diff + vI;
783
+ }
784
+ } else if (vI >= this.items.length) {
785
+ var stepwidth = diff / items;
786
+ } else {
787
+ var stepwidth = diff * ( vI / items);
788
+ //var stepwidth = diff/absDiff * Math.max(diff * diff,Math.min(absDiff,0.3)) * ( vI / this.items.length);
789
+ //var stepwidth = this.flowSpeedFactor * diff / this.visibleItems;
790
+ //var stepwidth = this.flowSpeedFactor * diff * ( this.visibleItems / this.items.length)
791
+ //var stepwidth = this.flowSpeedFactor * diff / this._millisecondsPerStep * 2; // const. speed
792
+ }
793
+ return stepwidth;
794
+ },
795
+
796
+ calcSize: function (item) {
797
+ var rP = item.relativePosition;
798
+ //var rPN = relativePositionNormed;
799
+ //var vI = this.conf.visibleItems;
800
+
801
+ var h = 1/(Math.abs(rP)+1);
802
+ var w = h;
803
+ return {width: w, height: h};
804
+ },
805
+
806
+ calcCoordinates: function (item) {
807
+ var rP = item.relativePosition;
808
+ //var rPN = item.relativePositionNormed;
809
+ var vI = this.conf.visibleItems;
810
+
811
+ var f = 1 - 1/Math.exp( Math.abs(rP)*0.75);
812
+ var x = item.side * vI/(vI+1)* f;
813
+ var y = 1;
814
+
815
+ return {x: x, y: y};
816
+ },
817
+
818
+ /*
819
+ calcRelativeItemPosition: function (item) {
820
+ var x = 0;
821
+ var y = -1;
822
+ return {x: x, y: y};
823
+ },
824
+ */
825
+
826
+ calcZIndex: function (item) {
827
+ return -Math.abs(item.relativePositionNormed);
828
+ },
829
+
830
+ calcFontSize: function (item) {
831
+ return item.size.height;
832
+ },
833
+
834
+ calcOpacity: function (item) {
835
+ return Math.max(1 - ((1 - this.conf.endOpacity ) * Math.sqrt(Math.abs(item.relativePositionNormed))), this.conf.endOpacity);
836
+ }
837
+ },
838
+
839
+ /* ---------- end of defaultConf ---------- */
840
+
841
+
842
+ /*
843
+ * ==================== index helper methods ====================
844
+ */
845
+
846
+ /*
847
+ * checks if index is within the index range of the this.items array
848
+ * returns a value that is within this range
849
+ */
850
+ _checkIndex: function (index) {
851
+ index = Math.max(index, 0);
852
+ index = Math.min(index, this.itemsLastIndex);
853
+ return index;
854
+ },
855
+
856
+ /*
857
+ * sets the object property itemsLastIndex
858
+ */
859
+ _setLastIndex: function () {
860
+ this.itemsLastIndex = this.items.length - 1;
861
+ },
862
+
863
+ /*
864
+ */
865
+ _getItemByIndex: function (index) {
866
+ return this.items[this._checkIndex(index)];
867
+ },
868
+
869
+ _getItemByPosition: function (position) {
870
+ return this._getItemByIndex(this._getIndexByPosition(position));
871
+ },
872
+
873
+ /* returns the position of an item-index relative to current position */
874
+ _getPositionByIndex: function(index) {
875
+ if (!this.conf.circularFlow) return this._checkIndex(index);
876
+ var cI = this._getIndexByPosition(this._currentPosition);
877
+ var dI = index - cI;
878
+ if (Math.abs(dI) > dI+this.items.length)
879
+ dI += this.items.length;
880
+ else if (Math.abs(dI) > (Math.abs(dI-this.items.length)))
881
+ dI -= this.items.length;
882
+
883
+ return this._currentPosition + dI;
884
+
885
+ },
886
+
887
+ /* returns the index an item at position p would have */
888
+ _getIndexByPosition: function (position) {
889
+ if (position < 0) var mod = 0;
890
+ else var mod = 1;
891
+
892
+ var I = (Math.round(position) + mod) % this.items.length;
893
+ if (I>0) I -= mod;
894
+ else if(I<0) I += this.items.length - mod;
895
+ else if(position<0) I = 0;
896
+ else I = this.items.length - 1;
897
+
898
+ return I;
899
+ },
900
+
901
+ _getIndexByKeyWord: function (keyword, relativeTo, check) {
902
+ if (relativeTo)
903
+ var index = relativeTo;
904
+ else if (this._activeItem)
905
+ var index = this._activeItem.index;
906
+ else
907
+ var index = 0;
908
+
909
+ if (isNaN(keyword)) {
910
+ switch (keyword) {
911
+ case "first":
912
+ case "start":
913
+ index = 0;
914
+ break;
915
+ case "last":
916
+ case "end":
917
+ index = this.itemsLastIndex;
918
+ break;
919
+ case "middle":
920
+ case "center":
921
+ index = Math.round(this.itemsLastIndex/2);
922
+ break;
923
+ case "right":
924
+ case "next":
925
+ index += 1;
926
+ break;
927
+ case "left":
928
+ case "pre":
929
+ case "previous":
930
+ index -= 1;
931
+ break;
932
+ case 'visible':
933
+ case 'visiblePre':
934
+ case 'visibleLeft':
935
+ index -= this.conf.visibleItems;
936
+ break;
937
+ case 'visibleNext':
938
+ case 'visibleRight':
939
+ index += this.conf.visibleItems;
940
+ break;
941
+ default:
942
+ index = index;
943
+ }
944
+ }
945
+ else {
946
+ index = keyword;
947
+ }
948
+ if (check != false)
949
+ index = this._checkIndex(index);
950
+
951
+ return index;
952
+ },
953
+
954
+
955
+ _setCaptionLabel: function (index) {
956
+ if(this.Position && !this.Slider.locked)
957
+ this.Position.setLabel(index);
958
+ this._setGlobalCaption();
959
+ },
960
+
961
+
962
+ /*
963
+ * ==================== public methods ====================
964
+ */
965
+ getAddOnConf: function(name) {
966
+ return ContentFlowGlobal.getAddOnConf(name);
967
+ },
968
+
969
+ setAddOnConf: function(name, conf) {
970
+ ContentFlowGlobal.setAddOnConf(name, conf);
971
+ },
972
+
973
+
974
+ /*
975
+ * calls _init() if ContentFlow has not been initialized before
976
+ * needed if ContentFlow is not automatically initialized on window.load
977
+ */
978
+ init: function () {
979
+ if(this.isInit) return;
980
+ this._init();
981
+ },
982
+
983
+ /*
984
+ * parses configuration object and initializes configuration values
985
+ */
986
+ setConfig: function(config) {
987
+ if (!config) return;
988
+ var dC = this._defaultConf;
989
+ for (var option in config) {
990
+ if (dC[option] == "undefined" ) continue;
991
+ switch (option) {
992
+ case "scrollInFrom":
993
+ case "startItem":
994
+ if (typeof(config[option]) == "number" || typeof(config[option]) == "string") {
995
+ //this["_"+option] = config[option];
996
+ this.conf[option] = config[option];
997
+ }
998
+ break;
999
+ default:
1000
+ if (typeof(dC[option] == config[option])) {
1001
+ //this["_"+option] = config[option];
1002
+ if (typeof config[option] == "function") {
1003
+ this.conf[option] = config[option].bind(this);
1004
+ }
1005
+ else {
1006
+ this.conf[option] = config[option];
1007
+ }
1008
+ }
1009
+ }
1010
+ }
1011
+ switch (this.conf.reflectionColor) {
1012
+ case this.conf.reflectionColor.search(/#[0-9a-fA-F]{6}/)>= 0?this.conf.reflectionColor:this.conf.reflectionColor+"x":
1013
+ this._reflectionColorRGB = {
1014
+ hR: this.conf.reflectionColor.slice(1,3),
1015
+ hG: this.conf.reflectionColor.slice(3,5),
1016
+ hB: this.conf.reflectionColor.slice(5,7),
1017
+ iR: parseInt(this.conf.reflectionColor.slice(1,3), 16),
1018
+ iG: parseInt(this.conf.reflectionColor.slice(3,5), 16),
1019
+ iB: parseInt(this.conf.reflectionColor.slice(5,7), 16)
1020
+ };
1021
+ break;
1022
+ case "none":
1023
+ case "transparent":
1024
+ default:
1025
+ this._reflectionColor = "transparent";
1026
+ this._reflectionColorRGB = {
1027
+ hR: 0, hG: 0, hB:0,
1028
+ iR: 0, iG: 0, iB:0
1029
+ };
1030
+ break;
1031
+ }
1032
+ if (this.items) {
1033
+ if (this.conf.visibleItems < 0)
1034
+ this.conf.visibleItems = Math.round(Math.sqrt(this.items.length));
1035
+ this.conf.visibleItems = Math.min(this.conf.visibleItems, this.items.length - 1);
1036
+ }
1037
+
1038
+ if (this.conf.relativeItemPosition) {
1039
+ var calcRP = {
1040
+ x: {
1041
+ left: function(size) { return -1 },
1042
+ center: function(size) { return 0 },
1043
+ right: function(size) { return 1 }
1044
+ },
1045
+ y: {
1046
+ top: function(size) { return -1 },
1047
+ center: function(size) { return 0 },
1048
+ bottom: function(size) { return 1 }
1049
+ }
1050
+ };
1051
+
1052
+ var iP = this.conf.relativeItemPosition;
1053
+ iP = iP.replace(/above/,"top").replace(/below/,"bottom");
1054
+ var x, y = null;
1055
+ x = iP.match(/left|right/);
1056
+ y = iP.match(/top|bottom/);
1057
+ c = iP.match(/center/);
1058
+ if (!x) {
1059
+ if (c) x = "center";
1060
+ else x = "center";
1061
+ }
1062
+ if (!y) {
1063
+ if (c) y = "center";
1064
+ else y = "top";
1065
+ }
1066
+ var calcX = calcRP.x[x];
1067
+ var calcY = calcRP.y[y];
1068
+ this.conf.calcRelativeItemPosition = function (item) {
1069
+ var x = calcX(item.size);
1070
+ var y = calcY(item.size);
1071
+ return {x: x, y: y};
1072
+ };
1073
+ this.conf.relativeItemPosition = null;
1074
+ }
1075
+
1076
+ if (this._reflectionType && this._reflectionType != "clientside") {
1077
+ this.conf.reflectionHeight = 0;
1078
+ }
1079
+
1080
+ },
1081
+
1082
+ getItem: function (index) {
1083
+ return this.items[this._checkIndex(Math.round(index))];
1084
+ },
1085
+
1086
+ /*
1087
+ * returns the index number of the active item
1088
+ */
1089
+ getActiveItem: function() {
1090
+ return this._activeItem;
1091
+ },
1092
+
1093
+ /*
1094
+ * returns the number of items the flow contains
1095
+ */
1096
+ getNumberOfItems: function () {
1097
+ return this.items.length;
1098
+ },
1099
+
1100
+ /*
1101
+ * reinitializes sizes.
1102
+ * called on window.resize
1103
+ */
1104
+ resize: function () {
1105
+ this._initSizes();
1106
+ this._initStep();
1107
+ },
1108
+
1109
+ /*
1110
+ * scrolls flow to item i
1111
+ */
1112
+ moveToPosition: function (p, holdPos) {
1113
+ if (!this.conf.circularFlow) p = this._checkIndex(p);
1114
+ this._targetPosition = p;
1115
+ this.conf.onMoveTo(this._getItemByPosition(p));
1116
+ this._initStep(false, holdPos);
1117
+ },
1118
+ moveToIndex: function (index) {
1119
+ this._targetPosition = Math.round(this._getPositionByIndex(this._getIndexByKeyWord(index, this._activeItem.index, !this.conf.circularFlow)));
1120
+ this.conf.onMoveTo(this._getItemByPosition(this._targetPosition));
1121
+ this._initStep();
1122
+ },
1123
+ moveToItem: function (item) {
1124
+ var i;
1125
+ if (item.itemIndex) i = item.itemIndex;
1126
+ else i = item.index;
1127
+ this.moveToIndex(i);
1128
+ },
1129
+ moveTo: function (i) {
1130
+ if (typeof i == "object") this.moveToItem(i);
1131
+ else if (isNaN(i) || (i == Math.floor(i) && i < this.items.length) ) this.moveToIndex(i);
1132
+ else this.moveToPosition(i);
1133
+ },
1134
+
1135
+ /*
1136
+ * initializes item and adds it at index position
1137
+ */
1138
+ _addItemCue: [],
1139
+ _addItemCueProcess: function (deleteFirst) {
1140
+ var c = this._addItemCue;
1141
+ if (deleteFirst == true)
1142
+ c.shift();
1143
+ if (c.length > 0 && ! c[0].p) {
1144
+ c[0].p = true;
1145
+ var self = this;
1146
+ var t = c.length > 5 ? 1 : 40;
1147
+ window.setTimeout(function () { self._addItem(c[0].el, c[0].i)}, t) ;
1148
+ }
1149
+ },
1150
+ addItem: function(el, index) {
1151
+ this._addItemCue.push({ el: el, i: index, p: false});
1152
+ if (this._addItemCue.length == 1)
1153
+ this._addItemCueProcess();
1154
+ },
1155
+
1156
+ _addItem: function(el, index) {
1157
+ if (typeof index == "string") {
1158
+ switch (index) {
1159
+ case "first":
1160
+ case "start":
1161
+ index = 0;
1162
+ break;
1163
+ case "last":
1164
+ case "end":
1165
+ index = isNaN(this.itemsLastIndex) ? 0 : this.itemsLastIndex;
1166
+ index += 1;
1167
+ break;
1168
+ default:
1169
+ index = this._getIndexByKeyWord(index);
1170
+ }
1171
+ }
1172
+
1173
+ index = Math.max(index, 0);
1174
+ index = Math.min(index, this.itemsLastIndex + 1);
1175
+ index = isNaN(index) ? 0 : index;
1176
+
1177
+ this.Flow.appendChild(el);
1178
+
1179
+ /* init item after insertion. that way it's part of the document and all styles are applied */
1180
+ var item = new ContentFlowItem(this, el, index);
1181
+ if (this.items.length == 0 ) {
1182
+ this.resize();
1183
+ if (this.conf.circularFlow) {
1184
+ item.pre = item;
1185
+ item.next = item;
1186
+ }
1187
+ }
1188
+ else {
1189
+ if (index == this.itemsLastIndex + 1) {
1190
+ item.pre = this.items[this.itemsLastIndex];
1191
+ item.next = item.pre.next;
1192
+ }
1193
+ else {
1194
+ item.next = this.items[index];
1195
+ item.pre = item.next.pre;
1196
+ }
1197
+ if (item.pre) item.pre.next = item;
1198
+ if (item.next) item.next.pre = item;
1199
+ }
1200
+ this.items.splice(index,0, item);
1201
+
1202
+ /* adjust item indices */
1203
+ for (var i = index; i < this.items.length; i++) {
1204
+ this.items[i].setIndex(i);
1205
+ }
1206
+ this._setLastIndex();
1207
+
1208
+ if (this.conf.origVisibleItems < 0) {
1209
+ this.conf.visibleItems = Math.round(Math.sqrt(this.items.length));
1210
+ }
1211
+ this.conf.visibleItems = Math.min(this.conf.visibleItems, this.items.length - 1);
1212
+
1213
+ /* adjust targetItem, currentPos so that current view does not change*/
1214
+ if (Math.round(this._getPositionByIndex(index)) <= Math.round(this._targetPosition)) {
1215
+ this._targetPosition++;
1216
+ if (!this.conf.circularFlow)
1217
+ this._targetPosition = Math.min(this._targetPosition, this.itemsLastIndex);
1218
+ }
1219
+ if (this._getPositionByIndex(index) <= this._currentPosition) {
1220
+ this._currentPosition++;
1221
+ if (!this.conf.circularFlow)
1222
+ this._currentPosition = Math.min(this._currentPosition, this.itemsLastIndex);
1223
+ }
1224
+
1225
+ // avoid display errors (wrong sizing)
1226
+ var CF = this;
1227
+ window.setTimeout(function () {
1228
+ if(CF.items.length == 1 ) {
1229
+ CF._currentPosition = -0.01;
1230
+ CF._targetPosition = 0;
1231
+ CF.resize();
1232
+ }
1233
+ else {
1234
+ CF._initStep();
1235
+ }
1236
+ }, 100);
1237
+
1238
+ return index;
1239
+
1240
+ },
1241
+
1242
+ /*
1243
+ * removes item at index position, cleans it up and returns it
1244
+ */
1245
+ rmItem: function(index) {
1246
+ if (index == "undefined") index = this._activeItem.index;
1247
+ index = this._getIndexByKeyWord(index);
1248
+ if (!this.items[index]) return null;
1249
+
1250
+ var item = this.items[index];
1251
+
1252
+ if (item.pre) item.pre.next = item.next;
1253
+ if (item.next) item.next.pre = item.pre;
1254
+ this.items.splice(index,1);
1255
+
1256
+ /* adjust item indices */
1257
+ for (var i = index ; i < this.items.length; i++) {
1258
+ this.items[i].setIndex(i);
1259
+ }
1260
+ this._setLastIndex();
1261
+
1262
+ /* adjust targetItem, currentPos and activeItem so that current view does not change*/
1263
+ if (Math.round(this._getPositionByIndex(index)) < Math.round(this._targetPosition)) {
1264
+ this._targetPosition--;
1265
+ if (!this.conf.circularFlow)
1266
+ this._targetPosition = this._checkIndex(this._targetPosition);
1267
+ }
1268
+ if (this._getPositionByIndex(index) < this._currentPosition) {
1269
+ this._currentPosition--;
1270
+ if (!this.conf.circularFlow)
1271
+ this._currentPosition = this._checkIndex(this._currentPosition);
1272
+ }
1273
+ this._activeItem = this._getItemByPosition(this._currentPosition);
1274
+
1275
+ /* remove item from DOM tree, take the next step and return removed item */
1276
+ var removedItem = item.element.parentNode.removeChild(item.element);
1277
+ // avoid display errors (wrong sizing)
1278
+ var CF = this;
1279
+ window.setTimeout(function () { CF._initStep() }, 10);
1280
+ return removedItem;
1281
+
1282
+ },
1283
+
1284
+
1285
+ /*
1286
+ * ==================== initialization ====================
1287
+ */
1288
+
1289
+
1290
+ /* -------------------- main init -------------------- */
1291
+ _init: function () {
1292
+
1293
+ if (typeof(this.Container) == 'string') { // no node
1294
+ var container = document.getElementById(this.Container);
1295
+ if (container) {
1296
+ this.Container = container;
1297
+ } else {
1298
+ throw ('ContentFlow ERROR: No element with id \''+this.Container+'\' found!');
1299
+ return;
1300
+ }
1301
+ }
1302
+
1303
+ /* ---------- reserve CSS namespace */
1304
+
1305
+ $CF(this.Container).addClassName('ContentFlow');
1306
+
1307
+ /* ---------- detect GUI elements */
1308
+ var flow = $CF(this.Container).getChildrenByClassName('flow')[0];
1309
+ if (!flow) {
1310
+ throw ('ContentFlow ERROR: No element with class\'flow\' found!');
1311
+ return;
1312
+ }
1313
+ this.Flow = new ContentFlowGUIElement(this, flow);
1314
+
1315
+ var scrollbar = this.Container.getChildrenByClassName('scrollbar')[0];
1316
+ if (scrollbar) {
1317
+ this.Scrollbar = new ContentFlowGUIElement(this, scrollbar);
1318
+ var slider = this.Scrollbar.getChildrenByClassName('slider')[0];
1319
+ if (slider) {
1320
+ this.Slider = new ContentFlowGUIElement(this, slider);
1321
+ var position = this.Slider.getChildrenByClassName('position')[0];
1322
+ if (position) {
1323
+ this.Position = new ContentFlowGUIElement(this, position);
1324
+ }
1325
+ }
1326
+
1327
+ }
1328
+
1329
+ /* ---------- init configuration */
1330
+ this.setConfig(this._defaultConf);
1331
+ this._initAddOns(); /* init AddOns */
1332
+ this.setConfig(this._userConf);
1333
+
1334
+ this._initSizes(); // ......
1335
+
1336
+
1337
+ /* ---------- init item lists ---------- */
1338
+ var items = this.Flow.getChildrenByClassName('item');
1339
+
1340
+ this.items = new Array();
1341
+ for (var i=0; i<items.length; i++) {
1342
+ var item = this.items[i] = new ContentFlowItem(this, items[i], i);
1343
+ if (i > 0) {
1344
+ item.pre = this.items[i-1];
1345
+ item.pre.next = item;
1346
+ }
1347
+ }
1348
+ this._setLastIndex();
1349
+ if (this.conf.circularFlow && this.items.length > 0) {
1350
+ var s = this.items[0];
1351
+ s.pre = this.items[this.items.length-1];
1352
+ s.pre.next = s;
1353
+ }
1354
+
1355
+ /* ---------- init GUI */
1356
+ this._initGUI();
1357
+
1358
+ /* ---------- init start parameters ---------- */
1359
+ if (this._activeElement != "content")
1360
+ this._activeElement = "element";
1361
+
1362
+ this.conf.origVisibleItems = this.conf.visibleItems;
1363
+ if (this.conf.visibleItems < 0) {
1364
+ this.conf.visibleItems = Math.round(Math.sqrt(this.items.length));
1365
+ }
1366
+ this.conf.visibleItems = Math.min(this.conf.visibleItems, this.items.length - 1);
1367
+
1368
+ this._targetPosition = this._getIndexByKeyWord(this.conf.startItem, 0);
1369
+
1370
+ var index = this._getIndexByKeyWord(this.conf.scrollInFrom, this._targetPosition);
1371
+ switch (this.conf.scrollInFrom) {
1372
+ case "next":
1373
+ case "right":
1374
+ index -= 0.5;
1375
+ break;
1376
+ case "pre":
1377
+ case "previous":
1378
+ case "left":
1379
+ index += 0.5;
1380
+ break;
1381
+ }
1382
+ this._currentPosition = index;
1383
+
1384
+
1385
+ /* ---------- wait till all images are loaded or
1386
+ * grace time is up to show all and take the first step
1387
+ */
1388
+ var now = new Date();
1389
+ var cf = this;
1390
+ var timer = window.setInterval (
1391
+ function() {
1392
+ if ( cf._imagesToLoad == 0 || new Date() - now > cf._loadingTimeout ) {
1393
+ clearInterval(timer);
1394
+
1395
+ cf._activeItem = cf.getItem(cf._currentPosition);
1396
+ if (cf._activeItem) {
1397
+ cf._activeItem.makeActive();
1398
+ cf._setCaptionLabel(cf._activeItem.index);
1399
+ }
1400
+
1401
+ cf.Flow.style.visibility = "visible"; // show flow after images are loaded
1402
+ if (cf.loadIndicator) cf.loadIndicator.style.display = "none";
1403
+ if (cf.Scrollbar) cf.Scrollbar.style.visibility = "visible";
1404
+
1405
+ cf.resize();
1406
+ for (var i=0; i < cf._loadedAddOns.length; i++) {
1407
+ var a = ContentFlowGlobal.AddOns[cf._loadedAddOns[i]];
1408
+ if (a.methods.afterContentFlowInit)
1409
+ a.methods.afterContentFlowInit(cf);
1410
+ }
1411
+ cf.conf.onInit();
1412
+ }
1413
+ }, 10
1414
+ );
1415
+
1416
+ this.isInit = true;
1417
+
1418
+ },
1419
+
1420
+ /* ---------- init AddOns ---------- */
1421
+ _initAddOns: function () {
1422
+
1423
+ // get an array of names of all AddOns that should be used
1424
+ var loadAddOns = [];
1425
+ if (this._userConf.useAddOns) {
1426
+ if (typeof this._userConf.useAddOns == "string") {
1427
+ loadAddOns = this._userConf.useAddOns.split(" ");
1428
+ }
1429
+ else if (typeof this._userConf.useAddOns == "array") {
1430
+ loadAddOns = this._userConf.useAddOns;
1431
+ }
1432
+ }
1433
+ else if (this.Container.getAttribute("useAddOns")) {
1434
+ loadAddOns = this.Container.getAttribute("useAddOns").split(" ");
1435
+ }
1436
+ else {
1437
+ loadAddOns = this.conf.useAddOns.split(' ');
1438
+ }
1439
+
1440
+
1441
+ // check the names for keywords
1442
+ for (var i=0; i<loadAddOns.length; i++) {
1443
+ if (loadAddOns[i] == "none") {
1444
+ loadAddOns = new Array();
1445
+ break;
1446
+ }
1447
+ else if (loadAddOns[i] == "all") {
1448
+ loadAddOns = new Array();
1449
+ for (var AddOn in ContentFlowGlobal.AddOns)
1450
+ loadAddOns.push(AddOn);
1451
+ break;
1452
+ }
1453
+ }
1454
+
1455
+ // init all AddOns that should be used and exist
1456
+ for (var i=0; i<loadAddOns.length; i++) {
1457
+ var AddOn = ContentFlowGlobal.AddOns[loadAddOns[i]];
1458
+ if (AddOn) {
1459
+ this._loadedAddOns.push(loadAddOns[i]);
1460
+ AddOn._init(this);
1461
+ this.Container.addClassName('ContentFlowAddOn_'+AddOn.name);
1462
+ if (AddOn.methods.onloadInit)
1463
+ AddOn.methods.onloadInit(this);
1464
+ }
1465
+ }
1466
+
1467
+ },
1468
+
1469
+
1470
+ _initGUI: function () {
1471
+
1472
+ // resize
1473
+ //if (!this.Browser.iPhone) {
1474
+ var resize = this.resize.bind(this);
1475
+ window.addEvent('resize', resize, false);
1476
+ //}
1477
+ //else {
1478
+ //var g = this;
1479
+ //window.addEvent('resize', function () {
1480
+ //g._initSizes();
1481
+ //g._initStep();
1482
+ //} , false);
1483
+ //}
1484
+
1485
+ // pre and next buttons
1486
+ var divs = this.Container.getElementsByTagName('div');
1487
+ for (var i = 0; i < divs.length; i++) {
1488
+ if ($CF(divs[i]).hasClassName('preButton')) {
1489
+ var pre = divs[i];
1490
+ var mt = this.conf.onclickPreButton;
1491
+ pre.addEvent('click', mt, false);
1492
+ }
1493
+ else if (divs[i].hasClassName('nextButton')) {
1494
+ var next = divs[i];
1495
+ var mt = this.conf.onclickNextButton;
1496
+ next.addEvent('click', mt, false);
1497
+ }
1498
+ }
1499
+
1500
+ // Container object
1501
+ // mousewheel
1502
+ if (this.conf.scrollWheelSpeed != 0) {
1503
+ var wheel = this._wheel.bind(this);
1504
+ if(window.addEventListener) this.Container.addEventListener('DOMMouseScroll', wheel, false);
1505
+ this.Container.onmousewheel = wheel;
1506
+ }
1507
+
1508
+ // key strokes
1509
+ var key = this._keyStroke.bind(this);
1510
+ if (this.conf.keys && !this.Browser.iPhone) {
1511
+ if (document.addEventListener) {
1512
+ if (!this.Browser.Opera) {
1513
+ var mouseoverCheck = document.createElement('div');
1514
+ mouseoverCheck.addClassName('mouseoverCheckElement');
1515
+ this.Container.appendChild(mouseoverCheck);
1516
+
1517
+ if (this.Browser.WebKit) {
1518
+ document.body.addEvent('keydown', function (event) {
1519
+ if (mouseoverCheck.offsetLeft > 0) key(event) ;
1520
+ });
1521
+ } else {
1522
+ window.addEvent('keydown', function (event) {
1523
+ if (mouseoverCheck.offsetLeft > 0) key(event) ;
1524
+ });
1525
+ }
1526
+ }
1527
+ else {
1528
+ this.Container.addEvent('keydown', key);
1529
+ }
1530
+ }
1531
+ else {
1532
+ this.Container.onkeydown = key;
1533
+ }
1534
+ }
1535
+
1536
+
1537
+ // Flow object
1538
+ if (this.conf.flowDragFriction > 0) {
1539
+ var onDrag = function (event) {
1540
+ var e = event;
1541
+ if (event.touches) e = event.touches[0];
1542
+ var mouseX = e.clientX;
1543
+ var mouseY = e.clientY;
1544
+
1545
+ if (this.conf.verticalFlow) {
1546
+ var dist = mouseY - this.Flow.mouseY; // px / or px per sec because _dragFlow wil be called in shorter intervalls if draged fast
1547
+ var dim = this.Flow.dimensions.height;
1548
+ }
1549
+ else {
1550
+ var dist = mouseX - this.Flow.mouseX; // px / or px per sec because _dragFlow wil be called in shorter intervalls if draged fast
1551
+ var dim = this.Flow.dimensions.width;
1552
+ }
1553
+ var itemDist = (dist / dim )* (2*this.conf.visibleItems +1); // items
1554
+ var target = this._currentPosition - itemDist * 2*this.conf.visibleItems / this.conf.flowDragFriction ;
1555
+
1556
+ this.Flow.mouseX = mouseX;
1557
+ this.Flow.mouseY = mouseY;
1558
+
1559
+ this.moveToPosition(target, true);
1560
+ }.bind(this);
1561
+
1562
+ var beforeDrag = function () {};
1563
+
1564
+ var afterDrag = function (event) {
1565
+ var t = Math.round(this._targetPosition);
1566
+ if (Math.abs( t - this._currentPosition) > 0.001 )
1567
+ this.moveToPosition(t);
1568
+ }.bind(this);
1569
+
1570
+
1571
+ this.Flow.makeDraggable(onDrag, beforeDrag, afterDrag);
1572
+ }
1573
+
1574
+ // Scrollbar Object
1575
+ if (this.Scrollbar) {
1576
+ var click = function(event) {
1577
+ if (!event) var event = window.event;
1578
+
1579
+ if (!this.Scrollbar.clickLocked) {
1580
+ var mouseX = event.clientX;
1581
+ var positionOnScrollbar = mouseX - this.Scrollbar.position.left;
1582
+ var targetIndex = Math.round(positionOnScrollbar/this.Scrollbar.dimensions.width * this.itemsLastIndex);
1583
+ this.moveToIndex(targetIndex);
1584
+ }
1585
+ else
1586
+ this.Scrollbar.clickLocked = false;
1587
+ }.bind(this);
1588
+ this.Scrollbar.addObserver('click', click);
1589
+ }
1590
+
1591
+ // Slider Object
1592
+ if (this.Slider) {
1593
+
1594
+ if (this.Browser.IE6) {
1595
+ var virtualSlider = document.createElement('div');
1596
+ virtualSlider.className = 'virtualSlider';
1597
+ this.Slider.appendChild(virtualSlider);
1598
+ }
1599
+
1600
+ // position slider on scrollbar
1601
+ this.Slider.setPosition = function (relPos) {
1602
+ relPos = relPos - Math.floor(relPos) + this._getIndexByPosition(Math.floor(relPos));
1603
+ if (Math.round(relPos) < 0)
1604
+ relPos = this.itemsLastIndex;
1605
+ else if (relPos <= 0)
1606
+ relPos = 0;
1607
+ else if (Math.round(relPos) > this.itemsLastIndex)
1608
+ relPos = 0;
1609
+ else if (relPos >= this.itemsLastIndex)
1610
+ relPos = this.itemsLastIndex;
1611
+
1612
+
1613
+ if (this.items.length > 1) {
1614
+ var sPos = (relPos / this.itemsLastIndex)* this.Scrollbar.dimensions.width;
1615
+ } else {
1616
+ var sPos = 0.5 * this.Scrollbar.dimensions.width;
1617
+ }
1618
+ this.Slider.style.left = sPos - this.Slider.center.x+ "px";
1619
+ this.Slider.style.top = this.Scrollbar.center.y - this.Slider.center.y +"px";
1620
+
1621
+ }.bind(this);
1622
+
1623
+ // make slider draggable
1624
+ var beforeDrag = function (event) {
1625
+ this.Scrollbar.clickLocked = true;
1626
+ }.bind(this);
1627
+
1628
+ var onDrag = function (event) {
1629
+ var e = event;
1630
+ if (event.touches) e = event.touches[0];
1631
+ var selectedIndex = this._checkIndex((e.clientX - this.Scrollbar.position.left) / this.Scrollbar.dimensions.width * this.itemsLastIndex);
1632
+ this._targetPosition = this._getPositionByIndex(selectedIndex);
1633
+ this.Slider.setPosition(selectedIndex);
1634
+ if (this.Position) this.Position.setLabel(selectedIndex);
1635
+ this._initStep(true, true);
1636
+ }.bind(this);
1637
+
1638
+ var afterDrag = function (event) {
1639
+ this._targetPosition = Math.round(this._targetPosition);
1640
+ this.conf.onMoveTo(this._getItemByPosition(this._targetPosition));
1641
+ this._initStep(true);
1642
+ }.bind(this);
1643
+
1644
+ this.Slider.makeDraggable(onDrag, beforeDrag, afterDrag);
1645
+ }
1646
+
1647
+
1648
+ // Position object
1649
+ if (this.Position) {
1650
+ this.Position.setLabel = function (index) {
1651
+ index = this._checkIndex(Math.round(index));
1652
+ if (this.items && this.items[index].label)
1653
+ this.Position.innerHTML = this.items[index].label.innerHTML;
1654
+ else
1655
+ this.Position.innerHTML = index + 1;
1656
+ }.bind(this);
1657
+ }
1658
+
1659
+
1660
+ this.globalCaption = this.Container.getChildrenByClassName('globalCaption')[0];
1661
+ this.loadIndicator = this.Container.getChildrenByClassName('loadIndicator')[0];
1662
+ },
1663
+
1664
+ /* ---------- init element sizes ---------- */
1665
+ _initSizes: function (x) {
1666
+ //if (this.Browser.Konqueror4 && x != true) {
1667
+ //var t = this;
1668
+ //window.setTimeout( function () { t._initSizes(true) }, 0);
1669
+ //return;
1670
+ //}
1671
+
1672
+ // sets this.maxHeight
1673
+ this._initMaxHeight();
1674
+
1675
+ var scrollbarHeight = this._initScrollbarSize();
1676
+
1677
+ // reduce maxHeit if container has a fixed height
1678
+ if (!this.conf.verticalFlow && this.Container.style.height && this.Container.style.height != "auto")
1679
+ this.maxHeight -= scrollbarHeight;
1680
+
1681
+ if (!this._activeItem) return;
1682
+
1683
+ var mFS = this._findBiggestItem();
1684
+
1685
+ var pF = this.Flow.findPos();
1686
+
1687
+ /* set height / width of flow */
1688
+ if (this.conf.verticalFlow) {
1689
+ this.Flow.style.width = mFS.width.width+"px";
1690
+ this.Flow.style.height =3* mFS.width.width * (1 + this.conf.reflectionHeight + this.conf.reflectionGap) + "px";
1691
+ } else {
1692
+ this.Flow.style.height = mFS.height.height +(mFS.height.top - pF.top)+"px";
1693
+ }
1694
+
1695
+ /* remove gap */
1696
+ var s = this.conf.verticalFlow ? mFS.width.width : mFS.height.height;
1697
+ var cH = s /(1 + this.conf.reflectionHeight + this.conf.reflectionGap);
1698
+ this.Flow.style.marginBottom = - (s - cH)+ "px";
1699
+
1700
+ this.Flow.dimensions = this.Flow.getDimensions();
1701
+
1702
+ if (!this.Browser.IE6) {
1703
+ if (this.conf.verticalFlow && this.Container.clientWidth < this.Flow.dimensions.width) {
1704
+ //this.Container.style.width = this.Flow.dimensions.width+"px";
1705
+ }
1706
+ else if (this.Container.clientHeight < this.Flow.dimensions.height) {
1707
+ this.Container.style.height = this.Flow.dimensions.height+"px";
1708
+ }
1709
+ }
1710
+
1711
+ if (this.conf.verticalFlow) {
1712
+ this.Flow.center = {x: this.Flow.dimensions.height/2, y:mFS.width.width/2};
1713
+ } else {
1714
+ this.Flow.center = {x: this.Flow.dimensions.width/2, y:mFS.height.height/2};
1715
+ }
1716
+
1717
+ },
1718
+
1719
+ /* -------------------------------------------------------------------------------- */
1720
+
1721
+ _initScrollbarSize: function () {
1722
+ var SB;
1723
+ var SL;
1724
+ var PO;
1725
+ if (SB = this.Scrollbar) {
1726
+ SB.setDimensions();
1727
+ var scrollbarHeight = SB.dimensions.height;
1728
+
1729
+ if (SL = this.Slider) {
1730
+ SL.setDimensions();
1731
+ scrollbarHeight += SL.dimensions.height;
1732
+
1733
+ if (PO = this.Position) {
1734
+
1735
+ var oldLabel = PO.innerHTML;
1736
+ var maxH = maxW = 0;
1737
+ PO.style.width = "auto";
1738
+
1739
+ if (this.items) {
1740
+ for (var i=0; i < this.items.length; i++) {
1741
+ var item = this.items[i];
1742
+ if (item.label) {
1743
+ PO.innerHTML = item.label.innerHTML;
1744
+ }
1745
+ else {
1746
+ PO.innerHTML = item.index;
1747
+ }
1748
+ var h = PO.clientHeight;
1749
+ var w = PO.clientWidth;
1750
+ if ( h > maxH) maxH = h;
1751
+ if ( w > maxW) maxW = w;
1752
+ }
1753
+ }
1754
+ else {
1755
+ PO.innerHTML = "&nbsp;";
1756
+ maxH = PO.clientHeight;
1757
+ maxW = PO.clientWidth;
1758
+ }
1759
+
1760
+ PO.innerHTML = oldLabel;
1761
+
1762
+ PO.setDimensions();
1763
+
1764
+ PO.style.width = maxW +"px";
1765
+ PO.style.left = (SL.dimensions.width - maxW)/2 + "px";
1766
+
1767
+ var extraSpace = PO.position.top - SL.position.top;
1768
+ if (extraSpace > 0) {
1769
+ extraSpace += -SB.dimensions.height + maxH;
1770
+ SB.style.marginBottom = extraSpace + "px";
1771
+ }
1772
+ else {
1773
+ extraSpace *= -1;
1774
+ SB.style.marginTop = extraSpace + "px";
1775
+ }
1776
+ scrollbarHeight += extraSpace;
1777
+ }
1778
+ }
1779
+ }
1780
+ else {
1781
+ scrollbarHeight = 0;
1782
+ }
1783
+
1784
+ return scrollbarHeight;
1785
+
1786
+ },
1787
+
1788
+ /* -------------------------------------------------------------------------------- */
1789
+
1790
+ _initMaxHeight: function () {
1791
+
1792
+ if (this.conf.verticalFlow) {
1793
+ var proportion = screen.width/screen.height;
1794
+ var Csd = this.Container.style.width;
1795
+ var Cdim = this.Container.clientWidth;
1796
+ var Fsd = this.Flow.style.width;
1797
+ var Fdim = this.Flow.clientWidth;
1798
+ var Fdim_o = this.Flow.clientHeight;
1799
+ } else {
1800
+ var proportion = screen.height/screen.width;
1801
+ var Csd = this.Container.style.height;
1802
+ var Cdim = this.Container.clientHeight;
1803
+ var Fsd = this.Flow.style.height;
1804
+ var Fdim = this.Flow.clientHeight;
1805
+ var Fdim_o = this.Flow.clientWidth;
1806
+ }
1807
+
1808
+ // set height of container and flow
1809
+ if (this.ContainerOldDim)
1810
+ Csd = this.ContainerOldDim;
1811
+ if (this.FlowOldDim)
1812
+ Fsd = this.FlowOldDim;
1813
+
1814
+ this.ContainerOldDim = "auto";
1815
+ this.FlowOldDim = "auto";
1816
+
1817
+
1818
+ /* calc maxHeight */
1819
+ if (this.conf.maxItemHeight <= 0) {
1820
+
1821
+ this.maxHeight = Fdim_o / 3 * proportion/1 * this.conf.scaleFactor; // divided by 3 because of left/center/right, yes it's a magic number
1822
+
1823
+ if (this.conf.verticalFlow && (this.maxHeight == 0 || this.maxHeight > Fdim)) {
1824
+ this.maxHeight = Fdim;
1825
+ }
1826
+
1827
+ if (Csd && Csd != "auto") {
1828
+ var gap = this.conf.verticalFlow ? 0 : this.conf.reflectionGap;
1829
+ var rH = this.conf.verticalFlow ? 0 : this.conf.reflectionHeight;
1830
+ this.maxHeight = Cdim/ (this.conf.scaleFactor* (1 + rH + gap));
1831
+ this.ContainerOldDim = Csd;
1832
+ }
1833
+ else if (Fsd && Fsd != "auto") {
1834
+ var gap = this.conf.verticalFlow ? 0 : this.conf.reflectionGap;
1835
+ this.maxHeight = Fdim / (this.conf.scaleFactor* (1 + this.conf.reflectionHeight + gap));
1836
+ this.FlowOldDim = Fsd;
1837
+ }
1838
+ }
1839
+ else {
1840
+ this.maxHeight = this.conf.maxItemHeight;
1841
+ }
1842
+ },
1843
+
1844
+ /* -------------------------------------------------------------------------------- */
1845
+
1846
+ _findBiggestItem: function () {
1847
+
1848
+ var currentItem = this._activeItem;
1849
+
1850
+ var itemP = currentItem.pre;
1851
+ var itemN = currentItem.next;
1852
+ var mFS = maxFlowSize = {
1853
+ width: { width: 0, left: 0, height:0, top: 0, item: null, rI: 0 },
1854
+ height: { width: 0, left: 0, height:0, top: 0, item: null, rI: 0 }
1855
+ }
1856
+
1857
+
1858
+ var checkMax = function (item, rI) {
1859
+ var el = item.element;
1860
+ el.style.display = "block";
1861
+ var p = el.findPos();
1862
+ var h = el.clientHeight;
1863
+ var w = el.clientWidth;
1864
+ if (h + p.top >= mFS.height.height + mFS.height.top) {
1865
+ mFS.height.height = h;
1866
+ mFS.height.top = p.top;
1867
+ mFS.height.item = item;
1868
+ mFS.height.rI = rI;
1869
+ }
1870
+ if (w + p.left >= mFS.width.width + mFS.width.left) {
1871
+ mFS.width.width = w;
1872
+ mFS.width.left = p.left;
1873
+ mFS.width.item = item;
1874
+ mFS.width.rI = rI;
1875
+ }
1876
+ el.style.display = "none";
1877
+ }
1878
+
1879
+ var ocp = this._currentPosition;
1880
+ this._currentPosition = this.conf.visibleItems+1;
1881
+
1882
+ // find the position with highest y-value
1883
+ for (var i=-this.conf.visibleItems; i <= this.conf.visibleItems; i++) {
1884
+ currentItem.element.style.display = "none";
1885
+ this._positionItem(currentItem, i);
1886
+ checkMax(currentItem, i);
1887
+ }
1888
+
1889
+ // find the biggest item
1890
+ var index = mFS.height.rI;
1891
+ for (var i=0; i < this.items.length; i++) {
1892
+ var item = this.items[i];
1893
+ item.element.style.display = "none";
1894
+ this._positionItem(item, index);
1895
+ checkMax(item, index);
1896
+ }
1897
+
1898
+ this._currentPosition = ocp;
1899
+
1900
+ return mFS
1901
+ },
1902
+
1903
+
1904
+
1905
+ /*
1906
+ * ==================== Key strok ====================
1907
+ */
1908
+
1909
+ /*
1910
+ * handles keystroke events
1911
+ */
1912
+ _keyStroke: function(event) {
1913
+ if(!event) var event = window.event;
1914
+
1915
+ if (event.which) {
1916
+ var keyCode = event.which;
1917
+ } else if (event.keyCode) {
1918
+ var keyCode = event.keyCode;
1919
+ }
1920
+
1921
+ if (this.conf.keys[keyCode]) {
1922
+ this.conf.keys[keyCode].bind(this)();
1923
+ return Event.stop(event);
1924
+ }
1925
+ else {
1926
+ return true;
1927
+ }
1928
+ },
1929
+
1930
+ /*
1931
+ * ==================== mouse wheel ====================
1932
+ * Event handler for mouse wheel event
1933
+ * http://adomas.org/javascript-mouse-wheel/
1934
+ */
1935
+
1936
+ _wheel: function (event) {
1937
+ if (!event) var event = window.event; // MS
1938
+
1939
+ var delta = 0;
1940
+ if (event.wheelDelta) {
1941
+ delta = event.wheelDelta/120;
1942
+ } else if (event.detail) {
1943
+ delta = -event.detail/3;
1944
+ }
1945
+
1946
+ if (delta) {
1947
+ var target = this._targetPosition ;
1948
+ if (delta < 0 ) {
1949
+ target += (1 * this.conf.scrollWheelSpeed);
1950
+ } else {
1951
+ target -= (1 * this.conf.scrollWheelSpeed);
1952
+ }
1953
+ this.moveToPosition(Math.round(target));
1954
+ }
1955
+
1956
+ return Event.stop(event);
1957
+ },
1958
+
1959
+
1960
+ /*
1961
+ * ==================== set global Caption ====================
1962
+ */
1963
+ _setGlobalCaption: function () {
1964
+ if (this.globalCaption) {
1965
+ this.globalCaption.innerHTML = '';
1966
+ if(this._activeItem && this._activeItem.caption)
1967
+ this.globalCaption.appendChild(this._activeItem.caption.cloneNode(true));
1968
+ }
1969
+ },
1970
+
1971
+ /*
1972
+ * ==================== move items ====================
1973
+ */
1974
+
1975
+ /*
1976
+ * intend to make a step
1977
+ */
1978
+ _initStep: function (holdSlider, holdPos) {
1979
+ if (this.Slider) {
1980
+ if(holdSlider) {
1981
+ this.Slider.locked = true;
1982
+ } else {
1983
+ this.Slider.locked = false;
1984
+ }
1985
+ }
1986
+ this._holdPos = holdPos == true ? true : false;
1987
+ if (!this._stepLock) {
1988
+ this._stepLock = true;
1989
+ this._step();
1990
+ }
1991
+ },
1992
+
1993
+ /*
1994
+ * make a step
1995
+ */
1996
+ _step: function () {
1997
+
1998
+ var diff = this._targetPosition - this._currentPosition;
1999
+ var absDiff = Math.abs(diff);
2000
+ if ( absDiff > 0.001) { // till activeItem is nearly at position 0
2001
+
2002
+ this._currentPosition += this.conf.flowSpeedFactor * this.conf.calcStepWidth(diff, absDiff, this.items.length, this.conf.visibleItems);
2003
+
2004
+ var AI = this.items[(this._getIndexByPosition(this._currentPosition))];
2005
+
2006
+ if (AI && AI != this._activeItem) {
2007
+ if (this._activeItem) this._activeItem.makeInactive();
2008
+ this._activeItem = AI;
2009
+ this._activeItem.makeActive();
2010
+ this._setCaptionLabel(this._activeItem.index);
2011
+ if (Math.abs(this._targetPosition - this._currentPosition) <= 0.5 ) this.conf.onReachTarget(this._activeItem);
2012
+ }
2013
+
2014
+ this._positionItems();
2015
+
2016
+ var st = this._step.bind(this);
2017
+ window.setTimeout(st,this._millisecondsPerStep);
2018
+
2019
+ } else if (!this._holdPos) {
2020
+ if (this.Slider) this.Slider.locked = false;
2021
+ this._currentPosition = Math.round(this._currentPosition);
2022
+ if(this.Position && !this.Slider.locked && this._activeItem) {
2023
+ this._setCaptionLabel(this._activeItem.index);
2024
+ }
2025
+ this._positionItems();
2026
+ this._stepLock = false;
2027
+ } else {
2028
+ this._stepLock = false;
2029
+ }
2030
+
2031
+ if (this.Slider && !this.Slider.locked) {
2032
+ this.Slider.setPosition(this._currentPosition);
2033
+ }
2034
+ },
2035
+
2036
+
2037
+
2038
+ /* ------------------------------------------------------------------------------------------------------ */
2039
+
2040
+ /*
2041
+ * position items
2042
+ */
2043
+ _positionItems: function () {
2044
+
2045
+ if (this._lastStart) {
2046
+ var item = this._lastStart;
2047
+ while (item) {
2048
+ item.element.style.display="none";
2049
+ item = item.next;
2050
+ if (item == this._lastStart) break;
2051
+ if (item && item.pre == this._lastEnd) break;
2052
+ }
2053
+ }
2054
+ else {
2055
+ this._lastStart = this._activeItem;
2056
+ }
2057
+
2058
+ if (!this._activeItem) return;
2059
+ var currentItem = this._activeItem;
2060
+ var itemP = currentItem.pre;
2061
+ var itemN = currentItem.next;
2062
+
2063
+ this._positionItem(currentItem, 0);
2064
+ for (var i=1; i <= this.conf.visibleItems && 2*i < this.items.length ; i++) {
2065
+ if (itemP) {
2066
+ this._positionItem(itemP, -i);
2067
+ this._lastStart = itemP;
2068
+ itemP = itemP.pre;
2069
+ }
2070
+ if (itemN) {
2071
+ this._positionItem(itemN, i);
2072
+ this._lastEnd = itemN;
2073
+ itemN = itemN.next;
2074
+ }
2075
+ }
2076
+
2077
+ },
2078
+
2079
+ _positionItem: function (item, relativeIndex) {
2080
+
2081
+ var conf = this.conf;
2082
+ var vF = conf.verticalFlow;
2083
+
2084
+ var els = item.element.style;
2085
+ //els.display =" none";
2086
+ //if (els.display != "none") return;
2087
+
2088
+ /* Index and position relative to activeItem */
2089
+ var p = item.position = this._currentPosition + relativeIndex;
2090
+ var relativePosition = item.relativePosition = Math.round(p) - this._currentPosition;
2091
+ var relativePositionNormed = item.relativePositionNormed = conf.visibleItems > 0 ? relativePosition/conf.visibleItems : 0;
2092
+ var side = relativePosition < 0 ? -1 : 1;
2093
+ side *= relativePosition == 0 ? 0 : 1;
2094
+ item.side = side;
2095
+
2096
+ var size = conf.calcSize(item);
2097
+ size.height = Math.max(size.height, 0);
2098
+ size.width = Math.max(size.width, 0);
2099
+ if (item.content.origProportion) size = this._scaleImageSize(item, size);
2100
+ item.size = size;
2101
+
2102
+ var coords = item.coordinates = conf.calcCoordinates (item);
2103
+ var relItemPos = item.relativeItemPosition = conf.calcRelativeItemPosition(item);
2104
+ var zIndex = item.zIndex = conf.calcZIndex (item);
2105
+ var fontSize = item.fontSize = conf.calcFontSize (item);
2106
+ var opacity = item.opacity = conf.calcOpacity(item);
2107
+
2108
+ size.height *= this.maxHeight;
2109
+ size.width *= this.maxHeight;
2110
+
2111
+ /* set position */
2112
+ var sA = vF ? size.height : size.width;
2113
+ var sB = vF ? size.width : size.height;
2114
+ var pX = this.Flow.center.x * ( 1 + coords.x ) + (relItemPos.x - 1) * sA/2;
2115
+ var pY = this.maxHeight/2 * ( 1 + coords.y ) + (relItemPos.y - 1 )* sB/2;
2116
+ els.left = (vF ? pY : pX)+"px";
2117
+ els.top = (vF ? pX : pY)+"px";
2118
+
2119
+ this._setItemSize(item, size);
2120
+
2121
+ /* set opacity */
2122
+ if (conf.endOpacity != 1) {
2123
+ this._setItemOpacity(item);
2124
+ }
2125
+
2126
+ /* set font size */
2127
+ if (!this.Browser.IE) els.fontSize = (fontSize * 100) +"%";
2128
+
2129
+ /* set z-index */
2130
+ els.zIndex = 32768 + Math.round(zIndex * this.items.length); // just for FF
2131
+
2132
+ conf.onDrawItem(item);
2133
+
2134
+ els.visibility = "visible";
2135
+ els.display = "block";
2136
+ },
2137
+
2138
+ _scaleImageSize: function (item, size, max) {
2139
+ var sFL = this.conf.scaleFactorLandscape;
2140
+ var sFP = this.conf.scaleFactorPortrait;
2141
+ var vF = this.conf.verticalFlow;
2142
+ var prop = item.content.origProportion;
2143
+ var width = size.width;
2144
+ var height = size.height;
2145
+ var c = item.content;
2146
+
2147
+ if (vF) {
2148
+ if (prop <= 1) {
2149
+ if (sFL != "max" && sFL != 1) {
2150
+ height *= sFL;
2151
+ width = Math.min(height * prop, max ? max : 1 );
2152
+ }
2153
+ height = width / prop;
2154
+ }
2155
+ else if (prop > 1) {
2156
+ if (sFP == "max") {
2157
+ height = max ? max : 1;
2158
+ }
2159
+ else if (sFP != 1) {
2160
+ width *= sFP;
2161
+ height = Math.min(width/prop, max ? max : 1)
2162
+ }
2163
+ else {
2164
+ height = width / prop;
2165
+ }
2166
+ width = height * prop;
2167
+ }
2168
+ }
2169
+ else {
2170
+ if (prop > 1) {
2171
+ if (sFL != "max" && sFL != 1) {
2172
+ width *= sFL;
2173
+ height = Math.min(width / prop, max ? max : 1);
2174
+ }
2175
+ width = height * prop;
2176
+ }
2177
+ else if (prop <= 1) {
2178
+ if (sFP == "max") {
2179
+ width = max ? max : 1;
2180
+ }
2181
+ else if (sFP != 1) {
2182
+ height *= sFP;
2183
+ width = Math.min(height*prop, max ? max : 1);
2184
+ }
2185
+ else {
2186
+ width = height * prop;
2187
+ }
2188
+ height = width / prop;
2189
+ }
2190
+ }
2191
+
2192
+ height = isNaN(height) ? 0 : height;
2193
+ width = isNaN(width) ? 0 : width;
2194
+
2195
+ if (!max && this.conf.fixItemSize) {
2196
+
2197
+ var propS = size.width / size.height;
2198
+
2199
+ var max = Math.max(size.width, size.height);
2200
+ var s = this._scaleImageSize(item, {width: max, height: max}, max);
2201
+
2202
+ if (propS < 1) {
2203
+ height = s.height/size.height;
2204
+ width = height * prop / propS;
2205
+ }
2206
+ else {
2207
+ width = s.width/size.width;
2208
+ height = width / prop * propS;
2209
+ }
2210
+
2211
+ var h = height * 100;
2212
+ var w = width * 100;
2213
+ var mL= (1 - width)/2 * 100;
2214
+ var mT= ( 1 - height ) / propS * 100 * (vF ? 0.5 : 1 );
2215
+ c.style.height = h+"%";
2216
+ if (item.reflection) item.reflection.style.height = h*this.conf.reflectionHeight+"%";
2217
+ c.style.width = w+"%";
2218
+ if (item.reflection) item.reflection.style.width = w+"%";
2219
+ c.style.marginLeft = mL+"%";
2220
+ if (item.reflection) item.reflection.style.marginLeft = mL+"%";
2221
+ c.style.marginTop = mT+"%";
2222
+
2223
+ item.element.style.overflow = "hidden";
2224
+
2225
+ return size;
2226
+ }
2227
+ else {
2228
+ return {width: width, height: height};
2229
+ }
2230
+
2231
+ },
2232
+
2233
+ _setItemSize: (function () {
2234
+ if (ContentFlowGlobal.Browser.IE) {
2235
+ var _setItemSize = function (item, size) {
2236
+ if (!this.conf.fixItemSize) {
2237
+ item.content.style.height = size.height+"px";
2238
+ }
2239
+ else if (ContentFlowGlobal.Browser.IE6) {
2240
+ var h = parseInt(item.content.style.height)/100;
2241
+ item.content.style.height = size.height*h+"px";
2242
+ var mT = parseInt(item.content.style.marginTop)/100;
2243
+ item.content.style.marginTop = size.height*mT+"px";
2244
+ }
2245
+ if (item.reflection) {
2246
+ var h = parseInt(item.content.style.height);
2247
+ item.reflection.style.height = h*this.conf.reflectionHeight+"px";
2248
+ item.reflection.style.marginTop = h * this.conf.reflectionGap + "px";
2249
+ }
2250
+ item.element.style.width = size.width +"px";
2251
+ item.element.style.height = size.height*(1+this.conf.reflectionHeight+this.conf.reflectionGap)+"px";
2252
+ }
2253
+ }
2254
+ else {
2255
+ var _setItemSize = function (item, size) {
2256
+ if (item.reflection) {
2257
+ item.element.style.height = size.height*(1+this.conf.reflectionHeight + this.conf.reflectionGap) +"px";
2258
+ item.reflection.style.marginTop = size.height * this.conf.reflectionGap + "px";
2259
+ }
2260
+ else if (this._reflectionWithinImage) {
2261
+ item.element.style.height = size.height*(1+this.conf.reflectionHeight + this.conf.reflectionGap) +"px";
2262
+ }
2263
+ else {
2264
+ item.element.style.height = size.height +"px";
2265
+ }
2266
+ item.element.style.width = size.width +"px";
2267
+ }
2268
+ }
2269
+ return _setItemSize;
2270
+
2271
+ })(),
2272
+
2273
+ _setItemOpacity: (function () {
2274
+ if (ContentFlowGlobal.Browser.IE6) {
2275
+ var _setItemOpacity = function (item) {
2276
+ if (item.content.origSrc && item.content.origSrc.match(/\.png$/) ) {
2277
+ var s = item.content.src;
2278
+ item.content.src = item.content.origSrc;
2279
+ item.content.style.filter = item.content.filterString+" progid:DXImageTransform.Microsoft.BasicImage(opacity="+item.opacity+")";
2280
+ item.content.src = s;
2281
+ }
2282
+ else {
2283
+ item.content.style.filter = "progid:DXImageTransform.Microsoft.BasicImage(opacity="+item.opacity+")";
2284
+ }
2285
+ if (item.reflection) item.reflection.style.filter = item.reflection.filterString+"progid:DXImageTransform.Microsoft.BasicImage(opacity="+item.opacity+")";
2286
+ }
2287
+ }
2288
+ else if (ContentFlowGlobal.Browser.IE) {
2289
+ var _setItemOpacity = function (item) { item.element.style.filter = "progid:DXImageTransform.Microsoft.BasicImage(opacity="+item.opacity+")"; }
2290
+ }
2291
+ else {
2292
+ var _setItemOpacity = function (item) { item.element.style.opacity = item.opacity; }
2293
+ }
2294
+ return _setItemOpacity;
2295
+ })()
2296
+
2297
+
2298
+ };
2299
+
2300
+
2301
+ /* ==================== extendig javascript/DOM objects ==================== */
2302
+
2303
+ /*
2304
+ * adds bind method to Function class
2305
+ * http://www.digital-web.com/articles/scope_in_javascript/
2306
+ */
2307
+
2308
+ if (!Function.bind) {
2309
+ Function.prototype.bind = function(obj) {
2310
+ var method = this;
2311
+ return function () {
2312
+ return method.apply(obj, arguments);
2313
+ };
2314
+ };
2315
+ }
2316
+
2317
+
2318
+ /*
2319
+ * extending Math object
2320
+ */
2321
+ if (!Math.erf2) {
2322
+ // error function (http://en.wikipedia.org/wiki/Error_function), implemented as erf(x)^2
2323
+ Math.erf2 = function (x) {
2324
+ var a = - (8*(Math.PI -3)/(3*Math.PI*(Math.PI -4)));
2325
+ var x2 = x*x;
2326
+ var f = 1 - Math.pow(Math.E, -x2 * (4/Math.PI + a*x2)/(1+a*x2));
2327
+ return f;
2328
+ };
2329
+ }
2330
+
2331
+ if (!Math._2PI05) {
2332
+ Math._2PI05 = Math.sqrt(2*Math.PI);
2333
+ }
2334
+
2335
+ if (!Math.normDist) {
2336
+ // normal distribution
2337
+ Math.normDist = function (x, sig, mu) {
2338
+ if (!sig) var sig = 1;
2339
+ if (!mu) var mu = 0;
2340
+ if (!x) var x = - mu;
2341
+ return 1/(sig * Math._2PI05) * Math.pow(Math.E, - (x-mu)*(x-mu)/(2*sig*sig) );
2342
+ };
2343
+ }
2344
+
2345
+ if (!Math.normedNormDist) {
2346
+ Math.normedNormDist = function (x, sig, mu) {
2347
+ return this.normDist(x, sig, mu)/this.normDist(mu, sig, mu);
2348
+ };
2349
+ }
2350
+
2351
+ if (!Math.exp) {
2352
+ Math.exp = function(x) {
2353
+ return Math.pow(Math.E, x);
2354
+ };
2355
+ }
2356
+
2357
+ if (!Math.ln) {
2358
+ Math.ln = Math.log;
2359
+ }
2360
+
2361
+ if (!Math.log2) {
2362
+ Math.log2 = function (x) {
2363
+ return Math.log(x)/Math.LN2;
2364
+ };
2365
+ }
2366
+
2367
+ if (!Math.log10) {
2368
+ Math.log10 = function (x) {
2369
+ return Math.log(x)/Math.LN10;
2370
+ };
2371
+ }
2372
+
2373
+ if (!Math.logerithm) {
2374
+ Math.logerithm = function (x, b) {
2375
+ if (!b || b == Math.E)
2376
+ return Math.log(x);
2377
+ else if (b == 2)
2378
+ return Math.log2(x);
2379
+ else if (b == 10)
2380
+ return Math.log10(x);
2381
+ else
2382
+ return Math.log(x)/Math.log(b);
2383
+ };
2384
+ }
2385
+
2386
+
2387
+ /*
2388
+ * extending Event object
2389
+ */
2390
+ if (!Event) var Event = {};
2391
+
2392
+ if (!Event.stop) {
2393
+ Event.stop = function (event) {
2394
+ event.cancelBubble = true;
2395
+ if (event.preventDefault) event.preventDefault();
2396
+ if (event.stopPropagation) event.stopPropagation();
2397
+ return false;
2398
+ };
2399
+ }
2400
+
2401
+ /*
2402
+ * extending Element object
2403
+ */
2404
+ if (document.all && !window.opera) {
2405
+ window.$CF = function (el) {
2406
+ if (typeof el == "string") {
2407
+ return window.$CF(document.getElementById(el));
2408
+ }
2409
+ else {
2410
+ if (CFElement.prototype.extend && el && !el.extend) CFElement.prototype.extend(el);
2411
+ }
2412
+ return el;
2413
+ };
2414
+ } else {
2415
+ window.$CF = function (el) {
2416
+ return el;
2417
+ };
2418
+ }
2419
+
2420
+ if (!window.HTMLElement) {
2421
+ CFElement = {};
2422
+ CFElement.prototype = {};
2423
+ CFElement.prototype.extend = function (el) {
2424
+ for (var method in this) {
2425
+ if (!el[method]) el[method] = this[method];
2426
+ }
2427
+ };
2428
+ }
2429
+ else {
2430
+ CFElement = window.HTMLElement;
2431
+ }
2432
+
2433
+
2434
+ /*
2435
+ * Thanks to Peter-Paul Koch
2436
+ * http://www.quirksmode.org/js/findpos.html
2437
+ */
2438
+ if (!CFElement.findPos) {
2439
+ CFElement.prototype.findPos = function() {
2440
+ var obj = this;
2441
+ var curleft = curtop = 0;
2442
+ try {
2443
+ if (obj.offsetParent) {
2444
+ curleft = obj.offsetLeft;
2445
+ curtop = obj.offsetTop;
2446
+ while (obj = obj.offsetParent) {
2447
+ curleft += obj.offsetLeft;
2448
+ curtop += obj.offsetTop;
2449
+ }
2450
+ }
2451
+ }
2452
+ catch (ex) {}
2453
+ return {left:curleft, top:curtop};
2454
+ };
2455
+ }
2456
+
2457
+ if (!CFElement.getDimensions) {
2458
+ CFElement.prototype.getDimensions = function() {
2459
+ return {width: this.clientWidth, height: this.clientHeight};
2460
+ };
2461
+ }
2462
+
2463
+ /*
2464
+ * checks if an element has the class className
2465
+ */
2466
+ if (!CFElement.hasClassName) {
2467
+ CFElement.prototype.hasClassName = function(className) {
2468
+ return (new RegExp('\\b'+className+'\\b').test(this.className));
2469
+ };
2470
+ }
2471
+
2472
+ /*
2473
+ * adds the class className to the element
2474
+ */
2475
+ if (!CFElement.addClassName) {
2476
+ CFElement.prototype.addClassName = function(className) {
2477
+ if(!this.hasClassName(className)) {
2478
+ this.className += (this.className ? ' ':'') + className ;
2479
+ }
2480
+ };
2481
+ }
2482
+
2483
+ /*
2484
+ * removes the class className from the element el
2485
+ */
2486
+ if (!CFElement.removeClassName) {
2487
+ CFElement.prototype.removeClassName = function(className) {
2488
+ this.className = this.className.replace(new RegExp('\\b'+className+'\\b'), '').replace(/\s\s/g,' ');
2489
+ };
2490
+ }
2491
+
2492
+ /*
2493
+ * removes or adds the class className from/to the element el
2494
+ * depending if the element has the class className or not.
2495
+ */
2496
+ if (!CFElement.toggleClassName) {
2497
+ CFElement.prototype.toggleClassName = function(className) {
2498
+ if(this.hasClassName(className)) {
2499
+ this.removeClassName(className);
2500
+ } else {
2501
+ this.addClassName(className);
2502
+ }
2503
+ };
2504
+ }
2505
+
2506
+ /*
2507
+ * returns all children of element el, which have the class className
2508
+ */
2509
+ if (!CFElement.getChildrenByClassName) {
2510
+ CFElement.prototype.getChildrenByClassName = function(className) {
2511
+ var children = new Array();
2512
+ for (var i=0; i < this.childNodes.length; i++) {
2513
+ var c = this.childNodes[i];
2514
+ if (c.nodeType == 1 && $CF(c).hasClassName(className)) {
2515
+ children.push(c);
2516
+ }
2517
+ }
2518
+ return children;
2519
+ };
2520
+ }
2521
+
2522
+ /*
2523
+ * Browser independent event handling method.
2524
+ * adds the eventListener eventName to element el and attaches the function method to it.
2525
+ */
2526
+ if (!CFElement.addEvent) {
2527
+ CFElement.prototype.addEvent = function(eventName, method, capture) {
2528
+ if (this.addEventListener)
2529
+ this.addEventListener(eventName, method, capture);
2530
+ else
2531
+ this.attachEvent('on'+eventName, method);
2532
+ };
2533
+ }
2534
+
2535
+ /*
2536
+ * Browser independent event handling method.
2537
+ * removes the eventListener eventName with the attached function method from element el.
2538
+ */
2539
+ if (!CFElement.removeEvent) {
2540
+ CFElement.prototype.removeEvent = function(eventName, method, capture) {
2541
+ if (this.removeEventListener)
2542
+ this.removeEventListener(eventName, method, capture);
2543
+ else
2544
+ this.detachEvent('on'+eventName, method);
2545
+ };
2546
+ }
2547
+
2548
+ /*
2549
+ * Browser independent event handling method.
2550
+ * adds the eventListener eventName to element el and attaches the function method to it.
2551
+ */
2552
+ if (!window.addEvent) {
2553
+ window.addEvent = function(eventName, method, capture) {
2554
+ if (this.addEventListener) {
2555
+ this.addEventListener(eventName, method, capture);
2556
+ } else {
2557
+ if (eventName != 'load' && eventName != 'resize')
2558
+ document.attachEvent('on'+eventName, method);
2559
+ else
2560
+ this.attachEvent('on'+eventName, method);
2561
+ }
2562
+ };
2563
+ }
2564
+
2565
+ /*
2566
+ * Browser independent event handling method.
2567
+ * removes the eventListener eventName with the attached function method from element el.
2568
+ */
2569
+ if (!window.removeEvent) {
2570
+ window.removeEvent = function(eventName, method, capture) {
2571
+ if (this.removeEventListener) {
2572
+ this.removeEventListener(eventName, method, capture);
2573
+ } else {
2574
+ if (eventName != 'load' && eventName != 'resize')
2575
+ document.detachEvent('on'+eventName, method);
2576
+ else
2577
+ this.detachEvent('on'+eventName, method);
2578
+ }
2579
+ };
2580
+ }
2581
+
2582
+ /* ==================== start it all up ==================== */
2583
+ ContentFlowGlobal.init();
2584
+