/*

    This file is part of JonDesign's SmoothGallery v2.0.



    JonDesign's SmoothGallery is free software; you can redistribute it and/or modify

    it under the terms of the GNU General Public License as published by

    the Free Software Foundation; either version 3 of the License, or

    (at your option) any later version.



    JonDesign's SmoothGallery is distributed in the hope that it will be useful,

    but WITHOUT ANY WARRANTY; without even the implied warranty of

    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the

    GNU General Public License for more details.



    You should have received a copy of the GNU General Public License

    along with JonDesign's SmoothGallery; if not, write to the Free Software

    Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA



    Main Developer: Jonathan Schemoul (JonDesign: http://www.jondesign.net/)

    Contributed code by:

    - Christian Ehret (bugfix)

        - Nitrix (bugfix)

        - Valerio from Mad4Milk for his great help with the carousel scrolling and many other things.

        - Archie Cowan for helping me find a bugfix on carousel inner width problem.

        - Tomocchino from #mootools for the preloader class

        Many thanks to:

        - The mootools team for the great mootools lib, and it's help and support throughout the project.

*/



// declaring the class

var gallery = {

        initialize: function(element, options) {

                this.setOptions({

                        showArrows: true,

                        showCarousel: true,

                        showInfopane: true,

                        embedLinks: true,

                        fadeDuration: 500,

                        timed: false,

                        delay: 9000,

                        preloader: true,

                        preloaderImage: true,

                        preloaderErrorImage: true,

                        /* Data retrieval */

                        manualData: [],

                        populateFrom: false,

                        populateData: true,

                        destroyAfterPopulate: true,

                        elementSelector: "div.imageElement",

                        titleSelector: "h2",

                        subtitleSelector: "p",

                        linkSelector: "a.open",

                        imageSelector: "img.full",

                        thumbnailSelector: "img.thumbnail",

                        defaultTransition: "fade",

                        /* InfoPane options */

                        slideInfoZoneOpacity: 0.7,

                        slideInfoZoneSlide: true,

                        /* Carousel options */

                        carouselMinimizedOpacity: 0.4,

                        carouselMinimizedHeight: 20,

                        carouselMaximizedOpacity: 0.9,

                        thumbHeight: 75,

                        thumbWidth: 100,

                        thumbSpacing: 10,

                        thumbIdleOpacity: 0.6,

                        textShowCarousel: 'Acquisitions',

                        showCarouselLabel: true,

                        thumbCloseCarousel: true,

                        useThumbGenerator: false,

                        thumbGenerator: 'resizer.php',

                        useExternalCarousel: false,

                        carouselElement: false,

                        carouselHorizontal: true,

                        activateCarouselScroller: true,

                        carouselPreloader: true,

                        textPreloadingCarousel: 'Loading...',

                        /* CSS Classes */

                        baseClass: 'jdGallery',

                        withArrowsClass: 'withArrows',

                        /* Plugins: HistoryManager */

                        useHistoryManager: false,

                        customHistoryKey: false

                }, options);

                this.fireEvent('onInit');

                this.currentIter = 0;

                this.lastIter = 0;

                this.maxIter = 0;

                this.galleryElement = element;

                this.galleryData = this.options.manualData;

                this.galleryInit = 1;

                this.galleryElements = Array();

                this.thumbnailElements = Array();

                this.galleryElement.addClass(this.options.baseClass);



                this.populateFrom = element;

                if (this.options.populateFrom)

                        this.populateFrom = this.options.populateFrom;

                if (this.options.populateData)

                        this.populateData();

                element.style.display="block";



                if (this.options.useHistoryManager)

                        this.initHistory();



                if (this.options.embedLinks)

                {

                        this.currentLink = new Element('a').addClass('open').setProperties({

                                href: '#',

                                title: ''

                        }).injectInside(element);

                        if ((!this.options.showArrows) && (!this.options.showCarousel))

                                this.galleryElement = element = this.currentLink;

                        else

                                this.currentLink.setStyle('display', 'none');

                }



                this.constructElements();

                if ((this.galleryData.length>1)&&(this.options.showArrows))

                {

                        var leftArrow = new Element('a').addClass('left').addEvent(

                                'click',

                                this.prevItem.bind(this)

                        ).injectInside(element);

                        var rightArrow = new Element('a').addClass('right').addEvent(

                                'click',

                                this.nextItem.bind(this)

                        ).injectInside(element);

                        this.galleryElement.addClass(this.options.withArrowsClass);

                }

                this.loadingElement = new Element('div').addClass('loadingElement').injectInside(element);

                if (this.options.showInfopane) this.initInfoSlideshow();

                if (this.options.showCarousel) this.initCarousel();

                this.doSlideShow(1);

        },

        populateData: function() {

                currentArrayPlace = this.galleryData.length;

                options = this.options;

                var data = $A(this.galleryData);

                data.extend(this.populateGallery(this.populateFrom, currentArrayPlace));

                this.galleryData = data;

                this.fireEvent('onPopulated');

        },

        populateGallery: function(element, startNumber) {

                var data = [];

                options = this.options;

                currentArrayPlace = startNumber;

                element.getElements(options.elementSelector).each(function(el) {

                        elementDict = {

                                image: el.getElement(options.imageSelector).getProperty('src'),

                                number: currentArrayPlace,

                                transition: this.options.defaultTransition

                        };

                        elementDict.extend = $extend;

                        if ((options.showInfopane) | (options.showCarousel))

                                elementDict.extend({

                                        title: el.getElement(options.titleSelector).innerHTML,

                                        description: el.getElement(options.subtitleSelector).innerHTML

                                });

                        if (options.embedLinks)

                                elementDict.extend({

                                        link: el.getElement(options.linkSelector).href||false,

                                        linkTitle: el.getElement(options.linkSelector).title||false,

                                        linkTarget: el.getElement(options.linkSelector).getProperty('target')||false

                                });

                        if ((!options.useThumbGenerator) && (options.showCarousel))

                                elementDict.extend({

                                        thumbnail: el.getElement(options.thumbnailSelector).getProperty('src')

                                });

                        else if (options.useThumbGenerator)

                                elementDict.extend({

                                        thumbnail: options.thumbGenerator + '?imgfile=' + elementDict.image + '&max_width=' + options.thumbWidth + '&max_height=' + options.thumbHeight

                                });



                        data.extend([elementDict]);

                        currentArrayPlace++;

                        if (this.options.destroyAfterPopulate)

                                el.remove();

                });

                return data;

        },

        constructElements: function() {

                el = this.galleryElement;

                this.maxIter = this.galleryData.length;

                var currentImg;

                for(i=0;i<this.galleryData.length;i++)

                {

                        var currentImg = new Fx.Styles(

                                new Element('div').addClass('slideElement').setStyles({

                                        'position':'absolute',

                                        'left':'0px',

                                        'right':'0px',

                                        'margin':'0px',

                                        'padding':'0px',

                                        'backgroundPosition':"center center",

                                        'opacity':'0'

                                }).injectInside(el),

                                'opacity',

                                {duration: this.options.fadeDuration}

                        );

                        if (this.options.preloader)

                        {

                                currentImg.source = this.galleryData[i].image;

                                currentImg.loaded = false;

                                currentImg.load = function(imageStyle) {

                                        if (!imageStyle.loaded)        {

                                                new Asset.image(imageStyle.source, {

                                            'onload'  : function(img){

                                                                                                        img.element.setStyle(

                                                                                                        'backgroundImage',

                                                                                                        "url('" + img.source + "')")

                                                                                                        img.loaded = true;

                                                                                                }.bind(this, imageStyle)

                                                });

                                        }

                                }.pass(currentImg, this);

                        } else {

                                currentImg.element.setStyle('backgroundImage',

                                                                        "url('" + this.galleryData[i].image + "')");

                        }

                        this.galleryElements[parseInt(i)] = currentImg;

                }

        },

        destroySlideShow: function(element) {

                var myClassName = element.className;

                var newElement = new Element('div').addClass('myClassName');

                element.parentNode.replaceChild(newElement, element);

        },

        startSlideShow: function() {

                this.fireEvent('onStart');

                this.loadingElement.style.display = "none";

                this.lastIter = this.maxIter - 1;

                this.currentIter = 0;

                this.galleryInit = 0;

                this.galleryElements[parseInt(this.currentIter)].set({opacity: 1});

                if (this.options.showInfopane)

                        this.showInfoSlideShow.delay(1000, this);

                var textShowCarousel = formatString(this.options.textShowCarousel, this.currentIter+1, this.maxIter);

                if (this.options.showCarousel&&(!this.options.carouselPreloader))

                        this.carouselBtn.setHTML(textShowCarousel).setProperty('title', textShowCarousel);

                this.prepareTimer();

                if (this.options.embedLinks)

                        this.makeLink(this.currentIter);

        },

        nextItem: function() {

                this.fireEvent('onNextCalled');

                this.nextIter = this.currentIter+1;

                if (this.nextIter >= this.maxIter)

                        this.nextIter = 0;

                this.galleryInit = 0;

                this.goTo(this.nextIter);

        },

        prevItem: function() {

                this.fireEvent('onPreviousCalled');

                this.nextIter = this.currentIter-1;

                if (this.nextIter <= -1)

                        this.nextIter = this.maxIter - 1;

                this.galleryInit = 0;

                this.goTo(this.nextIter);

        },

        goTo: function(num) {

                this.clearTimer();

                if(this.options.preloader)

                {

                        this.galleryElements[num].load();

                        if (num==0)

                                this.galleryElements[this.maxIter - 1].load();

                        else

                                this.galleryElements[num - 1].load();

                        if (num==(this.maxIter - 1))

                                this.galleryElements[0].load();

                        else

                                this.galleryElements[num + 1].load();



                }

                if (this.options.embedLinks)

                        this.clearLink();

                if (this.options.showInfopane)

                {

                        this.slideInfoZone.clearChain();

                        this.hideInfoSlideShow().chain(this.changeItem.pass(num, this));

                } else

                        this.currentChangeDelay = this.changeItem.delay(500, this, num);

                if (this.options.embedLinks)

                        this.makeLink(num);

                this.prepareTimer();

                /*if (this.options.showCarousel)

                        this.clearThumbnailsHighlights();*/

        },

        changeItem: function(num) {

                this.fireEvent('onStartChanging');

                this.galleryInit = 0;

                if (this.currentIter != num)

                {

                        for(i=0;i<this.maxIter;i++)

                        {

                                if ((i != this.currentIter)) this.galleryElements[i].set({opacity: 0});

                        }

                        gallery.Transitions[this.galleryData[num].transition].pass([

                                this.galleryElements[this.currentIter],

                                this.galleryElements[num],

                                this.currentIter,

                                num], this)();

                        this.currentIter = num;

                }

                var textShowCarousel = formatString(this.options.textShowCarousel, num+1, this.maxIter);

                if (this.options.showCarousel)

                        this.carouselBtn.setHTML(textShowCarousel).setProperty('title', textShowCarousel);

                this.doSlideShow.bind(this)();

                this.fireEvent('onChanged');

        },

        clearTimer: function() {

                if (this.options.timed)

                        $clear(this.timer);

        },

        prepareTimer: function() {

                if (this.options.timed)

                        this.timer = this.nextItem.delay(this.options.delay, this);

        },

        doSlideShow: function(position) {

                if (this.galleryInit == 1)

                {

                        imgPreloader = new Image();

                        imgPreloader.onload=function(){

                                this.startSlideShow.delay(10, this);

                        }.bind(this);

                        imgPreloader.src = this.galleryData[0].image;

                        if(this.options.preloader)

                                this.galleryElements[0].load();

                } else {

                        if (this.options.showInfopane)

                        {

                                if (this.options.showInfopane)

                                {

                                        this.showInfoSlideShow.delay((500 + this.options.fadeDuration), this);

                                } else

                                        if ((this.options.showCarousel)&&(this.options.activateCarouselScroller))

                                                this.centerCarouselOn(position);

                        }

                }

        },

        createCarousel: function() {

                var carouselElement;

                if (!this.options.useExternalCarousel)

                {

                        var carouselContainerElement = new Element('div').addClass('carouselContainer').injectInside(this.galleryElement);

                        this.carouselContainer = new Fx.Styles(carouselContainerElement, {transition: Fx.Transitions.expoOut});

                        this.carouselContainer.normalHeight = carouselContainerElement.offsetHeight;

                        this.carouselContainer.set({'opacity': this.options.carouselMinimizedOpacity, 'top': (this.options.carouselMinimizedHeight - this.carouselContainer.normalHeight)});

                        this.carouselBtn = new Element('a').addClass('carouselBtn').setProperties({

                                title: this.options.textShowCarousel

                        }).injectInside(carouselContainerElement);

                        if(this.options.carouselPreloader)

                                this.carouselBtn.setHTML(this.options.textPreloadingCarousel);

                        else

                                this.carouselBtn.setHTML(this.options.textShowCarousel);

                        this.carouselBtn.addEvent(

                                'click',

                                function () {

                                        this.carouselContainer.clearTimer();

                                        this.toggleCarousel();

                                }.bind(this)

                        );

                        this.carouselActive = false;



                        carouselElement = new Element('div').addClass('carousel').injectInside(carouselContainerElement);

                        this.carousel = new Fx.Styles(carouselElement);

                } else {

                        carouselElement = $(this.options.carouselElement).addClass('jdExtCarousel');

                }

                this.carouselElement = new Fx.Styles(carouselElement, {transition: Fx.Transitions.expoOut});

                this.carouselElement.normalHeight = carouselElement.offsetHeight;

                if (this.options.showCarouselLabel)

                        this.carouselLabel = new Element('p').addClass('label').injectInside(carouselElement);

                carouselWrapper = new Element('div').addClass('carouselWrapper').injectInside(carouselElement);

                this.carouselWrapper = new Fx.Styles(carouselWrapper, {transition: Fx.Transitions.expoOut});

                this.carouselWrapper.normalHeight = carouselWrapper.offsetHeight;

                this.carouselInner = new Element('div').addClass('carouselInner').injectInside(carouselWrapper);

                if (this.options.activateCarouselScroller)

                {

                        this.carouselWrapper.scroller = new Scroller(carouselWrapper, {

                                area: 100,

                                velocity: 0.2

                        })



                        this.carouselWrapper.elementScroller = new Fx.Scroll(carouselWrapper, {

                                duration: 400,

                                onStart: this.carouselWrapper.scroller.stop.bind(this.carouselWrapper.scroller),

                                onComplete: this.carouselWrapper.scroller.start.bind(this.carouselWrapper.scroller)

                        });

                }

        },

        fillCarousel: function() {

                this.constructThumbnails();

                this.carouselInner.normalWidth = ((this.maxIter * (this.options.thumbWidth + this.options.thumbSpacing + 2))+this.options.thumbSpacing) + "px";

                this.carouselInner.style.width = this.carouselInner.normalWidth;

        },

        initCarousel: function () {

                this.createCarousel();

                this.fillCarousel();

                if (this.options.carouselPreloader)

                        this.preloadThumbnails();

        },

        flushCarousel: function() {

                this.thumbnailElements.each(function(myFx) {

                        myFx.element.remove();

                        myFx = myFx.element = null;

                });

                this.thumbnailElements = [];

        },

        toggleCarousel: function() {

                if (this.carouselActive)

                        this.hideCarousel();

                else

                        this.showCarousel();

        },

        showCarousel: function () {

                this.fireEvent('onShowCarousel');

                this.carouselContainer.start({

                        'opacity': this.options.carouselMaximizedOpacity,

                        'top': 0

                }).chain(function() {

                        this.carouselActive = true;

                        this.carouselWrapper.scroller.start();

                        this.fireEvent('onCarouselShown');

                        this.carouselContainer.options.onComplete = null;

                }.bind(this));

        },

        hideCarousel: function () {

                this.fireEvent('onHideCarousel');

                var targetTop = this.options.carouselMinimizedHeight - this.carouselContainer.normalHeight;

                this.carouselContainer.start({

                        'opacity': this.options.carouselMinimizedOpacity,

                        'top': targetTop

                }).chain(function() {

                        this.carouselActive = false;

                        this.carouselWrapper.scroller.stop();

                        this.fireEvent('onCarouselHidden');

                        this.carouselContainer.options.onComplete = null;

                }.bind(this));

        },

        constructThumbnails: function () {

                element = this.carouselInner;

                for(i=0;i<this.galleryData.length;i++)

                {

                        var currentImg = new Fx.Style(new Element ('div').addClass("thumbnail").setStyles({

                                        backgroundImage: "url('" + this.galleryData[i].thumbnail + "')",

                                        backgroundPosition: "center center",

                                        backgroundRepeat: 'no-repeat',

                                        marginLeft: this.options.thumbSpacing + "px",

                                        width: this.options.thumbWidth + "px",

                                        height: this.options.thumbHeight + "px"

                                }).injectInside(element), "opacity", {duration: 200}).set(this.options.thumbIdleOpacity);

                        currentImg.element.addEvents({

                                'mouseover': function (myself) {

                                        myself.clearTimer();

                                        myself.start(0.99);

                                        if (this.options.showCarouselLabel)

                                                $(this.carouselLabel).setHTML('<span class="number">' + (myself.relatedImage.number + 1) + "/" + this.maxIter + ":</span> " + myself.relatedImage.title);

                                }.pass(currentImg, this),

                                'mouseout': function (myself) {

                                        myself.clearTimer();

                                        myself.start(this.options.thumbIdleOpacity);

                                }.pass(currentImg, this),

                                'click': function (myself) {

                                        this.goTo(myself.relatedImage.number);

                                        if (this.options.thumbCloseCarousel)

                                                this.hideCarousel();

                                }.pass(currentImg, this)

                        });



                        currentImg.relatedImage = this.galleryData[i];

                        this.thumbnailElements[parseInt(i)] = currentImg;

                }

        },

        log: function(value) {

                if(console.log)

                        console.log(value);

        },

        preloadThumbnails: function() {

                var thumbnails = [];

                for(i=0;i<this.galleryData.length;i++)

                {

                        thumbnails[parseInt(i)] = this.galleryData[i].thumbnail;

                }

                this.thumbnailPreloader = new Preloader();

                this.thumbnailPreloader.addEvent('onComplete', function() {

                        var textShowCarousel = formatString(this.options.textShowCarousel, this.currentIter+1, this.maxIter);

                        this.carouselBtn.setHTML(textShowCarousel).setProperty('title', textShowCarousel);

                }.bind(this));

                this.thumbnailPreloader.load(thumbnails);

        },

        clearThumbnailsHighlights: function()

        {

                for(i=0;i<this.galleryData.length;i++)

                {

                        this.thumbnailElements[i].clearTimer();

                        this.thumbnailElements[i].start(0.2);

                }

        },

        changeThumbnailsSize: function(width, height)

        {

                for(i=0;i<this.galleryData.length;i++)

                {

                        this.thumbnailElements[i].clearTimer();

                        this.thumbnailElements[i].element.setStyles({

                                'width': width + "px",

                                'height': height + "px"

                        });

                }

        },

        centerCarouselOn: function(num) {

                if (!this.carouselWallMode)

                {

                        var carouselElement = this.thumbnailElements[num];

                        var position = carouselElement.element.offsetLeft + (carouselElement.element.offsetWidth / 2);

                        var carouselWidth = this.carouselWrapper.element.offsetWidth;

                        var carouselInnerWidth = this.carouselInner.offsetWidth;

                        var diffWidth = carouselWidth / 2;

                        var scrollPos = position-diffWidth;

                        try {

                          this.carouselWrapper.elementScroller.scrollTo(scrollPos,0);

                        }

                        catch(e) {

                          this.carouselWrapper.elementScroller.scrollTo = (scrollPos,0);

                        }

                }

        },

        initInfoSlideshow: function() {

                /*if (this.slideInfoZone.element)

                        this.slideInfoZone.element.remove();*/

                this.slideInfoZone = new Fx.Styles(new Element('div').addClass('slideInfoZone').injectInside($(this.galleryElement))).set({'opacity':0});

                var slideInfoZoneTitle = new Element('h2').injectInside(this.slideInfoZone.element);

                var slideInfoZoneDescription = new Element('p').injectInside(this.slideInfoZone.element);

                this.slideInfoZone.normalHeight = this.slideInfoZone.element.offsetHeight;

                this.slideInfoZone.element.setStyle('opacity',0);

        },

        changeInfoSlideShow: function()

        {

                this.hideInfoSlideShow.delay(10, this);

                this.showInfoSlideShow.delay(500, this);

        },

        showInfoSlideShow: function() {

                this.fireEvent('onShowInfopane');

                this.slideInfoZone.clearTimer();

                element = this.slideInfoZone.element;

                element.getElement('h2').setHTML(this.galleryData[this.currentIter].title);

                element.getElement('p').setHTML(this.galleryData[this.currentIter].description);

                if(this.options.slideInfoZoneSlide)

                        this.slideInfoZone.start({'opacity': [0, this.options.slideInfoZoneOpacity], 'height': [0, this.slideInfoZone.normalHeight]});

                else

                        this.slideInfoZone.start({'opacity': [0, this.options.slideInfoZoneOpacity]});

                if (this.options.showCarousel)

                        this.slideInfoZone.chain(this.centerCarouselOn.pass(this.currentIter, this));

                return this.slideInfoZone;

        },

        hideInfoSlideShow: function() {

                this.fireEvent('onHideInfopane');

                this.slideInfoZone.clearTimer();

                if(this.options.slideInfoZoneSlide)

                        this.slideInfoZone.start({'opacity': 0, 'height': 0});

                else

                        this.slideInfoZone.start({'opacity': 0});

                return this.slideInfoZone;

        },

        makeLink: function(num) {

                this.currentLink.setProperties({

                        href: this.galleryData[num].link,

                        title: this.galleryData[num].linkTitle

                })

                if (!((this.options.embedLinks) && (!this.options.showArrows) && (!this.options.showCarousel)))

                        this.currentLink.setStyle('display', 'block');

        },

        clearLink: function() {

                this.currentLink.setProperties({href: '', title: ''});

                if (!((this.options.embedLinks) && (!this.options.showArrows) && (!this.options.showCarousel)))

                        this.currentLink.setStyle('display', 'none');

        },

        /* To change the gallery data, those two functions : */

        flushGallery: function() {

                this.galleryElements.each(function(myFx) {

                        myFx.element.remove();

                        myFx = myFx.element = null;

                });

                this.galleryElements = [];

        },

        changeData: function(data) {

                this.galleryData = data;

                this.clearTimer();

                this.flushGallery();

                if (this.options.showCarousel) this.flushCarousel();

                this.constructElements();

                if (this.options.showCarousel) this.fillCarousel();

                if (this.options.showInfopane) this.hideInfoSlideShow();

                this.galleryInit=1;

                this.lastIter=0;

                this.currentIter=0;

                this.doSlideShow(1);

        },

        /* Plugins: HistoryManager */

        initHistory: function() {

                this.fireEvent('onHistoryInit');

                this.historyKey = this.galleryElement.id + '-picture';

                if (this.options.customHistoryKey)

                        this.historyKey = this.options.customHistoryKey();

                this.history = HistoryManager.register(

                        this.historyKey,

                        [1],

                        function(values) {

                                if (parseInt(values[0])-1 < this.maxIter)

                                        this.goTo(parseInt(values[0])-1);

                        }.bind(this),

                        function(values) {

                                return [this.historyKey, '(', values[0], ')'].join('');

                        }.bind(this),

                        this.historyKey + '\\((\\d+)\\)');

                this.addEvent('onChanged', function(){

                        this.history.setValue(0, this.currentIter+1);

                }.bind(this));

                this.fireEvent('onHistoryInited');

        }

};

gallery = new Class(gallery);

gallery.implement(new Events);

gallery.implement(new Options);



gallery.Transitions = new Abstract ({

        fade: function(oldFx, newFx, oldPos, newPos){

                oldFx.options.transition = newFx.options.transition = Fx.Transitions.linear;

                oldFx.options.duration = newFx.options.duration = this.options.fadeDuration;

                if (newPos > oldPos) newFx.start({opacity: 1});

                else

                {

                        newFx.set({opacity: 1});

                        oldFx.start({opacity: 0});

                }

        },

        crossfade: function(oldFx, newFx, oldPos, newPos){

                oldFx.options.transition = newFx.options.transition = Fx.Transitions.linear;

                oldFx.options.duration = newFx.options.duration = this.options.fadeDuration;

                newFx.start({opacity: 1});

                oldFx.start({opacity: 0});

        },

        fadebg: function(oldFx, newFx, oldPos, newPos){

                oldFx.options.transition = newFx.options.transition = Fx.Transitions.linear;

                oldFx.options.duration = newFx.options.duration = this.options.fadeDuration / 2;

                oldFx.start({opacity: 0}).chain(newFx.start.pass([{opacity: 1}], newFx));

        }

});



/* All code copyright 2007 Jonathan Schemoul */



/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *

 * Follows: Preloader (class)

 * Simple class for preloading images with support for progress reporting

 * Copyright 2007 Tomocchino.

 * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */



var Preloader = new Class({



  Implements: [Events, Options],



  options: {

    root        : '',

    period      : 100

  },



  initialize: function(options){

    this.setOptions(options);

  },



  load: function(sources) {

    this.index = 0;

    this.images = [];

    this.sources = this.temps = sources;

    this.total = this. sources.length;



    this.fireEvent('onStart', [this.index, this.total]);

    this.timer = this.progress.periodical(this.options.period, this);



    this.sources.each(function(source, index){

      this.images[index] = new Asset.image(this.options.root + source, {

        'onload'  : function(){ this.index++; if(this.images[index]) this.fireEvent('onLoad', [this.images[index], index, source]); }.bind(this),

        'onerror' : function(){ this.index++; this.fireEvent('onError', [this.images.splice(index, 1), index, source]); }.bind(this),

        'onabort' : function(){ this.index++; this.fireEvent('onError', [this.images.splice(index, 1), index, source]); }.bind(this)

      });

    }, this);

  },



  progress: function() {

    this.fireEvent('onProgress', [Math.min(this.index, this.total), this.total]);

    if(this.index >= this.total) this.complete();

  },



  complete: function(){

    $clear(this.timer);

    this.fireEvent('onComplete', [this.images]);

  },



  cancel: function(){

    $clear(this.timer);

  }



});



Preloader.implement(new Events, new Options);



/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *

 * Follows: formatString (function)

 * Original name: Yahoo.Tools.printf

 * Copyright Yahoo.

 * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */



function formatString() {

        var num = arguments.length;

        var oStr = arguments[0];

        for (var i = 1; i < num; i++) {

                var pattern = "\\{" + (i-1) + "\\}";

                var re = new RegExp(pattern, "g");

                oStr = oStr.replace(re, arguments[i]);

        }

        return oStr;

}
