/* author: Michael Wasserman */
/* Creation date: 12/19/2005 */

IMGSIZE = new RegExp('(/)med(/)');

document.getElementById('sss').href = "../css/script.css";
window.onload = init;

function picFrameObj (htmlPicFrame, htmlPicHolder, htmlCaption, loadImgMeth, size) {
	var frame = htmlPicFrame;
	var pic = htmlPicHolder;
	var caption = htmlCaption;
	var controlToken = null;
	function loadImgFromUrl (url) {
			loadImgMeth.call(this, url);
		};
	this.getFrame = function () {
			return frame;
		};
	this.getPic = function () {
			return pic;
		};
	this.setCaption = function (htmlText) {
			return caption.innerHTML = htmlText;
		};
	this.getControl = function () {
			return controlToken;
		};
	this.setControl = function (control) {
			return controlToken = control;
		};
	this.resetControl = function () {
			return controlToken = null;
		};
	this.showImg = function (imgObj) {
			if (imgObj && imgObj.constructor) switch (imgObj.constructor) {
				case Function :
					imgObj = imgObj();
					if (imgObj.constructor != imageObj) return false;
				case imageObj :
					loadImgMeth.call(pic, imgObj.getImgUrl(size));
					break;
				default : 
					return false;
			}
			else return false;
			this.setCaption(imgObj.desc);
			return this.makeVisible();
		};
	this.makeVisible = function () { 
			return makeVisible.call(frame); 
		};
	this.hide = function () { 
			return hide.call(frame); 
		};
}

function loadBackgroundImg (url) {
	this.style.backgroundImage = 'url(' + url + ')';
}

function loadImgSrc (url) {
	this.src = url;
}

function imageObj (url,desc) {
	this.img = 	{ 	
					sm : new Image ,
					med : new Image ,
					lg : new Image
				}
	this.desc = desc;
	this.url = url;
	this.fileName = url.fileNameStem();
	this.init = function (size) {
			if (this.img[size]) {
				return this.img[size].src = this.url.replace(IMGSIZE, '$1' + size + '$2');
			} else {
				return null;
			}
		};
	this.getImgUrl = function (size) {
			var img = this.img[size];
			if (img && img.src) {
				return img.src;
			} else {
				return this.init(size);
			}
		};
	return this;
}

function objColl (idProp) {
	var cursor = 0;
	var coll = new Array;
	var hash = idProp && new Object;
	this.length = 0;
	this.add = function (obj) {
			if (hash && obj && obj[idProp]) {
				hash[obj[idProp]] = this.length;
			}
			return this.length = coll.push(obj);
		};
	this.curr = function () {
			return coll[cursor];
		};
	this.next = function () {
			cursor = (cursor + 1) % coll.length;
			return this.curr();
		};
	this.prev = function () {
			cursor = (coll.length + cursor - 1) % coll.length;
			return this.curr();
		};
	this.byId = function(id) {
			if (hash && this.setCurr(hash[id]) != false) {
				return this.curr();
			} else return false;
		};
	this.hasId = function(id) {
			return !hash || hash.hasOwnProperty(id);
		};
	this.getCurr = function() {
			return cursor;
		};
	this.setCurr = function (i) {
			if (typeof i == 'string') switch (i) {
				case 'first' : return cursor = 0;
				case 'prev' : this.prev(); return cursor;
				case 'next' : this.next(); return cursor;
				case 'last' : return arguments.callee(coll.length - 1);
				default : i = parseInt(i);
			}
			if (typeof i == 'number' && i > 0 && i < coll.length) {
				return cursor = i;
			} else {
				return false;
			}
		};
	this.applyToAll = function (methName, argArr) {
			return coll.applyToAll(methName, argArr);
		};
	for (var i = 1; i < arguments.length; i++) this.add(arguments[i]);
}

Array.prototype.applyToAll = function (methName, argArr) {
	if (typeof argArr != 'object' || argArr.constructor != Array) return;
	for (var p in this) {
		if (this[p][methName] && this[p][methName].constructor == Function) {
			this[p][methName].apply(this[p], argArr);
		}
	}
}

function detail (elm) {
	elm.className = elm.className.replace(/brief/,'detail');
}

function brief (elm) {
	elm.className = elm.className.replace(/detail/,'brief');
}

function placeOrder (elm) {
	var catName = document.getElementsByTagName('title').item(0).innerHTML;
	var itemDesc = elm.shortDesc;
	var order = 'mailto:' + ORDERMAIL +
				'&subject=' + encodeURIComponent(ORDERSUBJ + catName) +
				'&body=' + encodeURIComponent(
					ORDERADDR + '\n\n\t' + 
					ORDERBODY + '\n\n\t' + (window.opera ? itemDesc.replace(/&/g, '%26') : itemDesc) + '\n\n\t' +
					ORDERPROM.replace(/<PRICE>/, getText(elm.price)) + '\n\n\t'
				);
	window.location = order;
}

function displayImg (entryElm, dir, size, val) {
	entryElm.picFrames[size].showImg(entryElm.imgColl[dir](val));
	entryElm.controls[size].makeVisible();
}

function makeVisible (elm) {
	elm = elm || this;
	return elm.style.display = 'block';
}

function hide (elm) {
	elm = elm || this;
	return elm.style.display = 'none';
}

function newPicControls (entryElm, size) {
	var controls = newControls();
	var names = { sm : 'Small' , med : 'Medium' , lg : 'Large' };
	with (controls) {
		appendChild(newButElm('button nav normal', 'Prev', [displayImg, [entryElm, 'prev', size]]));
		for (var s in entryElm.picFrames) {
			if (s == 'sm') {
				continue;
			} else if (s == size) {
				appendChild(
					newButElm('button nav normal', 'Close', 
						[
							displayImg, [entryElm, 'curr', 'sm'] ,
							entryElm.picFrames[size].hide , [entryElm.picFrames[size].getFrame()]
						]
					)
				);
			} else {
				appendChild(
					newButElm('button nav normal', names[s], 
						[
							entryElm.picFrames[size].hide , [entryElm.picFrames[size].getFrame()] ,
							displayImg, [entryElm, 'curr', s] ,
							entryElm.imgColl.applyToAll, ['init', [s]]
						]
					)
				);
			}
		}
		appendChild(newButElm('button nav normal', 'Next', [displayImg, [entryElm, 'next', size]]));
	}
	controls.makeVisible = function () {
			var t = entryElm.picFrames[size].getControl();
			if (t == this) return true;
			if (t && t.hide) {
				t.hide();
			} 
			if (makeVisible.call(this)) {
				entryElm.picFrames[size].setControl(this);
			}
		};
	controls.hide = function () {
			if (hide.call(this)) {
				entryElm.picFrames[size].resetControl();
			}
		};
	return controls;
}

function newControls () {
	return newElm('div','controls');
}

function newButElm (className, text, handlerArray) {
	var but = newElm('div', className, text);
	assignEventFunctions(but, 'onclick', handlerArray);
	but.makeVisible = makeVisible;
	but.hide = hide;
	return but;
}

function assignEventFunctions (elm, evt, handlerArray) {
	if (handlerArray.length % 2 > 0) handlerArray.push(null);
	elm[evt] = function () { 
			for (var args, handler, i = 0; i < handlerArray.length; i++) {
				handler = handlerArray[i];
				(args = handlerArray[++i]) ? handler.apply(elm, args) : handler();
			}
		};
	return elm;
}

function newElm (tagName, className, innerHTML) {
	var elm = document.createElement(tagName);
	if (className) elm.className = className;
	if (innerHTML) elm.innerHTML = innerHTML;
	return elm;
}

String.prototype.getHashTarget = function () {
	var a = /#([\w-]+)$/.exec(this.valueOf());
	return a && a[1];
}

String.prototype.firstWord = function () {
	var a = /[\w-]+/.exec(this.valueOf());
	return a && a[0];
}

String.prototype.fileName = function () {
	var a = /[\w.%-]+\W*$/.exec(this.valueOf());
	return a && a[0];
}

String.prototype.fileNameStem = function () {
	return this.valueOf().slice(this.valueOf().lastIndexOf('/') + 1, this.valueOf().lastIndexOf('.'));
}

String.prototype.collapseWS = function () {
	return this.valueOf().match(/\S+/g).join(' ');
}

function getText(elm, excludedClass) {
	var text = '';
	if (elm && elm.hasChildNodes() && (!excludedClass || elm.className.indexOf(excludedClass) < 0)) {
		var node = elm.firstChild;
		do {
			text += node.nodeType == 3 ? node.nodeValue : getText(node, excludedClass);
		} while (node = node.nextSibling);
	}
	return text;
}

function setAnchors (elm, entryElm, picFrameSize) {
	if (elm && elm.hasChildNodes()) {
		var imgId, node = elm.firstChild;
		do {
			if (node.nodeType == 1) {
				if (node.tagName.toLowerCase() == 'a') {
					if (entryElm.imgColl.hasId(imgId = node.href.fileNameStem())) {
						node.onclick = function () { 
								displayImg (entryElm, 'byId', picFrameSize, imgId);
								return false; 
							};
					}
				} else {
					setAnchors(node, entryElm, picFrameSize);
				}
			}
		} while (node = node.nextSibling);
	}
}

function entrySetUp (entryElm, picFrames) {
		if (entryElm.picFrames) return;
		// add picFrame references to entry element
		entryElm.picFrames = new Object;
		var size;
		for (size in picFrames) {
			entryElm.picFrames[size] = picFrames[size];
		}
		// set up small picture frame
		entryElm.picFrames.sm = newElm('div','pics');
		entryElm.picFrames.sm = new picFrameObj(
										entryElm.picFrames.sm ,
										entryElm.picFrames.sm.appendChild(newElm('div','pics')) ,
										entryElm.picFrames.sm.appendChild(newElm('div','caption',' ')) , 
										loadBackgroundImg , 
										'sm'
									);
		entryElm.picFrames.sm.hide = function () { return false; };
		entryElm.picFrames.sm.makeVisible = function () { return false; };
		entryElm.insertBefore(entryElm.picFrames.sm.getFrame(), entryElm.picSm);
		// set up image collection
		entryElm.imgColl = new objColl('fileName');
		var elm;
		while (elm = entryElm.picSm.firstChild) {
			if (elm.tagName && elm.tagName.toLowerCase() == 'a') {
				entryElm.imgColl.add(new imageObj(elm.href, elm.innerHTML));
				if (entryElm.picSm.style.backgroundImage.indexOf(elm.href.fileName()) >= 0) {
					entryElm.imgColl.setCurr('last');
				}
			}
			entryElm.picSm.removeChild(elm);
		}
		entryElm.removeChild(entryElm.picSm);
		// load all small images
		entryElm.imgColl.applyToAll('init', ['sm']);
		// add controls for entry object's pics to picFrames
		for (size in entryElm.picFrames) {
			entryElm.controls[size] = 
				entryElm.picFrames[size].getFrame().insertBefore(
					newPicControls(entryElm, size) ,
					entryElm.picFrames[size].getFrame().firstChild
				);
		}
		// add message re buttons
		entryElm.controls['sm'].insertBefore(
			newElm('p','controlMessage','Use the buttons below to see all ' + entryElm.imgColl.length + ' pictures.'),
			entryElm.controls['sm'].firstChild
		);
		// display current image in small picture frame
		if (entryElm.imgColl.length) displayImg(entryElm, 'curr', 'sm');
		// if there are no pictures, hide the small picture frame
		else return hide.call(entryElm.picFrames.sm.getFrame());
		setAnchors(entryElm, entryElm, 'med');
}

function init () {

	var divs = document.getElementsByTagName('div'),
		shortDescFields = [['author',' '],['itemTitle',' ('],['imprint','). '],['price','.']],
		bookHash = new Object,
		entryElm, elm, i, j, field, n;
		itemNoInc = 0;
	for (i = 0; i < divs.length; i++) {
		if (divs[i].className.firstWord() == 'entry') {
			entryElm = divs[i];
			for (j = 0; j < entryElm.childNodes.length; j++) {
				elm = entryElm.childNodes[j];
				if (elm.nodeType != 1) continue;
				switch (field = elm.className.firstWord()) {
					case 'pics' : entryElm.picSm = elm; break;
					case 'item-no' : 
						if (!itemNoInc && (entryElm.itemNo = elm.name)) break;
						else {
							if (!itemNoInc && n) itemNoInc = parseInt(n);
							elm.innerHTML = (elm.name = entryElm.itemNo = ++itemNoInc) + '.';
							break;
						}
					case 'title' : entryElm.itemTitle = elm; break;
					case 'author' :
					case 'imprint' : 
					case 'price' : entryElm[field] = elm; break;
					default : if (/^h\d$/i.test(elm.tagName)) {
						entryElm.heading = elm;
					}
				}
			}
			if (n = entryElm.itemNo) {
				entryElm.shortElm = newElm('div', 'caption brief', entryElm.shortDesc = 'No. ' + n + '. ');
				if (entryElm.heading) {
					entryElm.shortElm.insertBefore(entryElm.heading.cloneNode(true), entryElm.shortElm.firstChild);
				}
				for (j = 0; j < shortDescFields.length; j++) {
					if (field = entryElm[shortDescFields[j][0]]) {
						entryElm.shortElm.appendChild(field.cloneNode(true));
					}
					entryElm.shortDesc += (getText(field, 'detail') || '—') + shortDescFields[j][1];
				}
				entryElm.shortDesc = entryElm.shortDesc.collapseWS();
				bookHash[n] = entryElm;
			}
			else alert('Book entry without item number!');
		}
	}
	
	// image frames
	var picFrames = new Object;
	picFrames.med = document.getElementsByTagName('body').item(0).appendChild(newElm('div','pics med'));
	picFrames.med = new picFrameObj(
										picFrames.med ,
										picFrames.med.appendChild(newElm('div','pics med')) ,
										picFrames.med.appendChild(newElm('div','caption')) ,
										loadBackgroundImg ,
										'med'
									);
	picFrames.lg = document.getElementsByTagName('body').item(0).appendChild(newElm('div','pics lg'));
	picFrames.lg = new picFrameObj(
										picFrames.lg ,
										picFrames.lg.appendChild(newElm('div','pics lg')).appendChild(newElm('img')) ,
										picFrames.lg.appendChild(newElm('div','caption')) ,
										loadImgSrc ,
										'lg'
									);

	var size;
	for (size in picFrames) {
		elm = picFrames[size].getFrame();
		// pseudo-fixed position for IE < 8
		try {
			if (elm.style.setExpression && !navigator.appVersion.match('MSIE 8.0')) {
				elm.style.position = 'absolute';
				elm.style.setExpression('top', 'eval(' + elm.uniqueID + '.offsetParent.scrollTop) + 10');
			}
		}
		catch(e) { }
	}
	// buttons for details/ordering
	var hashName = document.location.hash && document.location.hash.slice(1);
	var openers = new Array;
	var closers = new Array;
	for (n in bookHash) {
		entryElm = bookHash[n];
		entryElm.controls = new Object;
		entryElm.controls.main = 
			entryElm.insertBefore(
				newControls(), 
				entryElm.picSm
			);
		/*
		entryElm.controls.main.appendChild(
			newButElm('button flex order normal', 'Order...', [placeOrder, [entryElm]])
		);
		*/
		entryElm.opener = entryElm.controls.main.appendChild(
			newButElm('button flex brief normal', 'Detail', 
				[
					entrySetUp, [entryElm, picFrames],
					detail, [entryElm]
				]
			)
		);
		entryElm.closer = entryElm.controls.main.appendChild(
			newButElm('button flex detail normal', 'Brief', [brief, [entryElm]])
		);
		openers.push(entryElm.opener);
		closers.push(entryElm.closer);
	}
	// open linked item
	if (entryElm = bookHash[hashName]) entryElm.opener.onclick();
	
	var masterControls = 			
		document.getElementsByTagName('body').item(0).insertBefore(
			newControls(), 
			bookHash['1']
		);
	masterControls.appendChild(
		newButElm('button flex normal', 'All Details', 
			[
				function () { openers.applyToAll('onclick', []); }, null
			]
		)
	);
	masterControls.appendChild(
		newButElm('button flex normal', 'All Brief', 
			[
				function () { closers.applyToAll('onclick', []); }, null
			]
		)
	);
	if (typeof ieFixes != 'undefined') ieFixes(picFrames);
	
	//all details
	openers.applyToAll('onclick', []);

	// set up bookshelf image map browser
	var bookshelf = document.getElementById('bookshelfImg');
	if (bookshelf) {
		var bookCaption = bookshelf.parentNode.insertBefore(
								newElm('div','bookcaption'),
								bookshelf.nextSibling
							);
		var defaultCaption = bookCaption.appendChild(newElm('div',null,'Browse above with your mouse, or below with your scroll.'));
		var areas = document.getElementsByTagName('area');
		for (i = 0; i < areas.length; i++) {
			n = areas[i].href && areas[i].href.getHashTarget();
			if (n && bookHash[n]) {
				hide(bookCaption.appendChild(bookHash[n].shortElm));
				assignEventFunctions(areas[i], 'onclick' , [ bookHash[n].opener.onclick ]);
				assignEventFunctions(areas[i], 'onmouseover' , 
						[ 
							hide, [defaultCaption] ,
							makeVisible, [bookHash[n].shortElm] 
						]);
				assignEventFunctions(areas[i], 'onmouseout' , 
						[ 
							hide, [bookHash[n].shortElm] , 
							makeVisible, [defaultCaption]
						]);
				areas[i].title = '';
			}
		}
	}
}

var ORDERMAIL = 'books@nostrelivers.com';
var ORDERSUBJ = 'ORDER from ';
var ORDERADDR = 'To Nostre Livers Ltd., Arlington, Virginia:'
var ORDERBODY = 'I would like to purchase from your catalog the following book:';
var ORDERPROM = 'Upon your confirmation of its availability, I will send payment of <PRICE> by (check) (PayPal). I would like the book shipped to me at the following address:';
