/* 创建 XML 文档*/
/* 创建XML文档*/
/* <?xml version="1.0" encoding="utf-8"?>
<data>
<node name="QDW" type="SY">
<node name="QDW" type="SY">
<node name="ZS" type="B">
<node name="ZS" type="B">
<node name="WW" type="D" />
<group name="WW" type="D">
<node name="ZL" type="E">
<node name="SQ" type="F">
<node name="ZB" type="G">
</group>
<node name="WJ" type="H">
<node name="ZS" type="I">
<foo>
<bar>
<one>
<two>
<two name="ZS" type="B" />
<two name="ZC" type="C" />
</two>
</one>
</bar>
</foo>
</data> */
/* XML结点树*/
/* ?xml
|
data
|
node - node - node - node - node - group - node - node - foo
| |
node - node - node bar
|
one
|
two
|
two - two
测试代码:
/* main.c */
#include<string.h>
#include<stdio.h>
#include<stdlib.h>
#ifdef __cplusplus
extern "C" {
#endif
#include<mxml-private.h>
int main()
{
FILE *fp;
FILE *fptra;
char Buff[2018] = {0};
char *name_str;
char *type_str;
mxml_node_t *tree;
mxml_node_t *node;
mxml_node_t *pxml; /* <?xml ... ?> */
mxml_node_t *pdata; /* <data> */
mxml_node_t *pnode; /* <node> */
mxml_node_t *pgroup; /* <group> */
/* 创建一个新的xml文档的版本号 */
pxml = mxmlNewXML("1.0");
/* 创建节点data */
pdata = mxmlNewElement(pxml, "data");
/* 在data节点下创建子节点node */
pnode = mxmlNewElement(pdata, "node");
name_str = "qdw";
type_str = "sydq";
mxmlElementSetAttr(pnode, "name", name_str);
mxmlElementSetAttr(pnode, "type", type_str);
// mxmlElementSetAttr(pnode, "name", "QDW");
// mxmlElementSetAttr(pnode, "type", "SY");
mxmlLoadString(pdata, "<node name='QDW' type='SY'></node>",MXML_NO_CALLBACK);
/* 在data节点下创建子节点node */
pnode = mxmlNewElement(pdata, "node");
mxmlElementSetAttr(pnode, "name", "ZS");
mxmlElementSetAttr(pnode, "type", "B");
mxmlLoadString(pdata, "<node name='ZS' type='B'></node>",MXML_NO_CALLBACK);
/* 在data节点下创建子节点node */
pnode = mxmlNewElement(pdata, "node");
mxmlElementSetAttr(pnode, "name", "LS");
mxmlElementSetAttr(pnode, "type", "C");
/* 在data节点下创建子节点group */
pgroup = mxmlNewElement(pdata, "group");
mxmlElementSetAttr(pnode, "name", "WW");
mxmlElementSetAttr(pnode, "type", "D");
/* 在group节点下创建子节点node */
pnode = mxmlNewElement(pgroup, "node");
mxmlElementSetAttr(pnode, "name", "ZL");
mxmlElementSetAttr(pnode, "type", "E");
/* 在group节点下创建子节点node */
pnode = mxmlNewElement(pgroup, "node");
mxmlElementSetAttr(pnode, "name", "SQ");
mxmlElementSetAttr(pnode, "type", "F");
/* 在group节点下创建子节点node */
pnode = mxmlNewElement(pgroup, "node");
mxmlElementSetAttr(pnode, "name", "ZB");
mxmlElementSetAttr(pnode, "type", "G");
/* 在data节点下创建子节点node */
pnode = mxmlNewElement(pdata, "node");
mxmlElementSetAttr(pnode, "name", "WJ");
mxmlElementSetAttr(pnode, "type", "H");
/* 在data节点下创建子节点node */
pnode = mxmlNewElement(pdata, "node");
mxmlElementSetAttr(pnode, "name", "ZS");
mxmlElementSetAttr(pnode, "type", "I");
/* 在data节点下创建子节点node */
mxmlLoadString(pdata, "<foo><bar><one><two><two name='ZS' type='B'></two><two name='ZC' type='C'></two></two></one>"
"</bar></foo>", MXML_OPAQUE_CALLBACK);
/* 保存生成的xml数据到creatxmlfiletest.xml */
fp = fopen("/shr/creatxmlfiletest.xml", "w");
mxmlSaveFile(pxml, fp, whitespace_cb);
fclose(fp);
/* 保存生成的xml数据到字符串缓存s8Buff */
mxmlSaveString(pxml, Buff, sizeof(Buff), whitespace_cb);
printf("s8Buff =\n");
printf("%s\n", Buff);
memset(Buff, 0, sizeof(Buff));
/* 删除节点,释放内存 */
mxmlDelete(pxml);
/* 读取 XML 文档*/
fptra = fopen("/shr/creatxmlfiletest.xml", "r");
tree = mxmlLoadFile(NULL, fptra, whitespace_cb);
fclose(fptra);
/* 遍历上述创建的文档,并将所有的属性和值打印 */
for (node = mxmlFindElement(tree, tree, "node", NULL, NULL, MXML_DESCEND);
node != NULL;
node = mxmlFindElement(node, tree, "node", NULL, NULL, MXML_DESCEND))
{
if(mxmlElementGetAttr( node, "name"))
printf("mane = %s ", mxmlElementGetAttr( node, "name"));
if(mxmlElementGetAttr( node, "type"))
printf("type = %s \n", mxmlElementGetAttr( node, "type"));
/* 保存生成的xml数据到字符串缓存s8Buff */
mxmlSaveString(node, Buff, sizeof(Buff), whitespace_cb);
printf("Buff =\n");
printf("%s\n", Buff);
memset(Buff, 0, sizeof(Buff));
}
printf("\n");
for (node = mxmlFindElement(tree, tree, "two", NULL, NULL, MXML_DESCEND);
node != NULL;
node = mxmlFindElement(node, tree, "two", NULL, NULL, MXML_DESCEND))
{
if(mxmlElementGetAttr( node, "name"))
printf("mane = %s ", mxmlElementGetAttr( node, "name"));
if(mxmlElementGetAttr( node, "type"))
printf("type = %s \n", mxmlElementGetAttr( node, "type"));
/* 保存生成的xml数据到字符串缓存s8Buff */
mxmlSaveString(node, Buff, sizeof(Buff), whitespace_cb);
printf("Buff =\n");
printf("%s\n", Buff);
memset(Buff, 0, sizeof(Buff));
}
printf("\n");
printf("mydemo end\n");
return 0;
}
#ifdef __cplusplus
}
#endif
mxmlSaveString(node, Buff, sizeof(Buff), whitespace_cb);中的换行缩进回调函数whitespace_cb自己修改了下:
/* mxml-private.h */
extern char return_buff[];
extern const char *whitespace_cb(mxml_node_t *node,int where);
/* mxml-private.c */
char return_buff[32] = {0};
const char *whitespace_cb(mxml_node_t *node, int where) /* I - Open or close tag? */
{
mxml_node_t *parent; /* Parent node */
int level; /* Indentation level 缩进级别*/
const char *name; /* Name of element */
static const char *tabs = "\t\t\t\t\t\t\t\t";
/* Tabs for indentation*/
name = node->value.element.name;
if (!strncmp(name, "?xml", 4))
{
// ?xml打开后换行
if (where == MXML_WS_AFTER_OPEN)
return ("\n");
else
return (NULL);
}
else if (name != NULL)
{
/*
* Newlines before open and after close...打开前和关闭后换行
*/
if ((where == MXML_WS_BEFORE_OPEN || where == MXML_WS_BEFORE_CLOSE) && node->child)
{
// 有子节点,打开前||关闭前换行缩进
if(node->parent)
{
parent = node->parent;
level = -1;
while(parent)
{
level ++;
if(parent->parent)
parent = parent->parent;
else
break;
}
}
if (level > 8)
level = 8;
else if (level < 0)
level = 0;
sprintf(return_buff, "%s%s", "\n", tabs + 8 - level);
return return_buff;
}
else if (where == MXML_WS_BEFORE_OPEN && !node->child)
{
// 没有子节点,打开前换行缩进
if(node->parent)
{
parent = node->parent;
level = -1;
while(parent)
{
level ++;
if(parent->parent)
parent = parent->parent;
else
break;
}
}
if (level > 8)
level = 8;
else if (level < 0)
level = 0;
sprintf(return_buff, "%s%s", "\n", tabs + 8 - level);
return return_buff;
}
}
return (NULL);
}