Type NodeInfo = class

public
	Function Create(name);
	Begin
		NodeName := name;
		ExtAttr  := array();
		ExtNodes := array();
	End

	Function GetAttrs(); virtual;
	Begin
		return ExtAttr;
	End

	Function GetChildren(); virtual;
	Begin
		return ExtNodes;
	End

	Function GetNode(index);  // 返回的index的对象
	Begin
		return ExtNodes[index]['obj'];
	End

	Function GetCount();	 // 返回当前节点的个数
	Begin
		return length(ExtAttr);
	End

	// arr := array('sz': 15, 'style': 'line');
	Function AddAttr(arr);	   // 添加属性
	Begin
		if not istable(arr) then return;
		ExtAttr union= arr;
		return 1;
	End

	Function Marshal();
	Begin
		children := getChildrenEx();
		child_arr := array();
		len := 0;
		for i:=0 to length(children)-1 do
		begin
			node_type := children[i]['nodeType'];
			obj := children[i]['obj'];

			if ifnil(obj) then continue;
			find := select thisrowindex as "rowindex_", * from child_arr where ['name'] = children[i]['name'] end;
			if not ifnil(obj) and not ifObj(obj) and istable(find) and ifstring(children[i]['attrEx']) and children[i]['attrEx'] <> '' then
			begin
				if not ifarray(find[0]['attributes']) then find[0]['attributes'] := array();
				key := children[i]['attrEx'];
				find[0]['attributes'] union= array(key : obj);
				child_arr[find[0]['rowindex_']]['attributes'] := find[0]['attributes'];
				continue;
			end

			arr := array('type': 'element', 'name': children[i]['name'], 'attributes': array());
			if node_type = 'empty' then  // <b/>
			begin
				// child_arr[len] := arr;
				// ++len;
				// continue;
			end
			else if node_type = 'pcdata' then
			begin
				arr['children'] := array(('type': 'pcdata', 'value': obj));
			end
			else if ifObj(obj) then
			begin
				marshal := obj.Marshal();
				if length(marshal['children'])=0 and length(marshal['attributes'])=0 then continue;
				arr['children'] := marshal['children'];
				arr['attributes'] union= marshal['attributes'];
			end
			else
			begin
				key := children[i]['attrName'] ? children[i]['attrName'] : children[i]['attrEx'] ? children[i]['attrEx'] : 'val';
				arr['attributes'] := array(key : obj);
			end

			child_arr[len++] := arr;
		end

		name_arr := str2array(NodeName, '/');
		tmp_arr := array('type': 'element', 'name': name_arr[length(name_arr)-1], 'children': child_arr);
		for i:=length(name_arr)-2 downto 0 do
		begin
			tmp_arr := array('type': 'element', 'name': name_arr[i], 'children': array(tmp_arr));
		end

		attrs_arr := GetAttrs();
		valid_arr := array();
		for k, v in attrs_arr do
		begin
			if not ifnil(v) then valid_arr[k] := v;
		end
		tmp_arr['attributes'] := valid_arr;
		return tmp_arr;
	End

	Function NewChildNode(nodeArr);
	Begin
		if not ifarray(nodeArr) then return 0;
		if not ifstring(nodeArr['name']) then return 0;
		arr := array(
			'name': nodeArr['name'],
			'obj': nodeArr['obj'],
			'attrEx': nodeArr['attrEx'],
			'nodeType': nodeArr['nodeType'],
		);
		ExtNodes union= arr;
		return 1;
	End
private
	Function getChildrenEx();
	Begin
		r := GetChildren();
		a := array();
		for i:=0 to length(r)-1 do Begin
			if ifarray(r[i]['obj']) then Begin
				a union= r[i]['obj'];
			End
			else
				a[ length(a) ] := r[i];
		end;
		return a;
	End;
public
	NodeName;
	ExtAttr;
	ExtNodes;

End
