在網(wǎng)上看過(guò)很多人轉(zhuǎn)載darronschall的 LabelCellRenderer 例子,其中有個(gè)錯(cuò)誤,把myList.cellRenderer = "LabelCellRenderer";這行代碼放到了注釋里面去了,但是到處轉(zhuǎn)載的依然沒(méi)有修正(其實(shí)原文是正確的)。
其實(shí)看了這個(gè)我們并沒(méi)有求甚解,要知道授人予魚(yú),不如授人予漁。我們?cè)賮?lái)看下為什么通過(guò)cellrenderer可以給List、DataGrid、Tree 和 Menu 組件以及其它列表組件增強(qiáng)單元格內(nèi)容顯示。
我們首先要從List組件開(kāi)始分析,List 類至關(guān)重要。DataGrid、Tree 和 Menu 組件是 List 類的擴(kuò)展。
List 類由行構(gòu)成。這些行顯示滑過(guò)和選區(qū)突出顯示,用作行選區(qū)的點(diǎn)擊狀態(tài),并在滾動(dòng)中扮演重要的角色。除了選區(qū)突出顯示和圖標(biāo)(如節(jié)點(diǎn)圖標(biāo)和 Tree 組件的展開(kāi)箭頭)之外,行還包含一個(gè)單元格(或者,如果是 DataGrid,則包含多個(gè)單元格)。在默認(rèn)情況下,這些單元格是實(shí)現(xiàn) CellRenderer API 的 TextField 對(duì)象。但是,您可以讓 List 使用不同的組件類作為每一行的單元格。唯一的要求是該類必須實(shí)現(xiàn) List 用于與單元格通信的 CellRenderer API。
List 類使用一種非常復(fù)雜的算法進(jìn)行滾動(dòng)。一個(gè)列表只會(huì)列出它一次能顯示的最多行數(shù),超出 rowCount 屬性的值的項(xiàng)目根本不會(huì)獲得行。在列表滾動(dòng)時(shí),它會(huì)將所有行上下移動(dòng)(取決于滾動(dòng)方向)。然后,列表將重復(fù)使用滾出視圖的行;列表會(huì)重新初始化這些行,并使用它們作為正在滾入視圖的新行,方法是將舊行的值設(shè)置為視圖中的新行,然后將舊行移到新項(xiàng)目滾入視圖的位置。
要使用 CellRenderer API,您必須編寫(xiě)包含下面四個(gè)方法的類
CellRenderer.getPreferredHeight() 返回單元格的首選高度 CellRenderer.getPreferredWidth() 返回單元格的首選寬度 CellRenderer.setSize() 設(shè)置單元格的寬度和高度 CellRenderer.setValue() 設(shè)置要顯示在單元格中的內(nèi)容
基于列表的組件將使用該類與單元格通信。這就是我們看到的darronschall定義的LabelCellRenderer類。
系統(tǒng)將為單元格自動(dòng)指定兩個(gè)方法和一個(gè)屬性
CellRenderer.getCellIndex() 返回包含單元格渲染器數(shù)據(jù)字段的名稱的字符串 CellRenderer.getDataLabel() 返回包含兩個(gè)字段(columnIndex 和 rowIndex)的對(duì)象,這兩個(gè)字段指明單元格的位置 CellRenderer.listOwner 指向包含單元格的列表的引用 以便允許它與基于列表的組件通信。例如,假設(shè)單元格內(nèi)包含一個(gè)復(fù)選框,該復(fù)選框?qū)е滦性趩螕魰r(shí)被選中。單元格渲染器需要引用包含它的基于列表的組件,以便調(diào)用基于列表的組件的 selectedIndex 屬性。同時(shí),單元格需要知道它當(dāng)前正在渲染的項(xiàng)目索引,以便能夠?qū)?selectedIndex 設(shè)置為正確的編號(hào);單元格可以使用 CellRenderer.listOwner 和 CellRenderer.getCellIndex() 達(dá)到此目的。您不需要實(shí)現(xiàn)這些 API;在將單元格放到基于列表的組件內(nèi)時(shí),單元格將自動(dòng)接收這些 API。 我們來(lái)看下LabelCellRenderer類實(shí)現(xiàn)的這幾個(gè)方法代碼:
function createChildren(Void) : Void { label = createObject("Label", "label", 1, { styleName:this, owner:this }); label.html = true; size(); } // setSize is implemented by UIComponent and calls size(), after setting // __width and __height function size(Void) : Void { label.setSize(__width, __height); // make sure the label field is in the top-left corner // of the row label._x = 0; label._y = 0; } function setValue(str:String, item:Object, sel:Boolean) : Void { // hide the label if no data to display label._visible = (item!=undefined); // this line actually sets htmlText label.text = item.label; } function getPreferredHeight(Void) : Number { // this is the height with the default font, you might // need to adjust this to suit your needs return 18; } function getPreferredWidth(Void) : Number { // default to the width of the listbox return __width; }
其中用來(lái)顯示html標(biāo)記的就是setValue方法了。 我們定義了這個(gè)類后,剩下就是對(duì)List組件來(lái)設(shè)置新的單元格渲染器了。使用下面的代碼: 1 : //LabelCellRenderer就是指定單元格渲染的連接ID 2 : myList.cellRenderer = "LabelCellRenderer";
也許看完這些,你可以做出更好效果的渲染器來(lái)。要注意的是,只有flashMX2004的List組件才支持。
出處:
責(zé)任編輯:qhwa
◎進(jìn)入論壇Flash專欄版塊參加討論
|