天天看點

動态載入資料的無重新整理TreeView控件(8)

作為一個TreeView控件,顯示、操作、動态加載都完成了,接下來最重要的就是怎麼和使用者代碼結合了。事件是一種控件結合使用者互動較好的方式,接下來就介紹一下在這個TreeView控件中的事件處理模型及實作。

我們應該承認,C#的+=和-=方式的事件attach和dettach方式是非常清晰易用的。不過由于JavaScript不支援運算符重載,要實作這樣的調用方式非常的困難,因為隻有基本的JavaScript數值類型(int,

float)才支援+=和-=操作。是以我們考慮按dom那樣使用attachEvent的調用方式來實作TreeView控件的事件支援。

    Dom提供的attachEvent和dettachEvent其本質是對一個集合的操作,集合中可以存放一個事件的多個處理器引用。比如:

動态載入資料的無重新整理TreeView控件(8)

 document.attachEvent('onload', handler1);

動态載入資料的無重新整理TreeView控件(8)

 document.attachEvent('onload', handler2);

動态載入資料的無重新整理TreeView控件(8)

 // . . .

動态載入資料的無重新整理TreeView控件(8)

 document.attachEvent('onload', handlerN);

    于是我們先實作一個EventHander類,它就是用來存放事件處理器,并處理事件觸發的。代碼如下:

動态載入資料的無重新整理TreeView控件(8)

<script language="javascript">

動态載入資料的無重新整理TreeView控件(8)

</script>

    其實就是個集合,用來放置handlers,并同時觸發。

    同時為了調用友善,為Object對象attach了一個AttachEvent的原型方法:

動态載入資料的無重新整理TreeView控件(8)

Object.prototype.AttachEvent = function(eventName, eventHandler)

動态載入資料的無重新整理TreeView控件(8)

{

動态載入資料的無重新整理TreeView控件(8)

    if ( typeof(eventName) != 'string' || typeof(eventHandler) != 'function' )

動态載入資料的無重新整理TreeView控件(8)

    {

動态載入資料的無重新整理TreeView控件(8)

        return new Error('eventName, eventHandler. Error parameters type.');

動态載入資料的無重新整理TreeView控件(8)

    }

動态載入資料的無重新整理TreeView控件(8)

    if ( eventName[0] != 'e' || eventName[1] != '_' )

動态載入資料的無重新整理TreeView控件(8)
動态載入資料的無重新整理TreeView控件(8)

        eventName = 'e_' + eventName;

動态載入資料的無重新整理TreeView控件(8)
動态載入資料的無重新整理TreeView控件(8)

    var evt = this[eventName];

動态載入資料的無重新整理TreeView控件(8)

    if ( typeof(evt) != 'undefined' )

動态載入資料的無重新整理TreeView控件(8)
動态載入資料的無重新整理TreeView控件(8)

        if ( __typeof__(evt) == 'EventHandler' )

動态載入資料的無重新整理TreeView控件(8)

        {

動态載入資料的無重新整理TreeView控件(8)

            evt.AttachHandler(eventHandler);

動态載入資料的無重新整理TreeView控件(8)

        }

動态載入資料的無重新整理TreeView控件(8)

        else

動态載入資料的無重新整理TreeView控件(8)
動态載入資料的無重新整理TreeView控件(8)

            this[eventName] = new EventHandler(this, eventName, eventHandler);

動态載入資料的無重新整理TreeView控件(8)
動态載入資料的無重新整理TreeView控件(8)
動态載入資料的無重新整理TreeView控件(8)

};

定義好了事件的處理模型,我們在TreeView中怎麼使用呢?下面一Collapse操作為例,如果我們要再TreeNode執行了Collapse後做一些使用者自定義的事情,比如修改圖示什麼的。于是我們在TreeNode中定一個事件,名叫:e_Collapsed。修改Collpase方法如下:

動态載入資料的無重新整理TreeView控件(8)

TreeNode.prototype.Collapse = function()

動态載入資料的無重新整理TreeView控件(8)
動态載入資料的無重新整理TreeView控件(8)

    var elmtNode = this.m_Element;

動态載入資料的無重新整理TreeView控件(8)

    var childTree = elmtNode.nextSibling;

動态載入資料的無重新整理TreeView控件(8)

    if ( childTree )

動态載入資料的無重新整理TreeView控件(8)
動态載入資料的無重新整理TreeView控件(8)

        childTree.style.display = 'none';

動态載入資料的無重新整理TreeView控件(8)

        this.m_IsChildExpanded = false;

動态載入資料的無重新整理TreeView控件(8)

        elmtNode.OpIcon.src = TreeStyle.OpIcon(this.GetOpIconName());

動态載入資料的無重新整理TreeView控件(8)

        if ( this.e_Collapsed )

動态載入資料的無重新整理TreeView控件(8)
動态載入資料的無重新整理TreeView控件(8)

            this.e_Collapsed.Execute('collapse');

動态載入資料的無重新整理TreeView控件(8)
動态載入資料的無重新整理TreeView控件(8)

    }     

動态載入資料的無重新整理TreeView控件(8)

    其實就是添加了一個觸發eventHandlers的調用this.e_Collapsed.Execute('collapse');。使用這個event和使用DHMTL的dom中的attachEvent一樣,并且也支援attach多個eventHandler到一個事件上。

動态載入資料的無重新整理TreeView控件(8)

 var node = new TreeNode('TestNode');

動态載入資料的無重新整理TreeView控件(8)

 node.AttachEvent('Collapsed', fnCollapsed);

    // 這裡把事件名寫成'Collapsed'和'e_Collapsed'是完全一樣的,AttachEvent内部做了處理。

    eventHandler就是一個普通的函數,隻是它的arguments[0]和arguments[1]是sender和eventArgs。上面示例的處理函數示例為:

動态載入資料的無重新整理TreeView控件(8)

 function fnCollapsed(sender, e)

動态載入資料的無重新整理TreeView控件(8)

 {

動态載入資料的無重新整理TreeView控件(8)

     var node = sender;

動态載入資料的無重新整理TreeView控件(8)

     node.SetCustomizeIcon('E:\\Working\\Private\\TreeView\\Images\\close.gif');

動态載入資料的無重新整理TreeView控件(8)

     status = 'collapsed status: ' + e + ', ' + sender.m_Id;

動态載入資料的無重新整理TreeView控件(8)

 }

    作用是把目前TreeNode的圖示換為'close.gif'。

    使用上面的方法,我們可以為TreeNode實作以下常用的事件:

動态載入資料的無重新整理TreeView控件(8)

 this.e_Clicked = null;

動态載入資料的無重新整理TreeView控件(8)

 this.e_SelectedChanged = null;

動态載入資料的無重新整理TreeView控件(8)

 this.e_CheckedChanged = null;

動态載入資料的無重新整理TreeView控件(8)

 this.e_NodeCreating = null;

動态載入資料的無重新整理TreeView控件(8)

 this.e_Expanded = null;

動态載入資料的無重新整理TreeView控件(8)

 this.e_Collapsed = null;

動态載入資料的無重新整理TreeView控件(8)

 this.e_Appended = null;

    這些事件在沒有AttachEvent之前不會産生任何的處理代價,除了一個if判斷。

本文轉自部落格園鳥食軒的部落格,原文連結:http://www.cnblogs.com/birdshome/,如需轉載請自行聯系原部落客。

繼續閱讀