编辑工具与测试环境
netbeans 7.2.1
主要用来创建一个php项目,用于编辑php程序。
webstorm 6
主要用来方便javascript代码的编写工作。
xampp 1.8.1
主要需要使用其中的apache服务器。
chrome 26.0.1386.0
用来调试javascript代码
代码
index.html
<html>
<head>
<meta http-equiv='Content-Type' content='text/html; charset=utf-8' />
<title>AJAX with PHP: Quickstart</title>
<link rel=stylesheet href="css/mystyle.css" type="text/css">
<script type="text/javascript" src="js/myutil.js"></script>
<script type="text/javascript" src="js/quickstart.js"></script>
</head>
<body>
<div>
<div id="xmltable">
</div>
<div class="getxml">
<input type="button" οnclick="getXmlFromPhp()" value="获取XML文档" />
</div>
</div>
<div>
<div class="editxml">
<table border="1" class="fancytable" id=table2>
<tr class="headerrow">
<td>CD专辑名</td>
<td>表演者</td>
<td>国家</td>
<td>发行公司</td>
<td>售价</td>
<td>出版年份</td>
</tr>
<tr class="datarowodd" id="editform" name="editform">
<td><input type="text" id="title" name="title"/></td>
<td><input type="text" id="artist" name="artist"/></td>
<td><input type="text" id="country" name="country"/></td>
<td><input type="text" id="company" name="company"/></td>
<td><input type="text" id="price" name="price"/></td>
<td><input type="text" id="year" name="year"/></td>
</tr>
</table>
</div>
<div>
<input type="button" οnclick="appendRecord()" value="添加记录" />
<input type="button" οnclick="deleteRecord()" value="删除记录" />
</div>
</div>
</body>
</html>
js/myutil.js中的函数
函数:createXmlHttpRequestObject()
//获取XMLHttpRequest对象
function createXmlHttpRequestObject(){
var xmlhttp;
//IE
if(window.ActiveXObject){
try{
xmlhttp = new ActiveXObject("Microsoft.XMLHTTP");
}catch (e){
xmlhttp = false;
}
}
//Mozilla或其他browsers
else{
try{
xmlhttp = new XMLHttpRequest();
}catch (e){
xmlhttp = false;
}
}
if (!xmlhttp){
alert("实例化XMLHttpRequest对象出错.");
return xmlhttp;
}
else
return xmlhttp;
}
函数:isnull()
//判断子节点是否为空
function isnull(obj)
{
var nodevalue = "";
if(obj.childNodes[0] != null)
{
nodevalue =obj.childNodes[0].nodeValue;
}
return nodevalue;
}
函数:xml2string(node)
function xml2string(node) {
if (typeof(XMLSerializer) !== 'undefined') {
var serializer = new XMLSerializer();
return serializer.serializeToString(node);
} else if (node.xml) {
return node.xml;
}
}
js/quickstart.js中的函数
变量
//保存XMLHttpRequest对象引用
var xmlHttp = createXmlHttpRequestObject();
//保存鼠标点击的表格table1的当前一行记录对应的HTML元素tr的id属性的值
var currentRecord;
//用于保存XML的DOM对象
var orderDoc;
函数:getDataByid(number)
//根据编号获取数据
function getDataByid(number){
//获取number序号的CD元素节点的所有子元素节点的值
var title =isnull(orderDoc.getElementsByTagName("TITLE")[number]);
var artist =isnull(orderDoc.getElementsByTagName("ARTIST")[number]);
var country =isnull(orderDoc.getElementsByTagName("COUNTRY")[number]);
var company = isnull(orderDoc.getElementsByTagName("COMPANY")[number]);
var price =isnull(orderDoc.getElementsByTagName("PRICE")[number]);
var year =isnull(orderDoc.getElementsByTagName("YEAR")[number]);
var test = number%2;
var std ="";
//根据number的奇偶性添加,表格记录行
if(test == 1) {
std='<tr id='+'"'+ (number+1) +'"' + 'class="datarowodd">' +
'<td>'+(title)+'</td><td>'+(artist)+'</td><td>'+(country)+'</td>' +
'<td>'+(company)+'</td><td>'+(price)+'</td><td>'+(year)+'</td>' +
'</tr>';
}else if(test == 0){
std='<tr id='+'"'+ (number+1) +'"' + 'class="dataroweven">' +
'<td>'+(title)+'</td><td>'+(artist)+'</td><td>'+(country)+'</td>' +
'<td>'+(company)+'</td><td>'+(price)+'</td><td>'+(year)+'</td>' +
'</tr>';
}
return std;
}
函数:getContent()
/*
获取XML文档树中所有CD元素节点,并以HTML表格形式保存
*/
function getContent(){
var stringsss = "";
//获取CD元素节点的个数
var items=orderDoc.getElementsByTagName("CD").length;
//添加HTML表格,以及表格标题行
stringsss+='<table border="1" class="fancytable" id=table1>' +
'<tr class="headerrow">' +
'<td>CD专辑名</td><td>表演者</td><td>国家</td>' +
'<td>发行公司</td><td>售价</td><td>出版年份</td></tr>';
//将每一个CD元素节点内容作为表格的一行记录
for(i=0;i<items;i++){
stringsss+=getDataByid(i);
}
//添加HTML表格结束标签
stringsss+='</table>'
//在HTML文档中的id="xmltable"元素内容中添加stringsss字符串,即表格的HTML代码串。
document.getElementById("xmltable").innerHTML = stringsss;
//为表格的每行添加onclick事件处理方法
addTrEvent();
}
函数:getXmlFromPhp()
/*
构造并发送HTTP请求,请求服务器发送XML文档
*/
function getXmlFromPhp(){
//判断XMLHttpRequest对象是否空闲
if (xmlHttp.readyState == 4 || xmlHttp.readyState == 0)
{
xmlHttp.open("GET", "sendXML.php", true);
//指定处理服务器响应内容的方法
xmlHttp.onreadystatechange = recvServerXml;
//向服务器发送请求
xmlHttp.send(null);
}else{
alert("XMLHttpRequest对象忙!");
setTimeout('getXmlFromPhp()', 1000);
}
}
函数:recvServerXml()
/*
处理服务端发送来的XML文档内容
用来根据接收到的XML文档,生成HTML表格代码
*/
function recvServerXml(){
//当传送完成才继续
if (xmlHttp.readyState == 4){
//状态200表示传送成功完成
if (xmlHttp.status == 200){
//提取从服务器返回的XML文档
xmlResponse = xmlHttp.responseXML;
//将获取的XML文档DOM树结构对象赋值给全局变量orderDoc,以备之后使用
orderDoc = xmlResponse;
//构造HTML表格
getContent();
}
//如果返回一个非200的HTTP状态,则表示出错
else{
alert("在访问服务器时出现错误: " + xmlHttp.statusText);
}
}
}
函数:saveXmlToPhp()
/*
构造并发送HTTP请求,将修改的XML DOM对象发送给服务器端保存
并将新的DOM对象返回,以便更新客户端。
*/
function saveXmlToPhp(){
if (xmlHttp.readyState == 4 || xmlHttp.readyState == 0)
{
xmlHttp.open("POST", "saveXML.php", true);
//将XML DOM对象转换成字符串
var xmlstr = xml2string(orderDoc);
//设置本次请求的结果处理方法
xmlHttp.onreadystatechange = recvServerXml;
//将XML文档序列化字符串作为参数发给服务器
xmlHttp.send(xmlstr);
}else{
alert("XMLHttpRequest对象忙!");
setTimeout('saveXmlToPhp()', 1000);
}
}
函数:appendRecord()
/*
在本地的XML DOM对象中添加一个新的CD子节点
*/
function appendRecord(){
//对空白编辑框的计数
var emptyCount = 0;
//循环检查table2中的文本编辑框,是否为全空,如果全为空则退出appendRecord()
for(var i=0; i<6;i++){
if(document.getElementById("table2").getElementsByTagName("input")[i].value == ""){
emptyCount++;
}
}
if(emptyCount >= 6){
alert("至少有一个记录项不为空");
return;
}
//保存CD元素的所有子元素名,以备循环创建子节点之用
var nodeNameArray = new Array("TITLE","ARTIST","COUNTRY","COMPANY","PRICE","YEAR");
//获取根元素节点
var root = orderDoc.documentElement;
//获取DOM树中CD元素节点的个数
var cdnodeNum = orderDoc.getElementsByTagName("CD").length;
//创建一个新元素节点:CD
var newCdNode = orderDoc.createElement("CD");
//将id属性节点设置为新建的CD元素节点的属性
newCdNode.setAttribute("id",(cdnodeNum+1).toString());
//循环添加CD元素节点的各个子节点
for(var i=0; i< 6; i++){
//依据nodeNameArray数组中字符串的先后顺序创建CD的子元素节点
var cdChildNode = orderDoc.createElement(nodeNameArray[i]);
//创建文本子节点
var textNode = orderDoc.createTextNode(document.getElementById("table2").getElementsByTagName("input")[i].value);
//将文本子节点添加到新建的元素节点中
cdChildNode.appendChild(textNode);
//将新建的元素节点添加为之前创建的CD元素节点中,作为其子元素节点。
newCdNode.appendChild(cdChildNode);
}
//将CD元素节点添加的根元素节点中,作为其子元素节点
root.appendChild(newCdNode);
//请求服务器保存更新后的XML文档内容,并返回新的XML文档
saveXmlToPhp();
}
函数:deleteRecord()
function deleteRecord(){
//获取XML DOM对象中所有CD元素节点
var cdNodeList = orderDoc.getElementsByTagName("CD");
//获取根元素节点
var rootElement = orderDoc.documentElement;
//获取CD元素节点的个数
var cdNodeNum = cdNodeList.length;
//循环找到一个id属性值等于currentRecord的CD元素节点,然后将CD元素节点,从根节点中移除
for(var i=0;i<cdNodeNum;i++){
if(cdNodeList[i].getAttribute("id") == currentRecord){
rootElement.removeChild(cdNodeList[i]);
break;
}
}
//获得移除后的XML DOM对象中的CD元素节点集
cdNodeList = orderDoc.getElementsByTagName("CD");
cdNodeNum = cdNodeList.length;
//更新所有CD元素节点的id属性值
for(var i=0;i<cdNodeNum;i++){
cdNodeList[i].setAttribute("id",(i+1).toString());
}
//请求服务器保存更新后的XML文档,并返回新的XML文档
saveXmlToPhp();
}
函数:addTrEvent()
/*
为table1的每行添加onclick事件处理方法
*/
function addTrEvent()
{
var table = document.getElementById("table1");
for(var i=0;i<table.rows.length;i++){
table.rows[i].onclick = new Function("trFunc(this)")
}
}
函数:trFunc(tr)
/*
点击表格记录行时,要处理的事情
*/
function trFunc(tr){
//记录当前点击的记录行tr元素的属性id的值,以便删除记录使用
if(!tr){
return;
}
currentRecord = tr.getAttribute("id");
if(window.cur){
if(tr.getAttribute("class") == "datarowodd")
window.cur.style.background = "#efefef";
else if(tr.getAttribute("class") == "dataroweven")
window.cur.style.background = "#fff";
}
tr.style.background = "#CCC";
window.cur = tr;
var childs = tr.childNodes;
var items = childs.length;
for(var i=0; i< items; i++){
if(childs[i].hasChildNodes()){
//如果有子节点(文本子节点),就将该子节点的值赋值给文本框
document.getElementById("table2").getElementsByTagName("input")[i].value = childs[i].firstChild.nodeValue;
}else{
//如果没有文本子节点,也就是表格单元内容为空时,设置文本框内容为空
document.getElementById("table2").getElementsByTagName("input")[i].value = "";
}
}
}
sendXML.php
<?php
$xmlString = file_get_contents('cd_data.xml');
header('Content-Type: text/xml;charset=utf-8');
echo $xmlString;
?>
saveXML.php
<?php
$besavexml = file_get_contents("php://input");
$XML = simplexml_load_string($besavexml);
$XML->asXML('cd_data.xml');
header('Content-Type: text/xml;charset=utf-8');
echo $besavexml;
?>
css/mystyle.css
.fancytable{border:1px solid #cccccc; width:100%; border-collapse:collapse;}
.fancytable td{border:1px solid #cccccc; color:#555555;text-align:left; line-height:28px;}
.datarowodd{background-color:#ffffff;}
.dataroweven{ background-color:#efefef;}
.headerrow{ background-color:#0066cc;}
.headerrow td{ color:#ffffff; text-align:center;}
.coolborder{
border:1px solid #0066cc; padding:5px;
-webkit-border-radius: 5px;
-moz-border-radius: 5px;
border-radius: 5px;
}
cd_data.xml
<?xml version="1.0" encoding="utf-8"?>
<CATALOG>
<CD>
<TITLE>Empire Burlesque</TITLE>
<ARTIST>Bob Dylan</ARTIST>
<COUNTRY>USA</COUNTRY>
<COMPANY>Columbia</COMPANY>
<PRICE>10.90</PRICE>
<YEAR>1985</YEAR>
</CD>
<CD>
<TITLE>Hide your heart</TITLE>
<ARTIST>Bonnie Tyler</ARTIST>
<COUNTRY>UK</COUNTRY>
<COMPANY>CBS Records</COMPANY>
<PRICE>9.90</PRICE>
<YEAR>1988</YEAR>
</CD>
<CD>
<TITLE>Greatest Hits</TITLE>
<ARTIST>Dolly Parton</ARTIST>
<COUNTRY>USA</COUNTRY>
<COMPANY>RCA</COMPANY>
<PRICE>9.90</PRICE>
<YEAR>1982</YEAR>
</CD>
<CD>
<TITLE>Still got the blues</TITLE>
<ARTIST>Gary Moore</ARTIST>
<COUNTRY>UK</COUNTRY>
<COMPANY>Virgin records</COMPANY>
<PRICE>10.20</PRICE>
<YEAR>1990</YEAR>
</CD>
<CD>
<TITLE>Eros</TITLE>
<ARTIST>Eros Ramazzotti</ARTIST>
<COUNTRY>EU</COUNTRY>
<COMPANY>BMG</COMPANY>
<PRICE>9.90</PRICE>
<YEAR>1997</YEAR>
</CD>
</CATALOG>
代码测试说明:
假设项目所有文件存放在xmldomtest文件夹中,则xmldomtest下的目录结构大致如下:
将xmldomtest这个文件夹拷贝到xampp的安装目录下的htdocs子目录中,启动apache服务器,然后在chrome浏览器地址栏中输入http://127.0.0.1/xmldomtest/index.html即可。
注意事项
所有文件保存到磁盘全部采用utf-8编码方式保存。
测试截图
本人只是略懂皮毛,刚刚初学,东拼西凑出此文章,其根本目的只作为备忘,如能为和我一样的初学者提供一点借鉴和帮助,就略感欣慰了。