/**
 * Simple news container class.
 */
var News = new Class({
	initialize: function(json, newsId) {
		this.id = newsId;
		this.image = unescape(json.image);
		this.imageAlt = unescape(json.image_alt);
		this.link = unescape(json.link);
		this.headline = unescape(json.headline);
		this.text = unescape(json.text);
	}
});
/**
 * A news rotator that fetches the sources from external source.
 */
var NewsRotator = new Class({
	Implements: Options,
	options: {
		fetchUrl: 'http://www.fk-austria.at/index.php?eID=rotatingNews',
		imageFolder: 'uploads/pics/',
		prefixNews: 'news_',
		prefixTiming: 'rotate_'
	},
	/**
	 * Initializes necessary container and starts the periodical rotation of the news.
	 */
	initialize: function() {
		this.blocked = 0;
		var outer = $('rotateCnt');
		this.target = $$('td.possibleRotateTrgt')[1];
		this.news = new Array();
		this.current = 1; // first news is already displayed, we use second to rotate first
		if ($chk(outer) && $chk(this.target)) {
			// get the timing
			this.timing = this.getPrefixedClassValue(outer.get('class'), this.options.prefixTiming);
			if (this.timing.toInt() == 0) {
				this.timing = 5;
			}
			this.timing *= 700;
			// fetch the news and start rotating after getting all
			this.fetchNews(outer.getFirst().getFirst().getFirst());
		}
	},
	/**
	 * Resolves the news to fetch and gets them.
	 */
	fetchNews: function(parent) {
		// get the ids to fetch
		this.newsIds = new Array();
		parent.getChildren('div').each(function(elem) {
			this.newsIds.push(this.getPrefixedClassValue(elem.get('class'), this.options.prefixNews));
		}, this);
		this.newsIds.sort(function(a, b) {
			if (a < b) return -1;
			if (a > b) return 1;
			return 0;
		});
		// fetch the json elements
		this.newsIds.each(function(newsId) {
			new Request.JSON({
				url: this.options.fetchUrl,
				onComplete: this.addNews.bindWithEvent(this, newsId)
			}).get({id: newsId});
		}, this);
	},
	/**
	 * Adds the fetched news to internal array.
	 * Initializes the image preloading.
	 */
	addNews: function(json, newsId) {
		this.news.push(new News(json, newsId));
		if (this.news.length == this.newsIds.length) {
			this.preloadImages();
		}
	},
	/**
	 * Preloads the images of the divs.
	 * Initializes the function that builds the news html.
	 */
	preloadImages: function() {
		var urls = new Array();
		this.news.each(function(news) {
			urls.push(this.options.imageFolder + news.image);
		}, this);
		new Asset.images(
			urls, {
				onComplete: this.buildNewsHTML.bind(this)
			}
		);
	},
	/**
	 * Creates the html structure for the fetched news.
	 * Initializes the rotation.
	 */
	buildNewsHTML: function() {
		this.newsHTML = new Array();
		this.news.each(function(news) {
			this.newsHTML.push(new Element('table', {
				width: 540,
				border: 0,
				cellspacing: 0,
				cellpadding: 0,
				html: '<tbody>' + 
						'<tr>' +
							'<td colspan="2">' + 
								'<a title="' + news.imageAlt + '" href="' + news.link + '">' +
									'<img border="0" title="' + news.imageAlt + '" alt="' + news.imageAlt + '" src="' + this.options.imageFolder + news.image + '"/>' +
								'</a>' + 
							'</td>' +
						'</tr>' + 
						'<tr>' +
							'<td width="438" valign="top" align="left">' +
								'<h2 style="margin-top: 10px;">' + 
									'<b>' + 
										'<a title="' + news.headline + '" href="' + news.link + '">' + news.headline + '</a>' +
									'</b>' + 
								'</h2>' +
							'</td>' +
							'<td width="102" valign="bottom" align="left"></td>' +
						'</tr>' +
						'<tr>' +
							'<td valign="top" align="left" colspan="2">' +
								'<span style="font-size: 12px; color: #fff; font-family: Verdana,Arial,sans-serif;line-height: 15px;">' + news.text + '</span>' +
							'</td>' +
						'</tr>' +
					'</tbody>'
			}));
		}, this);
		// rotate the news
		this.rotateNews.periodical(this.timing, this);
	},
	/**
	 * Fetches the news ids that should be rotated.
	 */
	getNewsToRotate: function(parent) {
		parent.getChildren('div').each(function(elem) {
			this.news.push(this.getPrefixedClassValue(elem.get('class'), this.options.prefixNews));
		}, this);
	},
	/**
	 * Rotates to the next news.
	 */
	rotateNews: function() {
		if (this.blocked == 0) {
			this.blocked = 1;
			// if last news reached we start all over again
			if (this.current == this.newsHTML.length) {
				this.current = 0;
			}
			// fade out the old news
			var fxOld = new Fx.Elements(this.target.getChildren('table'), {
				wait: false,
				duration: 700,
				transition: Fx.Transitions.Linear,
				onComplete: this.showNextNews.bind(this)
			}).start({ 0: { 'opacity': 0 } });
		}
	},
	/**
	 * Shows the next news by removing the old news from dom and fading in the new one.
	 */
	showNextNews: function(old) {
		var newsToShow = this.newsHTML[this.current++].clone().set('styles', {'opacity': 0});
		var father = this;
		var fxNew = new Fx.Elements(newsToShow, {
			wait: false,
			duration: 700,
			transition: Fx.Transitions.Linear,
			onComplete: function() { father.blocked = 0 }
		});
		old.dispose();
		this.target.grab(newsToShow);
		fxNew.start({ 0: {'opacity': 1}	});
	},
	/**
	 * Extracts a prefixed value hidden in a css class name.
	 * E.g. <div class="class1 class2 value5 test"> and call it with the class value and prefix 'value' would return 5
	 */
	getPrefixedClassValue: function(txt, prefix) {
		var result;
		txt.split(' ').each(function(elem) {
			if (elem.trim().contains(prefix)) {
				result = elem.substring(prefix.length);
			}
		});
		return result;
	}
});
window.addEvent('domready', function() {
	new NewsRotator();
});