前段时间也写了些关于CE下操作XML文件的帖子,不过大多是套用人家的办法,而且是在EVC平台下,并使用MFC基础类库。这几天亲自自己来动手,直接调用WIN32API,在VS2005下开发CE下XML文件的全面操作,下面是一些心得,供大家参考下。
首先为测试XML文件,保存在SD卡上,文件内容如下:
<?xml version="1.0"?>
<note>
<to>George</to>
<from>John</from>
<heading>Reminder</heading>
<body>Don't forget the meeting!</body>
</note>
接着创建项目工程:
在新建项目对话框中,选择,智能设备->Win32智能设备项目,输入名称***XML_WriteOrRead***,一路确定下去,系统帮你也自动生成不少代码,其实也就是窗体创建的过程代码。注册窗口,创建窗口,消息循环,完成后编译一下就出来了个带菜单栏的白色窗体。
下面介绍下头文件:(主要引用到Msxml2.h,然后宏定义几个按钮ID,以及XMLdom 树相关节点,节点列表,根节点等几个全局变量,再声明几个处理XML文件函数,包括连接,读,写,保存,删除,修改)
XML_WriteOrRead.h
#pragma once
#ifdef STANDARDSHELL_UI_MODEL
#include "resource.h"
#endif
#include "Afxwin.h"
#include <windows.h>
#include <commctrl.h>
#include "Msxml2.h"
#define IDC_BTNLink 100
#define IDC_BTNtest 101
#define IDC_BTNWrite 102
#define IDC_BTNDelete 103
#define IDC_BTNReplace 104
//
IXMLDOMDocument *pDoc = NULL;
IXMLDOMNodeList *pNodelist = NULL;
IXMLDOMNode *pNode = NULL;
IXMLDOMElement *pRootElement = NULL;
//XML Fuction
//打开XML文件
BOOL LoadMyXml(CString stXmlFile);
//读取XML文件节点
void ReadNode(LPCTSTR szURL);
//关闭文件入口
void CloseXML(void);
//向XML文件中写入节点
void WriteNode(LPCTSTR szURL);
//删除XML文件中的某个节点
void DeleteNode(LPCTSTR szPath,LPCTSTR szURL,int i);
//修改xml中的节点
void ReplaceNode(LPCTSTR szURL,CString szText,int i);
//保存修改后的XML文件
void SaveXML(LPCTSTR szPath);
接着在XML_WriteOrRead.cpp书写函数实现以及调用
//
///函数名字:LoadMyXml
//功能描述:链接设备上的XML文件
//输入:设备上XML文件的路径
//输出值:TRUE或则FLASE
//修改备注:蒋新星 2009-9-22
//
BOOL LoadMyXml(CString stXmlFile)
{
if (SUCCEEDED(CoInitializeEx(NULL,COINIT_MULTITHREADED)))
{
if (SUCCEEDED(CoCreateInstance(CLSID_DOMDocument,NULL,CLSCTX_INPROC_SERVER | CLSCTX_LOCAL_SERVER,IID_IXMLDOMDocument,(void**)&pDoc)))
{
VARIANT vFile;
vFile.vt = VT_BSTR ;
VARIANT_BOOL vBool;
vFile.bstrVal = SysAllocString(stXmlFile);//.XML文件名
pDoc->load(vFile,&vBool);//加载XML文件
::AfxMessageBox(_T("文件载入成功!!"));
if(vBool != VARIANT_TRUE)
return 0 ;
}
}
return TRUE;
}
//
///函数名字:ReadNode
//功能描述:按路径读取文件节点及其属性值
//输入:设备上XML文件节点路径
//输出值:无
//修改备注:蒋新星 2009-9-23
//
void ReadNode(LPCTSTR szURL)
{
IXMLDOMNode *spXMLNode = NULL;
HRESULT hr;
BSTR bsparentxml;
hr = pDoc->selectSingleNode((TCHAR *)szURL,&spXMLNode);
if( FAILED( hr ) ) // Empty xml file
{
MessageBox( NULL, L"Node is not found!", L"Error finding XML", MB_ICONSTOP );
}
hr = spXMLNode->get_nodeName(&bsparentxml); //获取双亲节点
MessageBox(NULL,CString(bsparentxml),_T("开始获取按钮!"),MB_OK);
//获取子节点的个数
long value;
spXMLNode->get_childNodes(&pNodelist);
spXMLNode->Release();
pNodelist->get_length(&value);
//s.Format(_T("%d"),value);
for (int i=0;i<value;i++)
{
BSTR bsxml1;
BSTR text;
pNodelist->get_item(i,&spXMLNode);
spXMLNode->get_nodeName(&bsxml1);
spXMLNode->get_text(&text);
MessageBox(NULL,CString(bsxml1),_T("开始获取按钮!"),MB_OK);
MessageBox(NULL,CString(text),_T("开始获取按钮!"),MB_OK);
}
}
//
///函数名字:CloseXML
//功能描述:释放内存
//输入:无
//输出值:无
//修改备注:蒋新星 2009-9-23
//
void CloseXML(void)
{
pNodelist->Release();
pNode->Release();
pDoc->Release();
CoUninitialize();
}
//
///函数名字:WriteNode
//功能描述:写入节点
//输入:写入XML文件的节点位置
//输出值:无
//修改备注:蒋新星 2009-9-24
//
void WriteNode(LPCTSTR szURL)
{
IXMLDOMNode *parentNode=NULL;
IXMLDOMNode *newRootNode=NULL;
IXMLDOMNode *childNode=NULL;
IXMLDOMNode *newChildNode=NULL;
IXMLDOMNode *textNode=NULL;
IXMLDOMText *nodeText=NULL;
//
HRESULT hr;
//BSTR bsparentxml;
hr = pDoc->selectSingleNode((TCHAR *)szURL,&parentNode);
if( FAILED( hr ) ) // Empty xml file
{
MessageBox( NULL, L"Node is not found!", L"Error finding XML", MB_ICONSTOP );
}
//hr = parentNode->get_nodeName(&bsparentxml); //获取双亲节点
//
pDoc->createNode(CComVariant(NODE_ELEMENT),CComBSTR("No"),L"",&newRootNode);
pDoc->createNode(CComVariant(NODE_ELEMENT),CComBSTR("Date"),L"",&newChildNode);
pDoc->createTextNode(CComBSTR(_T("2009-09-24")),&nodeText);
newRootNode->appendChild(newChildNode,&childNode);
childNode->appendChild(nodeText,&textNode);
parentNode->appendChild(newRootNode,&childNode);
::AfxMessageBox(_T("节点写入成功!!"));
}
//
///函数名字:SaveXML
//功能描述:保存修改后的XML文件
//输入:保存文件的路径
//输出值:无
//修改备注:蒋新星 2009-9-24
//
void SaveXML(LPCTSTR szPath)
{
HRESULT hr;
hr = pDoc->save(CComVariant(szPath));
::AfxMessageBox(_T("文件保存成功"));
CloseXML();
}
//
///函数名字:DeleteNode
//功能描述:删除指定位置上的节点
//输入:szPath:删除节点的父亲节点路径;szURL:删除节点的路径;i:删除节点在同级节点列表中的索引号
//输出值:无
//修改备注:蒋新星 2009-9-25
//
void DeleteNode(LPCTSTR szPath,LPCTSTR szURL,int i)
{
IXMLDOMNode *parentNode=NULL;
IXMLDOMNode *childNode = NULL;
IXMLDOMNode *oldNode = NULL;
HRESULT hr;
hr = pDoc->selectSingleNode((TCHAR *)szPath,&parentNode);
hr = pDoc->selectNodes((TCHAR *)szURL,&pNodelist);
long count = 0;
pNodelist->get_length(&count);
CString s;
s.Format(_T("%d"),count);
::AfxMessageBox(s);
pNodelist->get_item(i,&childNode);
parentNode->removeChild(childNode,&oldNode);
}
//
///函数名字:ReplaceNode
//功能描述:删除指定位置上的节点
//输入:szPath:删除节点的父亲节点路径;szURL:删除节点的路径;i:删除节点在同级节点列表中的索引号
//输出值:无
//修改备注:蒋新星 2009-9-25
//
void ReplaceNode(LPCTSTR szURL,CString szText,int i)
{
IXMLDOMNode *spXMLNode = NULL;
HRESULT hr;
BSTR bsparentxml,newText;
newText=szText.AllocSysString();
hr = pDoc->selectSingleNode((TCHAR *)szURL,&spXMLNode);
if( FAILED( hr ) ) // Empty xml file
{
MessageBox( NULL, L"Node is not found!", L"Error finding XML", MB_ICONSTOP );
}
hr = spXMLNode->get_nodeName(&bsparentxml); //获取双亲节点
//获取子节点的个数
long value;
spXMLNode->get_childNodes(&pNodelist);
spXMLNode->Release();
pNodelist->get_length(&value);
//s.Format(_T("%d"),value);
BSTR bsxml1;
BSTR text;
pNodelist->get_item(i,&spXMLNode);
spXMLNode->get_nodeName(&bsxml1);
spXMLNode->put_text(newText);
spXMLNode->get_text(&text);
MessageBox(NULL,CString(bsxml1),_T("开始获取按钮!"),MB_OK);
MessageBox(NULL,CString(text),_T("开始获取按钮!"),MB_OK);
}
///
功能实现部分
LRESULT CALLBACK WndProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam)
{
--......
switch (message)
{
case WM_COMMAND:
wmId = LOWORD(wParam);
wmEvent = HIWORD(wParam);
if (wmId==IDC_BTNLink && wmEvent == BN_CLICKED) //读XML文件操作
{
LoadMyXml(L"//SDMMC//Test1.xml");
ReadNode(L"/note");
CloseXML();
}
if (wmId==IDC_BTNWrite && wmEvent == BN_CLICKED)//写XML文件操作
{
LoadMyXml(L"//SDMMC//Test.xml");
WriteNode(L"/note/to");
SaveXML(L"//SDMMC//Test1.xml");
}
if (wmId==IDC_BTNDelete && wmEvent == BN_CLICKED)//删除XML文件节点的操作
{
LoadMyXml(L"//SDMMC//Test1.xml");
DeleteNode(L"/note/to",L"/note/to/No",0);
SaveXML(L"//SDMMC//Test2.xml");
}
if (wmId==IDC_BTNReplace && wmEvent == BN_CLICKED)//修改节点的操作
{
LoadMyXml(L"//SDMMC//Test.xml");
ReplaceNode(L"/note",_T("蒋新星"),1);
SaveXML(L"//SDMMC//Test3.xml");
}
}
--......
}