Categories:

Manipulating the XML file

We saw eariler how to retrieve and load into browser memory a XML file using DHTML:

if (window.ActiveXObject){
var xmlDoc = new ActiveXObject("Microsoft.XMLDOM");
xmlDoc.async=false; //Enforce download of XML file first. IE only.
}
else if (document.implementation && document.implementation.createDocument)
var xmlDoc= document.implementation.createDocument("","doc",null);
xmlDoc.load("myfile.xml");

Once a XML file is retrieved, manipulating it is the same as manipulating any web page using the DOM- via the relevant DOM methods. That's the beauty of the DOM- it doesn't discriminate!

- Example: displaying a daily message

An example always get people moving in the right direction. Using the following simple XML file, let's retrieve and display a daily message using DHTML:

dailynews.xml:

<?xml version="1.0"?>
<messages>
<daily>Today is Sunday.</daily>
<daily>Today is Monday.</daily>
<daily>Today is Tuesday.</daily>
<daily>Today is Wednesday.</daily>
<daily>Today is Thursday.</daily>
<daily>Today is Friday.</daily>
<daily>Today is Saturday.</daily>
</messages>

Here we have a basic XML file populated with a different message for each day of the week. Below is the corresponding script to retrieve and display today's message:

The script:

<body>
<div id="container" style="background-color:yellow"></div>

<script>
//load xml file
if (window.ActiveXObject){
var xmlDoc = new ActiveXObject("Microsoft.XMLDOM");
xmlDoc.async=false; //Enforce download of XML file first. IE only.
}
else if (document.implementation && document.implementation.createDocument)
var xmlDoc= document.implementation.createDocument("","doc",null);
if (typeof xmlDoc!="undefined")
xmlDoc.load("dailynews.xml");

//Regular expression used to match any non-whitespace character
var notWhitespace = /\S/

function getdaily(){
//Cache "messages" element of xml file
var msgobj=xmlDoc.getElementsByTagName("messages")[0]

//REMOVE white spaces in XML file. Intended mainly for NS6/Mozilla
for (i=0;i<msgobj.childNodes.length;i++){
if ((msgobj.childNodes[i].nodeType == 3)&&
(!notWhitespace.test(msgobj.childNodes[i].nodeValue))) {
// that is, if it's a whitespace text node
msgobj.removeChild(msgobj.childNodes[i])
i--
}
}

var dateobj=new Date()
var today=dateobj.getDay() //returns 0-6. 0=Sunday

//Get today's message and display it in DIV:
document.getElementById("container").innerHTML=
xmlDoc.getElementsByTagName("messages")[0].childNodes[today].firstChild.nodeValue
}

if (typeof xmlDoc!="undefined"){
if (window.ActiveXObject) //if IE, simply execute script (due to async prop).
getdaily()
else //else if NS6, execute script when XML object has loaded
xmlDoc.onload=getdaily
}
</script>

</body>

Example:

Depending on your familiarity with the DOM, grasping the above script may be difficult at first. First, we create a reference to the <messages> tag of the XML file, via the DOM method document.getElementsByTagName() and storing the result in msgobj.

The code that follows removes all potential whitespace within the tag's containing elements, creating a common document tree across IE and NS6 (thanks to Alex Vincent). You see, in NS6 (and Mozilla), white spaces are considered elements as well (TEXT), while in IE, they are not. To illustrate this, consider the following container:

<parent>
<son>This is my son Timmy</son>
</parent>

In IE, childNodes[0] of the <parent> tag returns <son>, as one might expect. In NS6/Mozilla, however, childNodes[0] actually returns a whitespace, or "blank" space, between the two tags. This blank space is considered a TEXT element. Due to this, childNodes[1] is needed to correctly reference <son> in NS6 and Mozilla. To overcome this diverging treatment of the document by IE and NS, one way is simply to remove all potential whitespaces inside it, as we've done inside our script (note: please see this page for more info on removing white spaces in the DOM). This allows us to then use the same set of indexes for both IE and NS to access the various elements inside the xml file.

Finally, we get today's date (day of the week), and use it as the index of the <daily> element to retrieve and display its text for.