/**
	© Taras Bogach 2009
	License - GPL
*/
(function($){
	$.fn.magnify=function(options){
		options=$.extend({},$.fn.magnify.defaultOptions,options);
		var elements=this;
		elements.each(function(){
			var element=$(this);
			var defaults={};
			for(var key in options.property){
				if(options.property[key] instanceof Object){
					for(var key2 in options.property[key]){
						defaults[key2]=element.css(key2);
					}		
				}else{
					defaults[options.property[key]]=element.css(options.property[key]);
				}
			}
			if(options.distanceX==null)options.distanceX=element.width()*3;
			if(options.distanceY==null)options.distanceY=element.height()*3;
			$(this).data('magnify',{options:options,defaults:defaults})
		});
		$().bind('mousemove',function(event){
			elements.each(function(){
				$.fn.magnify.magnify($(this),event);
			});
		});
		return this;
	}
	$.fn.magnify.defaultOptions={
		maxExpansion:2,
		minExpansion:1,
		distance:null,
		distanceX:null,
		distanceY:null,
		property:["width","height"],
		onmagnify:function(event){}
	}
	$.fn.magnify.magnify=function(element,event){
		var data=element.data('magnify');
		var distance=element.offset();
		distance.left=Math.abs(event.pageX-distance.left-$(element).width()/2);
		distance.top=Math.abs(event.pageY-distance.top-$(element).height()/2);
		if(data.options.distance!=null){
			distance=Math.sqrt(Math.pow(distance.left,2)+Math.pow(distance.top,2));
			var expansion=data.options.maxExpansion*1+(distance/data.options.distance*(data.options.minExpansion-data.options.maxExpansion));
		}else{
			if(data.options.distanceX!=null){
				var expansionX=data.options.maxExpansion*1+(distance.left/data.options.distanceX*(data.options.minExpansion-data.options.maxExpansion));
			}
			if(data.options.distanceY!=null){
				var expansionY=data.options.maxExpansion*1+(distance.top/data.options.distanceY*(data.options.minExpansion-data.options.maxExpansion));
			}
			var expansion=((expansionX?expansionX:expansionY)+(expansionY?expansionY:expansionX))/2;
		}
		if(expansion<data.options.minExpansion)expansion=1;
		data.expansion=expansion;
		data.options.onmagnify({element:element,data:data});
		for(var key in data.options.property){
			if(data.options.property[key] instanceof Object){
				for(var key2 in data.options.property[key]){
					var Val="rgb("+$.fn.magnify.magnifyColor(
						expansion,
						data.options.minExpansion,
						data.options.maxExpansion,
						data.defaults[key2],
						data.options.property[key][key2]
					).join(",")+")";
					element.css(key2,Val);
				}		
			}else{
				if(data.options.property[key].match(/color/i)!=null){
					var Val="rgb("+$.fn.magnify.magnifyColor(
						expansion,
						data.options.minExpansion,
						data.options.maxExpansion,
						data.defaults[data.options.property[key]],
						[255,255,255]
					).join(",")+")";
				}else{
					var Str=data.defaults[data.options.property[key]].toString();
					var Val=Str.replace(/([0-9]+)/,expansion*parseInt(Str));
				}
				element.css(data.options.property[key],Val);
			}
		}
	}
	$.fn.magnify.magnifyColor=function(expansion,minExpansion,maxExpansion,from,to){
		from=$.fn.magnify.parseColor(from);
		to=$.fn.magnify.parseColor(to);
		var rgb=[];
		for(var key in from){
			rgb[key]=Math.round(from[key]+((to[key]-from[key])*((expansion-minExpansion)/(maxExpansion-minExpansion))));
		}
		return rgb;
	}
	$.fn.magnify.parseColor=function(color){
		var a=color;
		switch(true){
			case(color instanceof Object):
				var rgb=color;
				break;
			case(color.match(/^#[0-9a-f]{3}$/i)!=null):
				num=parseInt(color.replace("#",""),16);
				var rgb=[
					((num&0xF00)>>8)+(((num&0xF00)>>8)<<4),
					((num&0xF0)>>4)+(((num&0xF0)>>4)<<4),
					((num&0xF)>>0)+(((num&0xF)>>0)<<4)
				];
				break;
			case(color.match(/^#[0-9a-f]{6}$/i)!=null):
				num=parseInt(color.replace("#",""),16);
				var rgb=[
					(num&0xFF0000)>>16,
					(num&0xFF00)>>8,
					(num&0xFF)>>0
				];
				break;
			case(color.replace(/\s/g,"").match(/^rgb\([0-9]{1,3},[0-9]{1,3},[0-9]{1,3}\)$/i)!=null):
				var rgb=color.match(/[0-9]{1,3}/g);
				for(var i in rgb)rgb[i]=rgb[i]*1;
				break;
			case(color=="transparent"):
				var rgb=[255,255,255];
				break;
			default:
				var rgb=[0,0,0];
				break;
		}
		return rgb;
	}
})(jQuery);
