﻿// Declare our Class
WebLinc = function(config)
{
	config = config || {};
	config.SiteSettings = config.SiteSettings || {};
	$.extend(this, config);
};
WebLinc.prototype = $.extend(WebLinc.prototype,
{
	SiteSettings: null,

	init: function()
	{
		var __scopeHack = this;

		this.subscribedEvents = {};

		this.attachEvents();
		
		this.ProductComparisonManager = new WebLinc.ProductComparisonManager();
	},

	subscribedEvents: null,
	on: function(control, e, handler, scope)
	{
		this.subscribedEvents[control] = this.subscribedEvents[control] || {};
		this.subscribedEvents[control][e] = this.subscribedEvents[control][e] || [];
		this.subscribedEvents[control][e].push({handler: handler, scope: scope});
	},
	fireEvent: function(control, e)
	{
		if (this.subscribedEvents[control] && this.subscribedEvents[control][e])
		{
			for (var i = 0; i < this.subscribedEvents[control][e].length; i++)
			{
				this.subscribedEvents[control][e][i].handler.apply((this.subscribedEvents[control][e].scope || this), Array.prototype.slice.apply(arguments, [2]))
			}
		}
	},

	attachEvents: function()
	{
		this.attachInputEvents();
		this.attachAdvancedSelectorEvents();
	},
	attachInputEvents: function()
	{
		var __scopeHack = this;
		$("input[type=text], input[type=password], textarea")
			.focus(function()
			{
				$(this).addClass("focused");
			})
			.blur(function()
			{
				$(this).removeClass("focused");
			})
		;
	},
	attachAdvancedSelectorEvents: function()
	{
		function handleChange(as, it)
		{
			as.find('> li').removeClass('selected');
			it.addClass('selected');
		}

		var __scopeHack = this;
		$('ul.advanced-selector').each(function(i)
		{
			$(this).find('> li')
				.data('ul', $(this))
				.hover
				(
					function()
					{
						$(this).addClass('hover');
					},
					function()
					{
						$(this).removeClass('hover');
					}
				)
				.each(function(j)
				{
					if ($(this).find('> dl.item > dt.item-term input:radio:checked').length)
					{
						handleChange($(this).data('ul'), $(this));
					}
				})
				.find('> dl.item')
					.data('ul', $(this))
					.click(function(evt)
					{
						$(this).find('dt.item-term input:radio').get()[0].checked = true;
						handleChange($(this).data('ul'), $(this).parent());
					})
			;
		});
	},	

	productMediaFilenameStringToObject: function(str)
	{
		var obj = {};
		var parts = str.split(/\./);
		var key = parts[0];
		var parts = parts.slice(1);
		for (var i = 0; i < key.length; i++)
		{
			obj[key.charAt(i)] = parts[i];
		}
		return obj;
	},
	productMediaFilenameObjectToString: function(obj)
	{
		var arr = [''];
		var key = 'ihwvx';
		for (var i = 0; i < key.length; i++)
		{
			if (obj[key.charAt(i)])
			{
				arr[0] += key.charAt(i);
				arr[arr.length] = obj[key.charAt(i)];
			}
		}
		return arr.join('.');
	},
	
	RegisterTextBoxDefaultText: function(textBox, defaultText)
	{
		textBox.data('WebLinc.app.RegisterTextBoxDefaultText.DefaultText', defaultText);
		textBox
			.focus(function(evt)
			{
				var t = $(this);
				if ((t.data('WebLinc.app.RegisterTextBoxDefaultText.DefaultText') == undefined) && t.val().length)
				{
					t.data('WebLinc.app.RegisterTextBoxDefaultText.DefaultText', t.val());
				}
				if ((t.data('WebLinc.app.RegisterTextBoxDefaultText.DefaultText') != undefined) && (t.data('WebLinc.app.RegisterTextBoxDefaultText.DefaultText') == t.val()))
				{
					t.val("");
				}
			})
			.blur(function(evt)
			{
				var t = $(this);
				if (!t.val().length && (t.data('WebLinc.app.RegisterTextBoxDefaultText.DefaultText') != undefined))
				{
					t.val(t.data('WebLinc.app.RegisterTextBoxDefaultText.DefaultText'));
				}
			})
		;
		if (!textBox.val().length)
			textBox.val(defaultText);
	},
	
	SplitSearchString: function(s)
	{
		var c = '';
		var terms = [];
		var term = '';
		var mode = true;
		var quoting = false;
		for (var i = 0; i < s.length; i++)
		{
			c = s.charAt(i);
			switch (c)
			{
				case '-':
					if (!quoting && !term.length)
					{
						mode = false;
						continue;
					}
					break;
				case '+':
					if (!quoting && !term.length)
					{
						mode = true;
						continue;
					}
					break;
				case '"':
					if (quoting)
					{
						if (mode && term.length) terms[terms.length] = term;
						term = '';
					}
					quoting = !quoting;
					continue;
					break;
				case ' ':
					if (!quoting)
					{
						if (mode && term.length) terms[terms.length] = term;
						term = '';
						mode = true;
						continue;
					}
					break;
			}
			term += c;
		}
		if (mode && term.length) terms[terms.length] = term;
		return terms;
	},
	
	HighlightText: function(els, terms, split)
	{
		if (split)
		{
			terms = this.SplitSearchString(terms);
		}
		else
		{
			terms = [terms];
		}
		function processNode(node, terms)
		{
			for (var i = 0; i < node.childNodes.length; i++)
			{
				processNode(node.childNodes[i], terms);
			}
			if (node.nodeType == 3)
			{
				term = terms[0];
				var newNode = node;
				var value = node.nodeValue;
				var idx = value.toLowerCase().indexOf(term.toLowerCase());
				if (idx >= 0)
				{
					value = '<span class="highlight-wrapper">' + value.substr(0, idx) + '<span class="highlight">' + value.substr(idx, term.length) + '</span>' + value.substr((idx + term.length)) + '</span>';
					newNode = $(value).get(0);
					$(node).replaceWith(newNode);
				}
				if (terms.length > 1)
				{
					processNode(newNode, $.map(terms, function(obj, i) { if (i > 0) { return obj; } }));
				}
			}
		}
		els.each(function(i)
		{
			processNode(this, terms);
		});
	},
	
	ProductComparisonManager: null
});

WebLinc.dialog = function(options, template)
{
	var __scopeHack = this;

	this.options = options;
	this.options.bgiframe = true;
	this.options.zIndex = 6000;
	this.prepareDialog(template);
	this.dialog.dialog(this.options);
	this.dialog.bind
	(
		'dialogopen',
		function(evt, ui)
		{
			var dialogElement = __scopeHack.dialog.closest('.ui-dialog');
			var dialogContentElement = dialogElement.find('.ui-dialog-content');

			dialogElement.appendTo(document.forms[0]);

			dialogContentElement.css('height', 'auto');
			dialogContentElement.css('min-height', 'auto');
			dialogContentElement.css('overflow', 'visible');
			var heightDelta = dialogElement.outerHeight() - dialogContentElement.height();
			var widthDelta = dialogElement.outerWidth() - dialogContentElement.width();
			/*
			var newHeight = (__scopeHack.options.innerHeight ? __scopeHack.options.innerHeight : dialogContentElement.height()) + heightDelta;
			var newWidth = (__scopeHack.options.innerWidth ? __scopeHack.options.innerWidth : dialogContentElement.width()) + widthDelta;
			__scopeHack.dialog.dialog('option', 'height', newHeight);
			__scopeHack.dialog.dialog('option', 'width', newWidth);
			*/
			__scopeHack.dialog.dialog('option', 'height', (__scopeHack.options.innerHeight ? (__scopeHack.options.innerHeight + heightDelta): 'auto'));
			__scopeHack.dialog.dialog('option', 'width', (__scopeHack.options.innerWidth ? (__scopeHack.options.innerWidth + widthDelta) : 'auto'));
			__scopeHack.dialog.dialog('option', 'position', [(($(window).width()/2)-(dialogElement.width()/2)), (($(window).height()/2)-(dialogElement.height()/2))]);
		}
	);
};
WebLinc.dialog.prototype =
{
	options: null,
	dialog: null,
	prepareDialog: function(template)
	{
		if (template)
		{
			this.dialog = $(template);
		}
		else
		{
			var d = document.createElement('div');
			document.body.appendChild(d);
			this.dialog = $(d);
		}
	}
};

WebLinc.productImageDialog = function(options, height, width, template)
{
	options.innerHeight = height;
	options.innerWidth = width;
	WebLinc.dialog.call(this, options, template);
	if (!template)
	{
		this.dialog.append(document.createElement('img'));
	}
}
WebLinc.productImageDialog.prototype = $.extend(WebLinc.dialog.prototype, {});

WebLinc.quickViewDialog = function(options, template)
{
	__scopeHack = this;

	options.resizable = false;
	options.draggable = false;
	WebLinc.dialog.call(this, options, template);
}
WebLinc.quickViewDialog.prototype = $.extend(WebLinc.dialog.prototype, {});

WebLinc.productImageZoomer = function(handles, height, width, template)
{
	var __scopeHack = this;
	this.height = height;
	this.width = width;
	this.dialog = new WebLinc.productImageDialog
	(
		{
			autoOpen: false,
			resizable: false,
			draggable: false
		},
		height,
		width,
		template
	);
	handles.click(function(evt)
	{
		var src = '';
		switch (this.tagName)
		{
			case 'IMG':
				var uri = new WebLinc.utility.uri(this.src);
				var img = WebLinc.app.productMediaFilenameStringToObject(uri.file);
				img.h = __scopeHack.height;
				img.w = __scopeHack.width;
				uri.file = WebLinc.app.productMediaFilenameObjectToString(img);
				src = uri.build();
				break;
			case 'A':
				src = this.href;
				break;
		}
		if (src.length)
		{
			__scopeHack.dialog.dialog.dialog('open');
			__scopeHack.dialog.dialog.find('img').attr('src', src);
		}
		evt.preventDefault();
	});
}
WebLinc.productImageSwapper = function(handles, image, swapHeight, swapWidth, zoom, zoomHeight, zoomWidth)
{
	var __scopeHack = this;
	
	this.image = image;
	this.swapHeight = swapHeight;
	this.swapWidth = swapWidth;
	this.zoom = (zoom.length ? $('#' + zoom) : null);
	this.zoomHeight = zoomHeight;
	this.zoomWidth = zoomWidth;
	
	handles.click(function(evt)
	{
		evt.preventDefault();
		switch (this.tagName)
		{
			case 'IMG':
				var uri = new WebLinc.utility.uri($(this).attr('src'));
				break;
			case 'A':
				var uri = new WebLinc.utility.uri(this.href);
				break;
		}
		var img = WebLinc.app.productMediaFilenameStringToObject(uri.file);
		img.h = __scopeHack.swapHeight;
		img.w = __scopeHack.swapWidth;
		uri.file = WebLinc.app.productMediaFilenameObjectToString(img);
		__scopeHack.image.attr('src', uri.build());
		if (__scopeHack.zoom)
		{
			img.h = __scopeHack.zoomHeight;
			img.w = __scopeHack.zoomWidth;
			uri.file = WebLinc.app.productMediaFilenameObjectToString(img);
			__scopeHack.zoom.attr('href', uri.build());
		}
		return false;
	});
}

WebLinc.ProductComparisonManager = function()
{
	this._cookieName = 'ProductComparisonManager';
	this._dataKey = 'ProductComparisonManager.Product';
	
	this.checkBoxes = [];
	this.containers = [];
	this.productNodes = {};
}
WebLinc.ProductComparisonManager.prototype.GetProducts = function()
{
	var cookie = $.cookies.get(this._cookieName);
	if (!cookie)
		return [];

	cookie = $.evalJSON(cookie);

	return cookie;
}
WebLinc.ProductComparisonManager.prototype.SetProducts = function(products)
{
	if (!products.length)
		$.cookies.del(this._cookieName);
	else
	{
		$.cookies.set(this._cookieName, $.toJSON(products), {hoursToLive: 1});
	}
	for (var i = 0; i < this.checkBoxes.length; i++)
	{
		this.checkBoxes[i].attr('disabled', (products.length < WebLinc.app.SiteSettings.ProductComparisonMaximumAllowed || this.IsProductRegistered(this.checkBoxes[i].data(this._dataKey).ID) ? '' : 'disabled'));
	}
}
WebLinc.ProductComparisonManager.prototype.IsProductRegistered = function(id)
{
	var products = this.GetProducts();
	for (var i = 0; i < products.length; i++)
	{
		if (products[i].ID == id)
			return true;
	}
	return false;
}
WebLinc.ProductComparisonManager.prototype.RegisterCheckBox = function(checkBox, id, name, uri, imageUri)
{
	var __scopeHack = this;
	checkBox.data(this._dataKey, {ID: id, Name: name, Uri: uri, ImageUri: imageUri});
	checkBox.click(function(evt)
	{
		var product = $(this).data(__scopeHack._dataKey);
		if (this.checked)
		{
			__scopeHack.AddProduct
			(
				product.ID,
				product.Name,
				product.Uri,
				product.ImageUri
			);
		}
		else
		{
			__scopeHack.RemoveProduct(product.ID);
		}
	});
	var products = this.GetProducts();
	var found = false;
	for (var i = 0; i < products.length; i++)
	{
		if (products[i].ID == id)
		{
			found = true;
			break;
		}
	}
	checkBox.attr('checked', (found ? 'checked' : ''));
	checkBox.attr('disabled', (products.length < WebLinc.app.SiteSettings.ProductComparisonMaximumAllowed || this.IsProductRegistered(checkBox.data(this._dataKey).ID) ? '' : 'disabled'));
	this.checkBoxes.push(checkBox);
}
WebLinc.ProductComparisonManager.prototype.RegisterContainer = function(container)
{
	container = $(container);
	this.containers.push(this.initializeContainer(container));
}
WebLinc.ProductComparisonManager.prototype.initializeContainer = function(container)
{
	var ul = $(document.createElement('ul'));
	container = {container: container, list: ul};
	var product, li, div, img, a;

	var products = this.GetProducts();
	for (var i = 0; i < products.length; i++)
	{
		this.initializeProduct(products[i], container);
	}
	
	container.container.append(ul);

	return container;
}
WebLinc.ProductComparisonManager.prototype.initializeProduct = function(product, container)
{
	var __scopeHack = this;

	var containers = container ? [container] : this.containers;

	for (var i = 0; i < containers.length; i++)
	{
		li = $(document.createElement('li'));
		li.addClass('product');

		div = $(document.createElement('div'));
		div.addClass('image');
		img = $(document.createElement('img'));
		img.attr('src', product.ImageUri);
		img.attr('alt', product.Name);
		div.append(img);
		li.append(div);
		
		div = $(document.createElement('div'));
		div.addClass('name');
		a = $(document.createElement('a'));
		a.attr('href', product.Uri);
		a.append(product.Name);
		div.append(a);
		li.append(div);
		
		div = $(document.createElement('div'));
		div.addClass('remove');
		a = $(document.createElement('a'));
		a.attr('href','#');
		a.text("Remove");
		a.data(this._dataKey, product);
		a.click(function(e)
		{
			__scopeHack.RemoveProduct($(this).data(__scopeHack._dataKey).ID);
			return false;
		});
		div.append(a);
		li.append(div);
		
		containers[i].list.append(li);
		
		this.productNodes[product.ID] = this.productNodes[product.ID] || [];
		this.productNodes[product.ID].push(li);
	}
}
WebLinc.ProductComparisonManager.prototype.AddProduct = function(id, name, uri, imageUri)
{
	var product = {ID: id, Name: name, Uri: uri, ImageUri: imageUri};
	var products = this.GetProducts();
	for (var i = 0; i < products.length; i++)
	{
		if (products[i].ID == id)
		{
			return;
		}
	}
	this.initializeProduct(product);
	this.SetCheckBoxStates(product.ID, true);
	products.push(product);
	this.SetProducts(products);
}
WebLinc.ProductComparisonManager.prototype.RemoveProduct = function(id)
{
	var productNodes = this.productNodes[id] || [];
	for (var i = 0; i < productNodes.length; i++)
	{
		$(productNodes[i]).remove();
	}
	this.SetCheckBoxStates(id, false);
	var products = $.map(this.GetProducts(), function(product, i)
	{
		if (product.ID != id)
		{
			return product;
		}
	});
	this.SetProducts(products);
}
WebLinc.ProductComparisonManager.prototype.SetCheckBoxStates = function(id, checked)
{
	for (var i = 0; i < this.checkBoxes.length; i++)
	{
		if (this.checkBoxes[i].data(this._dataKey).ID == id)
		{
			this.checkBoxes[i].attr('checked', (checked ? "checked" : ""));
		}
	};
}

WebLinc.utility = {};	
WebLinc.utility.uri = function(uri)
{
	this.protocol = null;
	this.host = null;
	this.port = null;
	this.path = null;
	this.dir = null;
	this.file = null;
	this.queryString = null;

	if (uri)
	{
		this.parse(uri);
	}
};
WebLinc.utility.uri.prototype =
{
	parse: function(uri)
	{
		var re;
		var ret;
		if (uri[0] == '/')
		{
			ret = [null, null, null, uri.substr(1)];
		}
		else
		{
			re = new RegExp("^([^\:]+)\\:\\/\\/([^/]+)\\/?(.*)", "gi");
			var ret = re.exec(uri);
		}
		var tmp;
		if (ret)
		{
			this.protocol = ret[1];
			this.host = ret[2];
			re = new RegExp("([^#]*)#(.*)", "gi");
			tmp = re.exec(ret[3]);
			if (tmp)
			{
				ret[3] = tmp[1];
				this.hash = tmp[2];
			}
		
			re = new RegExp("([^\\?]*)\\??(.*)", "gi");
			tmp = re.exec(ret[3]);
			if (tmp)
			{
				ret[3] = tmp[1];
				this.queryString = tmp[2];
			}
		
			this.path = ret[3];
			tmp = this.path.split(/\//);
			this.dir = tmp.slice(0, (tmp.length - 1)).join('/');
			this.file = tmp.slice(-1)[0];
		}
	},
	build: function()
	{
		var uri = '';
		if (this.protocol && this.host)
		{
			uri += this.protocol + '://' + this.host;
			if (this.port)
			{
				uri += ':' + this.port;
			}
		}
		uri += '/' + this.dir;
		if (this.file)
		{
			uri += '/' + this.file;
		}
		if (this.queryString)
		{
			uri += '?' + this.queryString;
		}
		if (this.hash)
		{
			this.uri += '#' + this.hash;
		}
		return uri;
	}
};