// alert("Module xmlParserLib.js [v20071126] has loaded.");
//  <!-- to use this module, copy following (commented) line to your html file -->
//	<!-- <script src="/{server_alias}/includes/xmlParserLib.js"></script> -->

/* 
	name:	xmlParserLib.js
	dir:	htdocs/includes
	by: 	Iterate Pte Ltd
	func:	this library provides mechanisms to load an XML presentation script, 
			and to receive the name of that script as a URL parameter;
			the 'parseURL' function retrieves all CGI parameters passed in the URL, 
			and then loads them into a new 'keyVals' property in the current window;
			the 'openXMLfile' function is designed to receive the filename, and attempt
			to load the XML file, assuming the browser is capable (IE5 or NS6 or later);
			the loading may be asynchronous, especially if the XML file is very large,
			so we have to wait for an 'onload' event before doing any parsing of the XML;
			once the XML is loaded, we can parse the metadata into a presentation object,
			and parse the events into an array, which is sorted based on start times;
			at this point, the other presentation functions may be launched;
			support for Javascript 1.3 is required
	rev: 	20030906, wmc, created this module 
			20031009, wmc, fixed bug in 'parseXML' to permit nodes with blank entries
			20031011, wmc, added check for null XML object in 'parseXML' function, and added
				more detailed error message for parsing errors (such as ampersand errors) 
			20040204, wmc, fixed bug in 'parseURL' to unescape the search string before parsing
			20040427, wmc, added new function 'parseXMLmanifest' to read the programme manifest;
				deprecated 'parseXML' in favor of 'parseXMLscript', and fixed an error in both
				functions to assure that missing or empty tags don't break the parsing process
			20050530, wmc, modified 'parseXMLmanifest' to capture only integer bitrate values
			20050830, wmc, added validation check for 'callbackStr' parameter in 'openXMLfile';
				added support for different baseURL for Windows Media and RealMedia
			20071124, wmc, fixed syntax error in validation check in 'openXMLfile',
				added support for mediaURL in 'parseXMLscript'
			20071126, wmc, improved 'openXMLfile' to handle function name as callback parameter, 
				fixed inconsistencies in handling of 'parseXMLscript' and 'parseXMLmanifest'
				
		enhancements: 
			- consider using a generic library such as Fleefix (http://js.fleegix.org/download)
				The xmlparse.js library has a simple method for deserializing an XML document to 
				an array of JavaScript objects.
	
	--------------------------------------------------------------------------------
	Following are the common client-side functions defined in this module.
	--------------------------------------------------------------------------------
	parseURL			retrieves CGI params as name/value pairs, stores them in window frame
	openXMLfile			loads an XML file from local drive of URL, invokes handler
	parseXMLscript		parses the presentation script to extract metadata and events list
						(this is a special-purpose function for handling presentation scripts)
	parseXMLmanifest	parses the programme manifest to extract metadata and the show list
						(this is a special-purpose function for handling programme manifests)
	getTagContents	utility to extract string from a tag, returns "" if not found or empty
	safeTryCatch		utility function to protect try-catch syntax from throwing errors in NS4
	countChildren		utility function to count the valid child nodes under some XML node
	createTable			utility function to create a browsable table of XML contents

*/

var global = (top.dataframe ? top.dataframe : this);
var xmlParserLib = this;
var xmlDoc;						// create XML document object
var pObj = new Object;			// create a presentation object
var mObj = new Object;			// create a manifest object
var cgiParams = new Object;		// create an object to contain the CGI parameters

function parseURL (url) {
		// adds a new 'keyVals' property to the window.location object
		// note that this implementation is case-sensitive when retrieving by key
		// for example, where 'name=value', 'keyVals["name"]' returns 'value';
		// you may also access the parmeter pairs in order, as keyVals[0], etc.
	if (!url) return (null);
	var urlSearchStr = url.substring(url.indexOf("?") + 1, url.length);
	if (urlSearchStr == "") return (null);

	cgiParams.keyVals = unescape(urlSearchStr).split('&');
	for (var i = 0, num = cgiParams.keyVals.length; i < num; i++) {
		var pair = cgiParams.keyVals[i].split('=');
		cgiParams.keyVals[pair[0].toLowerCase()] = pair[1];
	}
	return (cgiParams.keyVals);
}

var timerID_01;
var retryCount = 0;
function loadXMLdata () {
	var dataLoadOk = false;
	if (!xmlParserLib) {
		alert("Error - URL parser library not loaded. This application requires \n" +
			 "Internet Explorer 5+ or Netscape 6+ to support reading of URL parameters.")
	} else {
		if (!mObj || !mObj.showListArray) {
			if (retryCount == 0)
				openXMLfile('manifest.xml', "parseXMLmanifest");	// load the manifest
			if (this.retryCount++ < 20) 
				timerID_01 = setTimeout('initPage()', 250);			// come back in 0.25 seconds
			else 
				alert("Error - Could not read manifest XML file.");
		} else {			
			clearTimeout(timerID_01);
			dataLoadOk = true;
		}
	}
	return (dataLoadOk);
}

function openXMLfile (filename, callbackStr) {
	var loadStatus = false;
	var timestamp = (new Date()).getTime();
	
		// perform parameter validation checks (and cleanup callbackStr)
	if (!filename) {
		alert("Error in xmlParserLib.openXMLfile - expects a filename.");
		return (false);
	}
	if (!callbackStr) {
		alert("Error in xmlParserLib.openXMLfile - expects a callbackStr.");
		return (false);
	}
	if (typeof(callbackStr) == "function") {
		if (callbackStr.name) {
			callbackStr = callbackStr.name;																				// convert function name to a string
		} else {
			callbackStr = callbackStr.toString();																	// convert function name to a string
			callbackStr = callbackStr.substr('function '.length);        					// trim off "function "
			callbackStr = callbackStr.substr(0, callbackStr.indexOf('('));        // trim off everything after the function name
		}
	} 
	if (typeof(callbackStr) != "string") {
		alert("Error in xmlParserLib.openXMLfile - expects callback parameter as function name or string.");
		return (false);
	} else if (!eval("window." + callbackStr)) {
		alert("Error in xmlParserLib.openXMLfile - could not find callback function: '" + callbackStr + "'.");
		return (false);
	}
	
		// construct a full URL from the filename supplied (path is relative to location of main window)
	var path = top.location.pathname;
	if (document.all) {
		path = path.replace(/\\/g,"/");
	}
	path = path.substr(0, path.lastIndexOf("/") + 1);
	var url = top.location.protocol + "//" + top.location.hostname + path + filename;
	// alert("got url for presentation script: " + url);
	
		// try reading the file using Navigator 6.x and IE 5.x object model (others not supported)
	if (document.implementation && document.implementation.createDocument) {
		xmlDoc = document.implementation.createDocument("", "", null);
		xmlDoc.onload = eval(callbackStr);		// Netscape loads asynchronously
		var errMsg = "Error in 'xmlParserLib' - the XML file '" + url + "' could not be found, or was invalid.";
		safeTryCatch ("xmlDoc.load('" + url + "?rev=" + timestamp + "');", errMsg);
		loadStatus = true;
	} else if (window.ActiveXObject) {
		xmlDoc = new ActiveXObject("Microsoft.XMLDOM");		
		xmlDoc.async = true;	// if set to 'false', script execution is blocked until load completes
		xmlDoc.onreadystatechange = function () {
			if (xmlDoc.readyState == 4) 
				eval(callbackStr + "()");
		};		// need semicolon, we're declaring a function
		xmlDoc.load(url + "?rev=" + timestamp);		// change revision date to clear any caches
		if (xmlDoc.parseError.errorCode != 0) {
			var strErrMsg = (global.commonLib ? trim(xmlDoc.parseError.srcText) : xmlDoc.parseError.srcText);
			alert("Error in 'xmlParserLib' - the XML file '" + url + "' could not be found, or was invalid.\n" +
				"Reason: " + xmlDoc.parseError.reason + 
				"Line: " + xmlDoc.parseError.line + ", position: " + xmlDoc.parseError.linepos + "\n" +
				"Source text: " + strErrMsg + "\n");
		} else {
			loadStatus = true;
		}
 	} else {
		alert("Error in 'xmlParserLib' - Your browser is not able to read XML, required for this application. " + 
		  "\nPlease try using Internet Explorer 5+ or Netscape 6+.");
	}
	return (loadStatus);
}

function parseXMLscript () {
	var str = "";
	var node;
	var presentation = xmlDoc.documentElement;
	if (presentation == null) return;
	
		// get all the metadata (if a tag is not present, that variable will become an empty string)
	pObj.version = getTagContents(presentation, 'version');
	pObj.playerType = getTagContents(presentation, 'playerType');
	pObj.seriesTitle = getTagContents(presentation, 'seriesTitle');
	pObj.title = getTagContents(presentation, 'title');
	pObj.presenterName = getTagContents(presentation, 'presenterName');
	pObj.description = getTagContents(presentation, 'description');
	pObj.author = getTagContents(presentation, 'author');
	pObj.copyright = getTagContents(presentation, 'copyright');
	pObj.recordingDate = getTagContents(presentation, 'recordingDate');
	pObj.publicationDate = getTagContents(presentation, 'publicationDate');
	pObj.mediaSource = getTagContents(presentation, 'mediaSource');
	pObj.mediaURL = getTagContents(presentation, 'mediaURL');
	pObj.slideSource = getTagContents(presentation, 'slideSource');
	pObj.duration = parseInt(getTagContents(presentation, 'duration'));
	pObj.eventListSize = countChildren(presentation.getElementsByTagName('events')[0]);
	pObj.eventListArray_index_id = 0;
	pObj.eventListArray_index_time = 1;
	pObj.eventListArray_index_filename = 2;
	pObj.eventListArray_index_topic = 3;
	pObj.eventListArray_index_caption = 4;
	// alert(commonLib.peekInside(pObj, 'presentation'));
	
		// get the information for each event
	events = presentation.getElementsByTagName('events').item(0);
	if (events && events.hasChildNodes()) {
		var eventListArray = new Array();
		eventList = events.getElementsByTagName('event');
		for (var i = 0; i < eventList.length; i++) {
			var event = eventList[i];
			eventListArray[i] = new Array();
			eventListArray[i][pObj.eventListArray_index_id] = event.getAttribute('id');
			eventListArray[i][pObj.eventListArray_index_time] = event.getAttribute('startTime');
			if (event.hasChildNodes()) {
				for (var j = 0; j < event.childNodes.length; j++) {
					if (event.childNodes[j].nodeType != 1) continue;	// for Netscape to skip over formatting
					if (!event.childNodes[j].firstChild) continue;		// skip if entry is blank
					switch (event.childNodes[j].nodeName) {
						case "imageSlide":
							eventListArray[i][pObj.eventListArray_index_filename] = event.childNodes[j].firstChild.nodeValue;
							break;
						case "topic":
							eventListArray[i][pObj.eventListArray_index_topic] = event.childNodes[j].firstChild.nodeValue;
							break;
						case "caption":
							eventListArray[i][pObj.eventListArray_index_caption] = event.childNodes[j].firstChild.nodeValue;
							break;
						default:
					}
				}
			}
		}

		if (global.commonLib && global.commonLib.sortArray)
			commonLib.sortArray(eventListArray, 1);
		else 
			alert("Error in 'xmlParserLib' - slide events could not be sorted.")
		pObj.eventListArray = eventListArray;
		pObj.isLoaded = true;
		// alert(commonLib.peekInside(eventListArray, 'eventListArray'));
		// alert(commonLib.peekInside(pObj, 'presentation'));
	} else {
		alert("Error in 'xmlParserLib' - no scripted events were found.");
	}
}

function parseCustomXMLscript () {
	var str = "";
	var node;
	var presentation = xmlDoc.documentElement;
	if (presentation == null) return;
	
		// get all the metadata (if a tag is not present, that variable will become an empty string)
	pObj.version = getTagContents(presentation, 'version');
	pObj.playerType = getTagContents(presentation, 'playerType');
	pObj.seriesTitle = getTagContents(presentation, 'seriesTitle');
	pObj.title = getTagContents(presentation, 'title');
	pObj.venue = getTagContents(presentation, 'venue');
	pObj.presenterName = getTagContents(presentation, 'presenterName');
	pObj.presenterTitle = getTagContents(presentation, 'presenterTitle');
	pObj.description = getTagContents(presentation, 'description');
	pObj.contactInfo = getTagContents(presentation, 'contactInfo');
	pObj.directoryLink = getTagContents(presentation, 'directoryLink');
	pObj.sponsorImage1 = getTagContents(presentation, 'sponsorImage1');
	pObj.sponsorImage2 = getTagContents(presentation, 'sponsorImage2');
	pObj.sponsorLink1 = getTagContents(presentation, 'sponsorLink1');
	pObj.sponsorLink2 = getTagContents(presentation, 'sponsorLink2');
	pObj.moreWebcastsImage1 = getTagContents(presentation, 'moreWebcastsImage1');
	pObj.moreWebcastsImage2 = getTagContents(presentation, 'moreWebcastsImage2');
	pObj.moreWebcastsImage3 = getTagContents(presentation, 'moreWebcastsImage3');
	pObj.moreWebcastsLink1 = getTagContents(presentation, 'moreWebcastsLink1');
	pObj.moreWebcastsLink2 = getTagContents(presentation, 'moreWebcastsLink2');
	pObj.moreWebcastsLink3 = getTagContents(presentation, 'moreWebcastsLink3');
	pObj.moreWebcastsCaption1 = getTagContents(presentation, 'moreWebcastsCaption1');
	pObj.moreWebcastsCaption2 = getTagContents(presentation, 'moreWebcastsCaption2');
	pObj.moreWebcastsCaption3 = getTagContents(presentation, 'moreWebcastsCaption3');
	pObj.author = getTagContents(presentation, 'author');
	pObj.copyright = getTagContents(presentation, 'copyright');
	pObj.recordingDate = getTagContents(presentation, 'recordingDate');
	pObj.publicationDate = getTagContents(presentation, 'publicationDate');
	pObj.mediaSource = getTagContents(presentation, 'mediaSource');
	pObj.mediaURL = getTagContents(presentation, 'mediaURL');
	pObj.mediaURLLow = getTagContents(presentation, 'mediaURLLow');
	pObj.mediaURLAudio = getTagContents(presentation, 'mediaURLAudio');
	pObj.slideSource = getTagContents(presentation, 'slideSource');
	pObj.duration = parseInt(getTagContents(presentation, 'duration'));
	pObj.eventListSize = countChildren(presentation.getElementsByTagName('events')[0]);
	pObj.eventListArray_index_id = 0;
	pObj.eventListArray_index_time = 1;
	pObj.eventListArray_index_filename = 2;
	pObj.eventListArray_index_topic = 3;
	pObj.eventListArray_index_caption = 4;
	// alert(commonLib.peekInside(pObj, 'presentation'));
	
		// get the information for each event
	events = presentation.getElementsByTagName('events').item(0);
	if (events && events.hasChildNodes()) {
		var eventListArray = new Array();
		eventList = events.getElementsByTagName('event');
		for (var i = 0; i < eventList.length; i++) {
			var event = eventList[i];
			eventListArray[i] = new Array();
			eventListArray[i][pObj.eventListArray_index_id] = event.getAttribute('id');
			eventListArray[i][pObj.eventListArray_index_time] = event.getAttribute('startTime');
			if (event.hasChildNodes()) {
				for (var j = 0; j < event.childNodes.length; j++) {
					if (event.childNodes[j].nodeType != 1) continue;	// for Netscape to skip over formatting
					if (!event.childNodes[j].firstChild) continue;		// skip if entry is blank
					switch (event.childNodes[j].nodeName) {
						case "imageSlide":
							eventListArray[i][pObj.eventListArray_index_filename] = event.childNodes[j].firstChild.nodeValue;
							break;
						case "topic":
							eventListArray[i][pObj.eventListArray_index_topic] = event.childNodes[j].firstChild.nodeValue;
							break;
						case "caption":
							eventListArray[i][pObj.eventListArray_index_caption] = event.childNodes[j].firstChild.nodeValue;
							break;
						default:
					}
				}
			}
		}

		if (global.commonLib && global.commonLib.sortArray)
			commonLib.sortArray(eventListArray, 1);
		else 
			alert("Error in 'xmlParserLib' - slide events could not be sorted.")
		pObj.eventListArray = eventListArray;
		pObj.isLoaded = true;
		// alert(commonLib.peekInside(eventListArray, 'eventListArray'));
		// alert(commonLib.peekInside(pObj, 'presentation'));
	}
}

function parseXMLmanifest () {
	var str = "";
	var node;
	var manifest = xmlDoc.documentElement;
	if (manifest == null) return;
	
		// first confirm the version number of the XML data file
	mObj.version = getTagContents(manifest, 'version');
	if (parseFloat(mObj.version) < 0.3) {
		parseXMLmanifest_02();			// use deprecated version
		return;
	}
		// get all the metadata (if a tag is not present, that variable will become an empty string)
	mObj.seriesTitle = getTagContents(manifest, 'seriesTitle');
	mObj.description = getTagContents(manifest, 'description');
	mObj.WM_baseMediaURL = getTagContents(manifest, 'WM_baseMediaURL');
	mObj.RM_baseMediaURL = getTagContents(manifest, 'RM_baseMediaURL');
	mObj.bitrateMinimum = getTagContents(manifest, 'bitrateMinimum');
	mObj.copyright = getTagContents(manifest, 'copyright');
	mObj.copyrightURL = getTagContents(manifest, 'copyrightURL');
	mObj.copyrightYear = getTagContents(manifest, 'copyrightYear');
	mObj.showListSize = countChildren(manifest.getElementsByTagName('shows')[0]);
	mObj.showListArray_index_id = 0;
	mObj.showListArray_index_title = 1;
	mObj.showListArray_index_presenters = 2;
	mObj.showListArray_index_techNotes = 3;
	mObj.showListArray_index_versions = 4;
	mObj.versionListArray_index_id = 0;
	mObj.versionListArray_index_type = 1;
	mObj.versionListArray_index_presentationFile = 2;
	mObj.versionListArray_index_scriptFile = 3;
	mObj.versionListArray_index_mediaFile = 4;
	mObj.versionListArray_index_mediaType = 5;
	mObj.versionListArray_index_bitrate = 6;
	mObj.versionListArray_index_isRestricted = 7;
	// alert("got manifest: " + commonLib.peekInside(mObj, 'manifest'));
	
		// read the entire show list
	shows = manifest.getElementsByTagName('shows').item(0);
	if (shows && shows.hasChildNodes()) {
		var showListArray = new Array();
		showList = shows.getElementsByTagName('show');
			// get the information for each show
		for (var i = 0; i < showList.length; i++) {
			var show = showList[i];
			versions = show.getElementsByTagName('versions').item(0);
			if (versions && versions.hasChildNodes()) {
				showListArray[i] = new Array();
				showListArray[i][mObj.showListArray_index_id] = show.getAttribute('id');
				showListArray[i][mObj.showListArray_index_title] = show.getAttribute('title');
				showListArray[i][mObj.showListArray_index_presenters] = getTagContents(show, 'presenters');
				showListArray[i][mObj.showListArray_index_techNotes] = getTagContents(show, 'techNotes');
				showListArray[i][mObj.showListArray_index_versions] = new Array();
				var versionListArray = showListArray[i][mObj.showListArray_index_versions];
				versionList = versions.getElementsByTagName('version');
					// get the information for each version of each show
				for (var j = 0; j < versionList.length; j++) {
					var version = versionList[j];
					versionListArray[j] = new Array();
					versionListArray[j][mObj.versionListArray_index_id] = version.getAttribute('id');
					versionListArray[j][mObj.versionListArray_index_type] = version.getAttribute('type');
					if (version.hasChildNodes()) {
						for (var k = 0; k < version.childNodes.length; k++) {
							if (version.childNodes[k].nodeType != 1) continue;	// for Netscape to skip over formatting
							if (!version.childNodes[k].firstChild) continue;		// skip if entry is blank
							switch (version.childNodes[k].nodeName) {
								case "presentationFile":
									versionListArray[j][mObj.versionListArray_index_presentationFile] = version.childNodes[k].firstChild.nodeValue;
									break;
								case "scriptFile":
									versionListArray[j][mObj.versionListArray_index_scriptFile] = version.childNodes[k].firstChild.nodeValue;
									break;
								case "mediaFile":
									versionListArray[j][mObj.versionListArray_index_mediaFile] = version.childNodes[k].firstChild.nodeValue;
									break;
								case "mediaType":
									versionListArray[j][mObj.versionListArray_index_mediaType] = version.childNodes[k].firstChild.nodeValue;
									break;
								case "bitrate":
									versionListArray[j][mObj.versionListArray_index_bitrate] = parseInt(version.childNodes[k].firstChild.nodeValue);
									break;
								case "isRestricted":
									versionListArray[j][mObj.versionListArray_index_isRestricted] = version.childNodes[k].firstChild.nodeValue;
									break;
								default:
							}
						}
					}
				}
			}
		}
		mObj.showListArray = showListArray;
		mObj.isLoaded = true;
		// alert(commonLib.peekInside(showListArray, 'showListArray'));
		// alert(commonLib.peekInside(mObj, 'manifest'));
	} else {
		alert("Error in 'xmlParserLib' - no shows were found in the manifest.");
	}
}

function getTagContents (parent, child) {
	var elems = parent.getElementsByTagName(child);
	if (elems && elems[0] && elems[0].firstChild && elems[0].firstChild.nodeValue) 
		return (elems[0].firstChild.nodeValue);
	else
		return ("");
}

function safeTryCatch (functionDeclaration, errMsg) {
		// this is necessary to prevent 'try' syntax errors in NS4 browsers
		// if we simply lock out browsers that don't support JS1.4, we omit IE5
	if (document.implementation && document.implementation.createDocument) 
		eval ("try {" + functionDeclaration + "} catch(err){ if (errMsg) alert(\"" + errMsg + "\");}");
}

function countChildren (node) {
	if (!node) return (0);
	var i = 0;
	var j = 0;
	while (i < node.childNodes.length) 
		if (node.childNodes[i++].nodeType == 1) j++;
	return (j);
}

function createTable (displayElement, pageLocation) {
	if (!document.getElementById(pageLocation)) {
		alert("Error in 'xmlParserLib' - unable to find page location: '" + pageLocation + "'.\t");
	} else {
		var x = xmlDoc.getElementsByTagName(displayElement);
		var newEl = document.createElement('TABLE');
		newEl.setAttribute('cellPadding', 5);
		var tmp = document.createElement('TBODY');
		newEl.appendChild(tmp);
		var row = document.createElement('TR');
		for (j=0; j < x[0].childNodes.length; j++) {
			if (x[0].childNodes[j].nodeType != 1) 
				continue;
			var container = document.createElement('TH');
			var theData = document.createTextNode(x[0].childNodes[j].nodeName);
			container.appendChild(theData);
			row.appendChild(container);
		}
		tmp.appendChild(row);
		for (i = 0; i < x.length; i++) {
			var row = document.createElement('TR');
			for (j=0; j < x[i].childNodes.length; j++) {
				if (x[i].childNodes[j].nodeType != 1) 
					continue;
				var container = document.createElement('TD');
				var theData = document.createTextNode(x[i].childNodes[j].firstChild.nodeValue);
				container.appendChild(theData);
				row.appendChild(container);
			}
			tmp.appendChild(row);
		}
		document.getElementById(pageLocation).appendChild(newEl);
	}
}

	/* DEPRECATED FUNCTIONS */
function parseXML () {
	parseXMLscript ();
}

	// this function is deprecated, and does not support show versions
function parseXMLmanifest_02 () {
	var str = "";
	var node;
	var manifest = xmlDoc.documentElement;
	if (manifest == null) return;
	
		// get all the metadata (if a tag is not present, that variable will become an empty string)
	mObj.version = ((node = manifest.getElementsByTagName('version')[0]) != null ? node.firstChild.nodeValue : "");
	mObj.seriesTitle = ((node = manifest.getElementsByTagName('seriesTitle')[0]) != null ? node.firstChild.nodeValue : "");
	mObj.description = ((node = manifest.getElementsByTagName('description')[0]) != null ? node.firstChild.nodeValue : "");
	mObj.WM_baseMediaURL = ((node = manifest.getElementsByTagName('WM_baseMediaURL')[0]) != null ? node.firstChild.nodeValue : "");
	mObj.RM_baseMediaURL = ((node = manifest.getElementsByTagName('RM_baseMediaURL')[0]) != null ? node.firstChild.nodeValue : "");
	mObj.bitrateMinimum = ((node = manifest.getElementsByTagName('bitrateMinimum')[0]) != null ? node.firstChild.nodeValue : "");
	mObj.showListSize = countChildren(manifest.getElementsByTagName('shows')[0]);
	mObj.showListArray_index_id = 0;
	mObj.showListArray_index_title = 1;
	mObj.showListArray_index_presentationFile = 2;
	mObj.showListArray_index_scriptFile = 3;
	mObj.showListArray_index_mediaFile = 4;
	mObj.showListArray_index_mediaType = 5;
	mObj.showListArray_index_bitrate = 6;
	mObj.showListArray_index_isRestricted = 7;
	// alert(commonLib.peekInside(mObj, 'manifest'));
	
		// get the information for each show
	shows = manifest.getElementsByTagName('shows').item(0);
	if (shows && shows.hasChildNodes()) {
		var showListArray = new Array();
		showList = shows.getElementsByTagName('show');
		for (var i = 0; i < showList.length; i++) {
			var show = showList[i];
			showListArray[i] = new Array();
			showListArray[i][mObj.showListArray_index_id] = show.getAttribute('id');
			showListArray[i][mObj.showListArray_index_title] = show.getAttribute('name');
			if (show.hasChildNodes()) {
				for (var j = 0; j < show.childNodes.length; j++) {
					if (show.childNodes[j].nodeType != 1) continue;	// for Netscape to skip over formatting
					if (!show.childNodes[j].firstChild) continue;		// skip if entry is blank
					switch (show.childNodes[j].nodeName) {
						case "presentationFile":
							showListArray[i][mObj.showListArray_index_presentationFile] = show.childNodes[j].firstChild.nodeValue;
							break;
						case "scriptFile":
							showListArray[i][mObj.showListArray_index_scriptFile] = show.childNodes[j].firstChild.nodeValue;
							break;
						case "mediaFile":
							showListArray[i][mObj.showListArray_index_mediaFile] = show.childNodes[j].firstChild.nodeValue;
							break;
						case "mediaType":
							showListArray[i][mObj.showListArray_index_mediaType] = show.childNodes[j].firstChild.nodeValue;
							break;
						case "bitrate":
							showListArray[i][mObj.showListArray_index_bitrate] = parseInt(show.childNodes[j].firstChild.nodeValue);
							break;
						case "isRestricted":
							showListArray[i][mObj.showListArray_index_isRestricted] = show.childNodes[j].firstChild.nodeValue;
							break;
						default:
					}
				}
			}
		}
		mObj.showListArray = showListArray;
		mObj.isLoaded = true;
		// alert(commonLib.peekInside(showListArray, 'showListArray'));
		// alert(commonLib.peekInside(mObj, 'manifest'));
	} else {
		alert("Error in 'xmlParserLib' - no shows were found in the manifest.");
	}
}

