/**
**************************
* Popup für Bildanzeigen *
**************************
*
* Version 2.1 (2011/03/13)
*
* Diese Bibliothek erzeugt ein Javascript-Objekt (jsPopup), welches inline-Popups für
* Bildvollansichten erzeugt.
*
* Die Benutzung des jsPopup-Objektes ist sehr einfach. Da sich das Script basierend auf einer
* hier einzustellenden CSS-Klasse die Link-Elemente dynamisch aus einem beliebigen Eltern-
* Element holt und ihnen ein onclick-Event zuweist, braucht es im HTML- Quelltext lediglich
* folgende Struktur (<element> steht stellvertretend für Elemente wie <p>, <div>, <span> usw.):
*
* <element class="bildergalerie">
* <a href="pfad/img.jpg"><img src="pfad/tn_img.jpg" alt="Beschreibung" /></a>
* </element>
*
* Sollte der Hyperlink auf keine Bilddatei verweisen, sprich: Wenn die Zieladresse nicht
* auf "gif", "jpg", "jpeg" oder "png" endet (Groß-/Kleinschreibung egal), dann wird keine
* Popup-Funktionalität für diesen Link eingerichtet.
*
* Die Vollansicht wird als Bildunterschrift den Wert aus dem ohnehin zwingend erforderlichen
* alt-Attribut verwenden.
*
* Neu in Version 2 ist der Blättermechanismus, mit dem man vor- und zurückblättern kann, wenn es
* in einer Galerie mehr als einen Bilderlink gibt.
*
* Diese Bibliothek unterliegt der LGPL!
*
* SOFTWARE LICENSE: LGPL
* (C) 2006-2010 Felix Riesterer
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
* License as published by the Free Software Foundation; either
* version 2.1 of the License, or (at your option) any later version.
* 
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
* Lesser General Public License for more details.
* 
* You should have received a copy of the GNU Lesser General Public
* License along with this library; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301  USA
*
*
* erstellt von Felix Riesterer (Felix.Riesterer@gmx.net)
*/


var jsPopup = {

	triggerClass : "bildergalerie",

	oversize : false,

	lastMouseCoords : { x : 0, y : 0 },

	galleries : [],

	init : function () {
		var scripts = document.getElementsByTagName("script"),
			t = this,
			oldWinOnLoad = window.onload,
			css, i, setting, _setting, v, _v;

		window.onload = function () {
			if (typeof (oldWinOnLoad) == "function")
				oldWinOnLoad();

			t.initPopupBox();
		};

		for (i = 0; i < scripts.length; i++) {
			if (scripts[i].src && scripts[i].src.match(/\/js_popup.js\b/i)) {
				t.baseURL = scripts[i].src.replace(/\/js_popup\.js.*/, "/");
			}
		}

		document.getElementsByTagName("head")[0].appendChild(t.createHTMLElement({
			tagName : "link",
			rel : "stylesheet",
			media : "screen, projection",
			href : t.baseURL + "js_popup.css"
		}));
	},

	initPopupBox : function () {
		var allElements = document.getElementsByTagName("*"),
			t = this,
			oldDocOnMouseMove = document.onmousemove,
			oldDocOnClick = document.onclick,
			oldWinOnResize = window.onresize,
			i, a, links, test;

		// alle Galerien ermitteln
		for (i = 0; i < allElements.length; i++) {
			if (allElements[i].className.indexOf(t.triggerClass) != -1) {
				/* Das Class-Attribut eines HTML-Elementes kann mehrere Klassennamen enthalten,
				die alle durch Leerzeichen getrennt sind. Diese Leerzeichen werden nun durch
				Kommata ersetzt, ebenso am Anfang und Ende je ein Komma hinzugefügt, sodass der
				gesuchte Klassenname zwischen zwei Kommas stehen muss, wenn er denn für dieses
				Element existiert. */
				test = "," + allElements[i].className.split(" ").join(",") + ",";

				if (test.indexOf("," + t.triggerClass + ",") != -1)
					t.galleries.push({elm : allElements[i]});
			}
		}

		for (i = 0; i < t.galleries.length; i++) {
			// alle Bilder-Links eines gefundenen Elternelements mit der Popup-Funktion erweitern
			links = t.galleries[i].elm.getElementsByTagName("a");

			for (a = 0; a < links.length; a++) {
				// jedes Link-Element auf enthaltendes Bild überprüfen
				if (links[a].getElementsByTagName("img")[0]
					&& links[a].href.match(/\.(gif|jpg|jpeg|png)\b/i)
				) {
					// Popup-Funktion anbringen
					links[a].onclick = function () {
						return t.preload(this);
					};

					if (!t.galleries[i].imageLinks) {
						t.galleries[i].imageLinks = new Array();
					}

					t.galleries[i].imageLinks.push(links[a]);
				}
			}
		}

		if (t.galleries.length) {
			document.onclick = function (e) {
				if (typeof(oldDocOnClick) == "function") {
					oldDocOnClick(e);
				}

				e = e || window.event;
				t.lastHoverElement = e.srcElement || e.target;

				return t.hover(e);
			};

			document.onmousemove = function (e) {
				if (typeof(oldDocOnMouseMove) == "function") {
					oldDocOnMouseMove(e);
				}

				e = e || window.event;
				t.lastMouseCoords.x = e.clientX;
				t.lastMouseCoords.y = e.clientY;

				if (typeof(t.viewPort.scrollLeft) == "number") {
					t.lastMouseCoords.x += t.viewPort.scrollLeft;
					t.lastMouseCoords.y +=  t.viewPort.scrollTop;
				}

				t.lastHoverElement = e.srcElement || e.target;

				return t.hover(e);
			};

			window.onresize = function (e) {
				if (typeof(oldWinOnResize) == "function") {
					oldWinOnResize(e);
				}

				return t.display();
			};

			t.viewPort = (document.compatMode && document.compatMode == "CSS1Compat") ?
				document.documentElement : document.body || null;

			t.background = t.createHTMLElement({
				tagName : "div",
				id : "js-popup-background"
			});
			document.body.appendChild(t.background);

			t.box = t.createHTMLElement({
				tagName : "div",
				id : "js-popup-box"
			});
			document.body.appendChild(t.box);

			t.image = t.createHTMLElement({
				tagName : "img",
				id : "js-popup-image"
			});
			t.box.appendChild(t.image);

			t.caption = document.createTextNode("...");
			t.box.appendChild(t.caption);

			t.closeIcon = t.createHTMLElement({
				tagName : "span",
				id : "js-popup-close"
			});
			t.box.appendChild(t.closeIcon);

			t.resizeIcon = t.createHTMLElement({
				tagName : "span",
				id : "js-popup-resize"
			});
			t.box.appendChild(t.resizeIcon);

			t.nextIcon = t.createHTMLElement({
				tagName : "span",
				id : "js-popup-next"
			});
			t.box.appendChild(t.nextIcon);

			t.prevIcon = t.createHTMLElement({
				tagName : "span",
				id : "js-popup-prev"
			});
			t.box.appendChild(t.prevIcon);

			t.waitIcon = t.createHTMLElement({
				tagName : "span",
				id : "js-popup-wait"
			});
			t.box.appendChild(t.waitIcon);
		}
	},

	preload : function (linkObj) {
		var t = this,
			caption, g, i;

		// IE
		if (window.event) {
			window.event.returnValue = false;
		}

		// Resized-Darstellung und Popup-Abmessungen für die Ladeanzeige setzen
		t.preloadImage = new Image();
		t.preloadImage.src = linkObj.href;

		t.box.style.width = "150px";
		t.box.style.height = "150px";
		t.image.style.display = "none";
		t.image.src = "";
		t.image.height = 0;
		t.image.width = 0;
		t.waitIcon.style.display = "block";
		t.resizeIcon.style.display = "";
		t.caption.data = "";

		t.center();

		// passendes Galerie-Objekt finden und dem box-Objekt zuordnen
		t.currentGallery = null;
		t.galleryIndex = null;

		for (g = 0; g < t.galleries.length; g++) {
			for (i = 0; i < t.galleries[g].imageLinks.length; i++) {
				if (t.galleries[g].imageLinks[i] === linkObj) {
					t.currentGallery = t.galleries[g];
					t.galleryIndex = i;
				}
			}
		}

		// Bildunterschrift für die Vollansicht vorbereiten
		caption = linkObj.getElementsByTagName("img")[0].getAttribute("alt");
		t.preloadImage.caption = (caption && caption != "") ? caption : "...";

		if (t.preloadImage.width > 0) {
			// Bild schon im Cache geladen? -> Sofort anzeigen
			t.display();
		} else {
			// Eventhandler setzen, damit nach dem Laden eine Anzeige kommt
			t.preloadImage.onload = function () { t.display(); };
			t.preloadImage.onerror = function () { t.display(); };
			t.hover({type:0});
		}

		// Link-Ausführung verhindern
		return false;
	},

	display : function () {
		var t = this,
			maxHeight = t.viewPort.clientHeight - 30,
			maxWidth = t.viewPort.clientWidth - 30,
			ratio = t.preloadImage.width / t.preloadImage.height,
			scaled;

		t.waitIcon.style.display = "";
		t.image.src = t.preloadImage.src;
		t.image.width = t.preloadImage.width;
		t.image.height = t.preloadImage.height;
		t.image.style.display = "";
		t.caption.data = t.preloadImage.caption;
		t.box.style.height = "";
		t.box.style.width = "";

		if (t.image.width > maxWidth) {
			t.image.width = maxWidth;
			t.image.height = Math.floor(maxWidth / ratio);
		}

		if (t.image.height > maxHeight) {
			t.image.height = maxHeight;
			t.image.width = Math.floor(maxHeight * ratio);
		}

		if (t.image.width != t.preloadImage.width
			|| t.image.height != t.preloadImage.height
		) {
			// Bild wird verkleinert angezeigt?
			if (t.image.width < t.preloadImage.width) {
				t.resizeIcon.className = "small";
			} else {
				t.resizeIcon.className = "small";
			}

			t.resizeIcon.style.display = "block";

		} else {
			t.resizeIcon.style.display = "";
			t.resizeIcon.className = "";
		}

		return t.center();
	},

	center : function () {
		var t = this,
			top, left;

		// Background vollen Viewport ausfüllen lassen
		t.background.style.width = t.viewPort.scrollWidth + "px";
		t.background.style.height = t.viewPort.scrollHeight + "px";
		t.background.style.display = "block";

		// zentrierte Position der Box errechnen
		left = t.viewPort.scrollLeft + Math.floor(
			(t.viewPort.clientWidth - t.box.offsetWidth) / 2
		);

		top = t.viewPort.scrollTop + Math.floor(
			(t.viewPort.clientHeight - t.box.offsetHeight) / 2
		);

		t.box.style.left = (left > 0 ? left : 0) + "px";
		t.box.style.top = (top > 0 ? top : 0) + "px";
		t.box.style.display = "block";

		return t.hover({type:0});
	},

	hide : function () {
		var t = this;

		t.box.style.display = "";
		t.background.style.display = "";
	},

	hover : function (e) {
		var t = this,
			dir, next;

		if (e.type == "click"
			&& (t.lastHoverElement == t.background || t.lastHoverElement == t.closeIcon)
		) {
			t.hide();
		}

		if (e.type == "click"
			&& t.lastHoverElement == t.resizeIcon
		) {
			if (t.image.width < t.preloadImage.width
				|| t.image.height < t.preloadImage.height
			) {
				t.resizeIcon.className = "full";
				t.image.height = t.preloadImage.height;
				t.image.width = t.preloadImage.width;

				t.center();

			} else {
				t.display();
			}
		}

		if ((t.lastHoverElement == t.box || t.lastHoverElement.parentNode == t.box)
			&& t.currentGallery
			&& t.currentGallery.imageLinks.length > 1
		) {
			// Hover-Bild anzeigen?
			t.nextIcon.style.display = "";
			t.prevIcon.style.display = "";
			t.image.className = "";

			// Ja. Nächstes oder vorheriges?
			dir = t.lastMouseCoords.x;
			dir -= t.box.offsetLeft;
			next = t.galleryIndex + (dir > t.box.offsetWidth / 2 ? 1 : -1);

			if (next >= 0 && next < t.galleryIndex) {
				t.prevIcon.style.display = "block";
				t.prevIcon.style.top = Math.floor(
					(t.image.height - t.prevIcon.offsetHeight) / 2
				) + "px";
				t.image.className = "change";

				if (e.type == "click"
					&& (t.lastHoverElement == t.box
						|| t.lastHoverElement == t.image
						|| t.lastHoverElement == t.prevIcon
					)
				) {
					t.preload(t.currentGallery.imageLinks[next]);
				}
			}

			if (next
				&& next < t.currentGallery.imageLinks.length
				&& next > t.galleryIndex
			) {
				t.nextIcon.style.display = "block";
				t.nextIcon.style.top = Math.floor(
					(t.image.height - t.nextIcon.offsetHeight) / 2
				) + "px";
				t.image.className = "change";

				if (e.type == "click"
					&& (t.lastHoverElement == t.box
						|| t.lastHoverElement == t.image
						|| t.lastHoverElement == t.nextIcon
					)
				) {
					t.preload(t.currentGallery.imageLinks[next]);
				}
			}
		}

		if (t.image.style.display == "none"
			|| (t.lastHoverElement != t.box && t.lastHoverElement.parentNode != t.box)
		) {
			t.prevIcon.style.display = "";
			t.nextIcon.style.display = "";
		}

		return true;
	},

	createHTMLElement : function (params) {
		var el, p;
		/* "params" ist ein Objekt, das folgende Eigenschaften haben kann:
			{ 	tagName : "p", // z.B. für <p>
				text : "Textinhalt" // als Text-ChildNode des Elements
				... // weitere (native) Eigenschaften des HTML-Elementobjekts (z.B. id, className etc.)
			} */
		if (params.tagName && params.tagName.match(/[a-z]/)) {
			el = document.createElement(params.tagName);

			for (p in params) {
				if (p.match(/^text/i)) {
					el.appendChild(document.createTextNode(params[p]));
				} else {
					if (!p.match(/^tagname$/i)) {
						el[p] = params[p];
					}
				}
			}
		}

		return el;
	}
};


// Die Popup-Funktionalität initialisieren
jsPopup.init();
