var qm;
if(!qm) {
    qm = {};
} else if (typeof qm !== 'object') {
    throw new Error('qm already exists and is not an object');
}
qm.carousel = Class.create({
    options: {
        _slides: [],
        _currentSlide: 0,
		_captionWidth: 0,
		_moveMode: 'absolute',
        interval: 5,
        duration: 1,
        fps: 50,
        url: '',
		siteUrl: '',
        container: {
            id: ''
        },
        caption: {
            id: '',
            startEl: '',
            endEl: ''
        },
        pointer: {
            id: ''
        }
    },
    initialize: function(options) {
        Object.extend(this.options, options);
    },
    startup: function() {
        var opts = this.options;
        if(opts._slides.length == 0 && opts.url != '') {
            new Ajax.Request(opts.url, {
                method: 'get',
                onSuccess: function(e) {
                    opts._slides = eval(e.responseText);
                    this.createCaption();
                    this.animate();
                    new PeriodicalExecuter(this.cycle.start.bind(this), opts.interval);
                }.bind(this)
            });
        }
    },
	animate: function() {
		this.moveArrow();
		this.updateContainer();
	},
    createCaption: function() {
        var opts = this.options;
        if(opts.caption.id !== '') {
	        opts._captionWidth = $(opts.caption.id).getWidth();
            for(var i=0; i<opts._slides.length; i++) {
                var cap = opts._slides[i].title;                      
                $(opts.caption.id).insert(opts.caption.startEl + cap + opts.caption.endEl);
                var cEls = $(opts.caption.id).childElements();
                var cElId = 'caption' + cEls.length;
                cEls[cEls.length - 1].setAttribute('id', cElId);
                cEls[cEls.length - 1].setAttribute('slide', cEls.length - 1);
				if(opts._slides.length == 1) {
					cEls[cEls.length - 1].setStyle({width: opts._captionWidth + 'px'});
				} else if(opts._slides.length > 1){
					cEls[cEls.length - 1].setStyle({width:(opts._captionWidth / opts._slides.length) + 'px'});
				}
                Event.observe(cElId, 'click', this.captionClick.bindAsEventListener(this));
            }
        }
    },
    captionClick: function(el) {
        var slide = el.target.readAttribute('slide');
        var opts = this.options;
        this.cycle.stop();
        opts._currentSlide = slide;
        this.animate();
    },
    cycle: {
        pexec: null,
        start: function(pe) {
			if(this.options._slides.length == 1) {
				this.cycle.stop();
			}
            if(this.cycle.stopped == false) {
                var opts = this.options;
                this.cycle.pexec = pe;
                new Effect.Fade(opts.container.id, {
                    duration: opts.duration,
                    fps: opts.fps,
                    afterFinish: function() {						
                        if(opts._slides.length > 0) {
                            //set _currentSlide and move pointer
                            if(opts._currentSlide < opts._slides.length - 1) {
                                opts._currentSlide = opts._currentSlide + 1;                           
                            } else {
                                opts._currentSlide = 0;                                
                            }
							this.animate();                        
                            new Effect.Appear(opts.container.id, {
                                duration: opts.duration,
                                fps: opts.fps,
                                queue: 'end'
                            });
                        }
                    }.bind(this)
                });
            } else {
                this.cycle.stop();
            }
        },
        stopped: false,
        stop: function() {
            if(this.stopped == false) {
                this.stopped = true;
            }
            if(this.pexec != null) {
                this.pexec.stop();
            }
        }
    },
    moveArrow: function(x, y) {
		var opts = this.options;
		var capWidth = (opts._captionWidth / opts._slides.length);
		var mx = (opts._currentSlide * capWidth) + (capWidth / 2);
        new Effect.Move($(opts.pointer.id), { x:mx, y:0, mode: opts._moveMode });
    },
    updateContainer: function() {
        var opts = this.options;
		var url = this.options.siteUrl;
		var curSlide = this.options._slides[this.options._currentSlide];
		var contents = '';
		if(curSlide != null) {
			url += curSlide['link'];
		}
		if(curSlide['url'] != null) {
        	contents = "<img src='" + curSlide['url'] + "'/>";
		} else if(curSlide['detailsHTML'] != null) {
			contents = '<p>' + curSlide['detailsHTML'] + '</p>';
		} else if(curSlide['details'] != null) {
			contents = '<p>' + curSlide['details'] + '</p>';
		}
		$(opts.container.id).update("<a href='" + url + "'>" + contents +'</a>');
    }
});