posts - 11, comments - 29, trackbacks - 0, articles - 1
  BlogJava :: 首页 :: 新随笔 ::  :: 聚合  :: 管理

AJAX Web Tree 构建方案及实现思想

Posted on 2006-01-27 16:42 -=Kinohl=- 阅读(2688) 评论(7)  编辑  收藏 所属分类: 编程语言

***************************************
关键字:AJAX,Tree,Struts,DOM
难易度:
软件版本:struts 1.2.8
时间:2006-01-27
Author:Kino
***************************************


前阵子写了一个小代码处理AJAX下WebTree的构建,其中碰到了一些问题,也有一些想法,现在说出来希望大家一起看看,如果案由问题请不吝赐教,本人不胜感激啊。

背景:
这次因为是加载在Struts上的开发,Web页面上的Tree作AJAX处理,因为有Node的增删改操作。Server端因为要和WebService连接,所以不做Cache。

解决案:
1。使用Polling调用AJAX定期更新Tree。
2。AJAX访问的地址是一个Action(例:createtree.do)。用来返回Tree模型或者错误消息(国际化)。
3。Browser解析XML的TreeModel。
4。在Browser比较新旧2个TreeModel,完成选中状态的继承。
5。CSS渲染TreeNode。

以上是简单的思路。传统的AJAX应该是尽量减少XMl传输量,迫于没有Cache的缘故,并且WS给我的节点并不能简单的得到父子关系。我选择了,每次Polling更新整棵树的方案。性能未测。

我这次在web server 端构建Tree时直接用深度优先转换成XML。XMl中数据的先后顺序决定了Tree从父到子,从兄到弟的深度优先关系,indent决定了深度(也就是缩进)。这样我从Server端传入的也就成了一个标准的Tree显示Model。格式定义如下。
  * Gobal Master Tree DTD
 * &lt!ELEMENT tree (tree*)&gt
 * &lt!ATTLIST tree
 *  id   CDATA #REQUIRED LoctionInfo's toString
 *  indent  CDATA #REQUIRED Tree's Level
 *  text        CDATA   #REQUIRED label in html
 *  tooltip     CDATA   #IMPLIED title in html
 *  action      CDATA   #IMPLIED href in html
 *  icon        CDATA   #IMPLIED close icon with the node status
 *  openicon    CDATA   #IMPLIED open icon with the node status
 *  open        CDATA   #IMPLIED&gt node's open states ,default is false in server.
 *  target  CDATA #IMPLIED node's open target
 *
<span id="maintree">
 <tree id="Ajax" indent=0 text="Root" tooltip="Root" action="/logout.do" icon="" openicon= "" open="false"/>
 <tree id="110" indent=1 text="Node 1" tooltip="Node 1" action="/logout.do" icon="" openicon= "" open="false"/>
 <tree id="120" indent=2 text="Node 2" tooltip="Node 2" action="/logout.do" icon="" openicon= "" open="false"/>
 <tree id="12580" indent=2 text="Node 3" tooltip="Node 3" action="/logout.do" icon="" openicon= "" open="false"/>
 <tree id="user" indent=1 text="Node 4" tooltip="Node 4" action="/logout.do" icon="" openicon= "" open="false"/>
</span>

上边的 Tree显示出来如下
Root
 │
 ├Node 1
 │    │
 │    ├Node 2
 │    └Node 3
 └Node 4
indent   就是缩进。
数据的先后顺序就是深度优先的遍历顺序。

这样的数据到了Browser,会先被转成一个对象数组。

 1// Tree Node object
 2// This function creates a node in the tree with the following arguments:
 3//    sId         - The node's index within the global nodes_array
 4//    iIndent    - The level within the tree hierarchy (0 = top)
 5//    sText      - The text displayed in the tree for this node
 6//    sTooltip     - the tool tip
 7//    oAction   - For a document, the address it will display when clicked
 8//    sIcon        - the node's icon 
 9//    sIconOpen    - the node's icon state
10//      bOpen - true  false
11function GMTreeNode(sId,iIndent,sText,sTooltip,sAction,sIcon,sIconOpen,bOpen,sTarget)
12{
13    if (sId) this.id = sId;
14    if (iIndent) this.indent = iIndent;
15    if (sText) this.text = sText;
16    if (sAction) this.action = sAction;
17    if (sTooltip) this.tooltip = sTooltip;
18    if (sIcon) this.icon = sIcon;
19    if (sIconOpen) this.iconopen = sIconOpen;
20    if (bOpen) this.open = bOpen;
21    if (sTarget) this.target = sTarget;
22    
23//    //alert(this.id + "  " + this.indent + "  " + this.text + "  " + this.action + "  " + 
24//    this.tooltip + "  " + this.icon + "  " + this.iconopen + "  " + this.open);
25}

然后会和正在显示的Tree数组 进行一个 比较,用于写入展开状态,代码如下:
 1/////////////////////////////////
 2//    >>>Compare 
 3//    compare maintree with maintree. and copy maintree to maintree
 4/////////////////////////////////
 5function compareTreeModel()
 6{
 7    //alert("I am here in compareTreeModel");
 8    if (ajaxtree.length <= 0){
 9        alert("ajaxtree is null");//TODO
10        return;
11    }

12    
13    if (maintree.length <= 0){
14        //alert("maintree is null");
15        maintree = ajaxtree;
16        return;
17    }

18    //compare start
19    //var maxlen = Math.max(ajaxtree.length,maintree.length);
20    for(var i=0;i<ajaxtree.length;i++)
21    {
22        for(var j=0;j<maintree.length;j++)
23        {
24            if (ajaxtree[i].id == maintree[j].id)
25            {
26                ajaxtree[i].open = maintree[j].open;
27                break;
28            }

29        }
    
30    }

31    
32    maintree = ajaxtree;
33    
34}
maintree 就是正在显示的 Tree,ajaxtree是刚得到的新Tree。2个对象都是TreeNode的数组。而TreeNode对象的Open属性即记录了节点的展开状态。那么这里就对这个节点状态进行“移植”,完毕后,把新Tree模型交付显示方法,也就是ToHtml方法。

转换Html部分算是一个比较容易出bug的危险点。

首先分析一下,生成的代码是什么样子的。
这里仍然用上边的那棵树作例子。
生成的DOM结构应该是
<div 父>
    <div  收缩>
    <img  折线  />
    <img  图标 />
    <a 节点动作>节点Label</a>
    <div 子>
        ....递归的构造
    </div 子>
    </div 收缩>
</div 父>

其次 对于这种并不直接含有父子关系的节点首先要判明一个节点的子 和 兄弟,然后用递归解决。
递归的思路如下深度优先:
function toHtml(节点index)
{
   var child_html;
   if 这个节点有子
   {
        Loop子节点
        {
               child_html[i] = toHtml(子节点index);
               i++;访问下一个子节点
   }
  
   var 所有子节点Html模块 = <div 收缩>   child_html.join("") </div>

   var 本节点Html模块 = <div 本节点><div 收缩><img ><img  图标 /><a 节点动作>节点Label</a>所有子节点Html模块</div 收缩></div 本节点>;

   return  本节点Html模块;
}

树就构建好了。

作为显示,使用了CSS的
background-repeat: repeat-y;
 background-image: url("../images/tree/I.png") !important;
 background-position-y: 1px !important; /* IE only */

还有padding-left作Div的向右偏移,默认的偏移量是19个像素点,然后根据Tree显示模型的indent相乘就ok了。

思路就是这些。希望能对 朋友们有所帮助。
欢迎讨论。

评论

# re: AJAX Web Tree 构建方案及实现思想  回复  更多评论   

2006-03-15 10:16 by 甲虫
您好,很荣幸看到这个,也非常的高兴,在网上找到很多却没有找到类似的,请您帮我一个忙,能不能把这个AJAX Web Tree 的完整的例子发给我一份,将不胜感激.
我的Email:sf1979@gmail.com
再次感谢!

# re: AJAX Web Tree 构建方案及实现思想  回复  更多评论   

2006-03-15 10:59 by 小叶
不知道有没有ASP版的?我也想学这个呢:)

# re: AJAX Web Tree 构建方案及实现思想  回复  更多评论   

2006-03-29 22:35 by kino
sorry 最近工作问题比较忙。很久没有来更新了。我这两天会给sf1979@gmail.com留下代码的。如果你修改了代码也请告诉我,做个交流好么。
如果想及时联系我请Mail To:kinoviti@gmail.com

# re: AJAX Web Tree 构建方案及实现思想  回复  更多评论   

2007-04-13 17:55 by
您好,很荣幸看到这个,在网上找到很多z至今还没有找到合适的,能不能把你这个AJAX Web Tree 的完整的例子发给我一份,不胜感激.
Email:guowei.hj@gmail.com
谢谢!

# re: AJAX Web Tree 构建方案及实现思想  回复  更多评论   

2007-04-13 18:01 by
真的 非常 谢谢!

# re: AJAX Web Tree 构建方案及实现思想  回复  更多评论   

2007-10-17 18:01 by siyuan
非常好可以把完整代码发给我吗?
我的Email:wjl_2007@sina.com
谢谢

# re: AJAX Web Tree 构建方案及实现思想  回复  更多评论   

2008-07-01 10:40 by dmm
非常好可以把完整代码发给我吗?
我的Email:dongming_9431@163.com
谢谢

只有注册用户登录后才能发表评论。


网站导航: