//xml.dom.js
// Inspired by Nicholas Zakas: Professional Javascript for Web Developers ISBN: 0-7645-7908-8
// Checks XML capability and defines x-browser function XmlDom()

//Global vars:
var isIE=false;
var isW3C=false;
var bTrace=false;//set to false after development done
if (!isNull(window.ActiveXObject))isIE=true	//	IE 5.5+
else if (!isNull(document.implementation) && 
		!isNull(document.implementation.createDocument)) isW3C=true// W3C standard, like NS 6+ or Mozilla browser
else alert('Your browser can\'t open the XML data file. Please use IE 5.5+ or NS 6+ / Firefox / Mozilla.');

function isNull(obj) {
	return(obj==null)||(obj==undefined); //In NN6.x undefined must be checked explicitly
}

function XmlDom() {
	if (isIE) {
		var arrSignatures = [	"MSXML2.DOMDocument.5.0",
						"MSXML2.DOMDocument.4.0",
						"MSXML2.DOMDocument.3.0",
						"MSXML2.DOMDocument",
									"Microsoft.XmlDom"];
		for (var i=0; i < arrSignatures.length; i++) {
			try {
					var oXmlDom = new ActiveXObject(arrSignatures[i]);
					return oXmlDom;
			}
			catch (oError) {/*ignore*/}
		}//end for          
		throw new Error("MSXML is not installed on your system.");
	}
	else if (isW3C) {
        var oXmlDom = document.implementation.createDocument("","",null);
        oXmlDom.parseError = {
	        valueOf: function () { return this.errorCode; },
	        toString: function () { return this.errorCode.toString() }
        };
        oXmlDom.__initError__();
        oXmlDom.addEventListener("load", function () {
            this.__checkForErrors__();
            this.__changeReadyState__(4);
        }, false);
        if(bTrace) alert("End Handling XmlDom as W3C");
        return oXmlDom;
    }
	else {
		throw new Error("Your browser doesn't support an XML DOM object.");
		alert("Your browser doesn't support an XML DOM object.");
	}
} //end function XmlDom

if (isW3C) {
	Document.prototype.readyState = 0;
	Document.prototype.onreadystatechange = null;
	Document.prototype.__changeReadyState__ = function (iReadyState) {
		this.readyState = iReadyState;
		if (typeof this.onreadystatechange == "function") {
			this.onreadystatechange();
		}
	};
	Document.prototype.__initError__ = function () {
		this.parseError.errorCode = 0;
		this.parseError.filepos = -1;
		this.parseError.line = -1;
		this.parseError.linepos = -1;
		this.parseError.reason = null;
		this.parseError.srcText = null;
		this.parseError.url = null;
	};
	Document.prototype.__checkForErrors__ = function () {
		if (this.documentElement.tagName == "parsererror") {
			var reError = />([\s\S]*?)Location:([\s\S]*?)Line Number (\d+), Column (\d+):<sourcetext>([\s\S]*?)(?:\-*\^)/;
			reError.test(this.xml);
			this.parseError.errorCode = -999999;
			this.parseError.reason = RegExp.$1;
			this.parseError.url = RegExp.$2;
			this.parseError.line = parseInt(RegExp.$3);
			this.parseError.linepos = parseInt(RegExp.$4);
			this.parseError.srcText = RegExp.$5;
		}
	};
	Document.prototype.loadXML = function (sXml) {
		this.__initError__();
		this.__changeReadyState__(1);

		var oParser = new DOMParser();
		var oXmlDom = oParser.parseFromString(sXml, "text/xml");

		while (this.firstChild) {
			this.removeChild(this.firstChild);
		}

		for (var i=0; i < oXmlDom.childNodes.length; i++) {
			var oNewNode = this.importNode(oXmlDom.childNodes[i], true);
			this.appendChild(oNewNode);
		}

		this.__checkForErrors__();
		this.__changeReadyState__(4);
	};
	Document.prototype.__load__ = Document.prototype.load;
	Document.prototype.load = function (sURL) {
		this.__initError__();
		this.__changeReadyState__(1);
		this.__load__(sURL);
	};

	Node.prototype.__defineGetter__("xml", function () {
		var oSerializer = new XMLSerializer();
		return oSerializer.serializeToString(this, "text/xml");
	});

} //end if (isW3C)

