$(document).ready(function() {viewerInit();});

var viewerInit = function() {
	var viewer = new Viewer(document.body);
};

var ViewerUtil = {
	'addZeros':function( str, n ) {
		while ( str.length < n ) {
			str = '0' + str;
		}
		return str;
	},
	'dec2hex': function( n, s ) {
		var i;
		var T = ['0','1','2','3','4','5','6','7','8','9','A','B','C','D','E','F'];
		var code = '';
		while ( n >= 16 ) {
			code += T[parseInt(n%16)];
			n /= 16;
		}
		code += T[parseInt(n%16)];
		while ( code.length < s ) {
			code += '0';
		}
		var codeRev = '';
		for ( i = 0; i < code.length; i++ ) {
			codeRev += code[code.length-1-i];
		}
		return codeRev;
	},
	'getRandom': function( lower, upper ) {
		var answer = 0;
		var n = Math.random() * 10000000;
		answer += lower;
		if ( upper - lower + 1 > 0 ) {
			answer += parseInt( n % ( upper - lower + 1 ) );
		}
		return answer;
	},
	'getRandomColorCode': function( lower, upper ) {
		var r = this.dec2hex(this.getRandom(lower,upper),2);
		var g = this.dec2hex(this.getRandom(lower,upper),2);
		var b = this.dec2hex(this.getRandom(lower,upper),2);
		return '#'+r+g+b;
	},
	'getColorWeight': function( color ) {
		var r = parseInt( color.substr(1,2), 16 );
		var g = parseInt( color.substr(3,2), 16 );
		var b = parseInt( color.substr(5,2), 16 );
		return {'r':r,'g':g,'b':b};
	},
	'getDarkColor': function( color ) {
		var c = this.getColorWeight( color );
		c.r = c.r - 100 < 0 ? 0 : c.r - 100;
		c.g = c.g - 100 < 0 ? 0 : c.g - 100;
		c.b = c.b - 100 < 0 ? 0 : c.b - 100;
		var r = this.dec2hex(c.r, 2);
		var g = this.dec2hex(c.g, 2);
		var b = this.dec2hex(c.b, 2)
		return "#"+r+g+b;
	},
};

var Viewer = function(parent) {
	var self = this;
	var boxes;
	var boxSize = 128;
	var boxNumberX = 0;
	var boxNumberY = 0;
	var frame = document.createElement('div');
	var element = document.createElement('div');
	var jqFrame = $(frame);
	var jqElement = $(element);
	var jqParent = $(parent);
	var width;
	var height;
	var x;
	var y;
	var images = new Array();
	
	var getElementDefaultCSS = function() {
		return {
			'position':'absolute',
			'top':x+'px',
			'left':y+'px',
			'overflow':'hidden',
			'width':boxNumberX*boxSize+'px',
			'height':boxNumberY*boxSize+'px',
		};
	};
	
	var getFrameDefaultCSS = function() {
		return {
			'position':'absolute',
			'top':'0px',
			'left':'0px',
			'overflow':'hidden',
			'width': width+'px',
			'height': height+'px',
			'z-index': '-5',
		};
	};
	var getAnimOption = function() {
		return {};
	};
	
	self.setPosition = function( _x, _y ) {
		x = _x;
		y = _y;
		return self;
	};
	
	self.update = function(anim) {
		width = $(window).width();
		height = $(window).height();
		
		jqElement.css( getElementDefaultCSS() );
		
		if ( anim ) {
			jqFrame.animate( getFrameDefaultCSS(), getAnimOption() );
		} else {
			jqFrame.css( getFrameDefaultCSS() );
		}
		
		return self;
	};
	
	self.init = function() {
		self.setPosition( -2*boxSize-boxSize/2, -2*boxSize-boxSize/2 );
		boxNumberX = Math.round( $(window).width()  / boxSize ) + 5;
		boxNumberY = Math.round( $(window).height() / boxSize ) + 5;
		
		boxes = new Array();
		for ( var i = 0; i < boxNumberY; i++ ) {
			boxes[i] = new Array();
			for ( var j = 0; j < boxNumberX; j++ ) {
				boxes[i][j] = new ViewerBox(boxSize, element, self);
				boxes[i][j].setPosition(j, i);
				var backgroundColor = ViewerUtil.getRandomColorCode(150, 255);
				var borderColor = ViewerUtil.getDarkColor( backgroundColor );
				boxes[i][j].setBackground(backgroundColor);
				boxes[i][j].setBorderColor( borderColor );
				boxes[i][j].update();
			}
		}

		var url = '/api/get_images.xml';
		$.ajax({
			'type'		: 'GET',
			'url'		: url,
			'dataType'	: 'xml',
			'success'	: loadImages
		});
				
		self.update();
		jqFrame.append(element);
		jqFrame.addClass('Viewer');
		jqParent.append(frame);
		return self;
	};
	
	var loadImages = function(xml) {
		$(xml).find('image').each(function() {
			images.push( $(this).first('id').context.textContent );
		});
		$('.Viewer:first').find('.ViewerBoxFrame').each(function() {
			var type = ViewerUtil.getRandom(0,2);
			if ( type == 0 ) {
				var img = document.createElement('img');
				img.src = '/api/get_image/'+images[ViewerUtil.getRandom(0,images.length-1)]+'/s';
				$(img).css({'width':$(this).width()+'px', 'height':$(this).height()+'px'});
				var pBox = this;
				$(pBox).show(true);
				$(img).ready(function() {
					$(img).css({'opacity':'0.0'});
					pBox.box.setHTML(img);
					$(img).animate({'opacity':'1.0'}, {'duration':1000});
				});
			}
		});
	};
		
	var demoCheckTimer = null;
	var demoTimer = null;
	
	self.demo = function() {
		$('.Viewer:first').find('.ViewerBoxFrame').each(function() {
			var type = ViewerUtil.getRandom(0,5);
			if ( type == 0 ) {
				this.box.show(true);
			} else if ( type == 1 ) {
				this.box.hide(true);
			} else if ( type == 2 ) {
				var img = document.createElement('img');
				img.src = '/api/get_image/'+images[ViewerUtil.getRandom(0,images.length-1)]+'/s';
				$(img).css({'width':$(this).width()+'px', 'height':$(this).height()+'px'});
				var pBox = this;
				$(pBox).show(true);
				$(img).ready(function() {
					$(img).css({'opacity':'0.0'});
					pBox.box.setHTML(img);
					$(img).animate({'opacity':'1.0'}, {'duration':1000});
				});
				// this.box.setHTML('<img src="/api/get_image/'+images[ViewerUtil.getRandom(0,images.length-1)]+'/s">');
			} else if ( type == 3 ) {
				this.box.hide(true, this.box.setHTML(''));
			}
		});
	};
	
	self.demoCheckReset = function() {
		clearInterval( demoTimer );
		demoTimer = null;
		clearInterval( demoCheckTimer );
		demoCheckTimer = null;
		demoCheckTimer = setInterval( self.demoCheck, 500 );
	};
	self.demoCheck = function() {
		if ( demoTimer == null ) {
			demoTimer = setInterval( self.demo, 5000 );
		}
	};
	
	self.init();
	self.demoCheckReset();
	return self;
};

var ViewerBox = function(_size, parent, viewer) {
	var self = this;
	var size = 128;
	var element = document.createElement('div');
	var frame = document.createElement('div');
	var jqElement = $(element);
	var jqFrame = $(frame);
	var jqParent = $(parent);
	var x;
	var y;
	var background = 'none';
	var borderColor = '#000000';
	
	self.getX = function() {
		return x;
	};
	self.getY = function() {
		return y;
	};
	self.setBackground = function(_background) {
		background = _background;
		return self;
	};
	self.setBorderColor = function(_color) {
		borderColor = _color;
		return self;
	};
		
	var getAnimOption = function(callback) {
		return {'complete':callback};
	};
	
	var getFrameDefaultCSS = function() {
		return {
			'position':'absolute',
			'width': size+'px',
			'height': size+'px',
			'cursor':'pointer',
		};
	};
	
	var getElementDefaultCSS = function() {
		return {
			'position':'absolute',
			'top': '0px',
			'left': '0px',
			'borderRadius': '5px',
			'border': '1px solid '+borderColor,
			'background': background,
			'width':size-4+'px',
			'height':size-4+'px',
			'overflow':'hidden',
		};
	};
	var getElementUpdateCSS = function() {
		return {
			'border': '1px solid '+borderColor,
			'background': background,
		};
	};
	
	var getPositionCSS = function() {
		return {
			'left': x*size+'px',
			'top': y*size+'px',
		};
	};
	
	self.setPosition = function( x_, y_ ) {
		x = x_;
		y = y_;
		return self;
	};
	
	self.update = function(anim) {
		jqElement.css( getElementUpdateCSS() );
		if ( anim ) {
			jqFrame.animate( getPositionCSS(), getAnimOption() );
		} else {
			jqFrame.css( getPositionCSS() );
		}
		return self;
	};
	
	self.setHTML = function(_html) {
		jqElement.empty().append(_html);
		return self;
	};
	
	var getPowerLightCSS = function() {
		return {
			'opacity':'1.0',
		};
	};
	self.setPowerLight = function(anim) {
		if ( anim ) {
			jqFrame.animate( getPowerLightCSS(), getAnimOption() );
		} else {
			jqFrame.css( getPowerLightCSS() );
		}
		return self;
	};
	var getLightCSS = function() {
		return {
			'opacity':'0.2',
		};
	};
	self.setLight = function(anim) {
		if ( anim ) {
			jqFrame.animate( getLightCSS(), getAnimOption() );
		} else {
			jqFrame.css( getLightCSS() );
		}
		return self;
	};
	var getHideCSS = function() {
		return {
			'opacity':'0.0'
		};
	};
	var getShowCSS = function() {
		return getLightCSS();
	};
	self.setHide = function(anim, callback) {
		if ( anim ) {
			jqFrame.animate( getHideCSS(), getAnimOption(callback) );
		} else {
			jqFrame.css( getHideCSS() );
		}
		return self;
	};
	
	self.show = function(anim) {
		if ( anim ) {
			jqFrame.animate( getShowCSS(), {'duration':1000} );
		} else {
			jqFrame.css( getShowCSS() );
		}
		return self;
	};
	
	self.hide = function(anim) {
		if ( anim ) {
			jqFrame.animate( getHideCSS(), {'duration':1000} );
		} else {
			jqFrame.css( getHideCSS() );
		}
		return self;
	};
	
	self.flash = function() {
		//self.setPowerLight(true).setLight(true);
		var opt1 = { 'duration': ViewerUtil.getRandom(500,1000) };
		var opt2 = { 'duration': ViewerUtil.getRandom(500,1000) };
		jqFrame.animate(getPowerLightCSS(), opt1).animate(getLightCSS(), opt2);
		return self;
	};
	
	self.init = function(_size) {
		size = _size;
		jqFrame.css( getFrameDefaultCSS() );
		jqFrame.addClass('ViewerBoxFrame');
		frame.box = self;
		self.setLight();
		jqFrame.append(element);
		jqElement.css( getElementDefaultCSS() );
		jqParent.append(frame);
		
		// reg events
		jqFrame.unbind('hover').hover( function() {
			viewer.demoCheckReset();
			self.setPowerLight(true);
		}, function() {
			viewer.demoCheckReset();
			self.setLight(true);
		});
		return self;
	};
	
	self.init(_size);
	return self;
};

