`
it_liuyong
  • 浏览: 98109 次
  • 性别: Icon_minigender_1
  • 来自: 北京
社区版块
存档分类
最新评论

FLEX中使用AS动态创建DataGrid

    博客分类:
  • flex
 
阅读更多
FLEX中使用AS动态创建DataGrid
2010年2月6日 17:48 查看评论(2) 分类:技术文章 Tags:as3 flex
初学FLEX时,需要在AS里动态生成DataGrid,结果搞了很久才搞明白怎么把用MXML写出来的DataGrid改成用AS写出来,其中最主要的就是自定义itemEditor、itemRender怎么写,写篇东西整理总结下。

先看看下面这段代码:

查看源代码打印帮助01.<?xml version="1.0" encoding="utf-8"?>
02.<mx:Application xmlns:mx="http://www.adobe.com/2006/mxml" layout="absolute">
03.   
<mx:Script>
04.       
<![CDATA[
05.           
import mx.collections.ArrayCollection;
06.           
import mx.controls.DataGrid;
07.           
import mx.events.ListEvent;
08.           
[Bindable]
09.           
private var dgDataArr:Array = [{name: "Jon", job: "officer"},
10.                                     
{name: "James", job: "seller"},
11.                                     
{name: "Jodon", job: "manager"}];
12.

13.           
private function itemClickHandler(e:ListEvent):void
14.           
{
15.               
trace(e.target);
16.           
}
17.

18.       
]]>
19.   
</mx:Script>
20.   
<mx:Component id="comboboxEditor">
21.       
<mx:ComboBox dataProvider="{dt}" editable="true">
22.           
<mx:Script>
23.               
<![CDATA[
24.                   
private var dt:Array = ["officer", "seller", "manager"];
25.               
]]>
26.           
</mx:Script>
27.       
</mx:ComboBox>
28.   
</mx:Component>
29.   
<mx:DataGrid width="100%" x="10" y="20" fontSize="14" dataProvider="{dgDataArr}" editable="true" itemClick="itemClickHandler(event)">
30.       
<mx:columns>
31.           
<mx:DataGridColumn dataField="name" editable="false" />
32.           
<mx:DataGridColumn dataField="job" itemEditor="{comboboxEditor}">
33.           
</mx:DataGridColumn>
34.       
</mx:columns>
35.   
</mx:DataGrid>
36.</mx:Application>
代码实现的是创建一个DataGrid,其中job栏可以编辑,并且编辑器是自定义的一个ComboBox。效果如下:



现在看怎么用AS代替MXML创建同样的DataGrid。


1.先实现这一句:
查看源代码打印帮助1.<mx:DataGrid x="10" y="20" editable="true" width="100%" fontSize="14" dataProvider="{dgDataArr}" itemClick="itemClickHandler(event)"></mx:DataGrid>
写成AS大概是这样:

查看源代码打印帮助01.private function init():void
02.{
03.   
var dgData:ArrayCollection = new ArrayCollection(dgDataArr);
04.   
var dataGrid:DataGrid = new DataGrid();
05.   
dataGrid.x = 10;
06.   
dataGrid.y = 20;
07.   
dataGrid.editable = true;
08.   
dataGrid.percentWidth = 100;
09.   
dataGrid.setStyle("fontSize", 14);
10.   
dataGrid.dataProvider = dgDataArr;
11.   
dataGrid.addEventListener(ListEvent.ITEM_CLICK, itemClickHandler);
12.   
addChild(dataGrid);
13.}
可以看到,在MXML里统一使用XX=”"的形式,但写成AS却各有不同。我没看过书,刚开始也迷惑,怎么就不能dataGrid.fontSize = 14这样写呢。

看下文档,才知道,每个MXML组件后面的属性分三种:

1.Properties 正常属性,如x y width等,写成AS是 dataGrid.x = 10

2.Styles 样式属性,如fontSize backgroundColor等,需要通过setStyle()设置,如dataGrid.setStyle(“fontSize”, 14);,也可以通过设置其styleName属性绑定到页面的一个css里。如:

查看源代码打印帮助1.dataGrid.styleName = "datagrid";查看源代码打印帮助1.<mx:Style>
2.   
.datagrid{
3.   
fontSize:14;
4.   
}
5.</mx:Style>
3.Events 事件属性,AS要使用事件侦听,itemClick=”itemClickHandler(event)”对应的是如dataGrid.addEventListener(ListEvent.ITEM_CLICK, itemClickHandler);。具体哪个属性对应哪个事件,就要查文档了。

其中width有点特殊,如果想设置百分比的宽度,不能用 dataGrid.width = “100%”,需要设置percentWidth,实际上在MXML设置width时如果有百分号,数值会传给percentWidth而不是width

还有一个属性比较特殊,就是dataProvider,它是一个实现ICollectionView接口的东西。如果传入的是Array,会自动转成ArrayCollection,如果是XMLList会转成XMLListCollection。这里直接传入一个ArrayCollection,是为了之后使用不同过滤函数时不用调用dataGrid.dataProvider而直接用dgData,如dgData.filterFunction = myFilterFunction

2.接下来添加列:
查看源代码打印帮助1.var columns:Array = new Array();
2.var col:DataGridColumn;
3.for ( var i:* in dgDataArr[0] ) {
4.   
col = new DataGridColumn(i);
5.   
if ( i == "name" ) col.editable = false;
6.   
columns.push(col);
7.}
8.dataGrid.columns = columns;
这里只有两栏属性,用for in有点浪费了,这里只是示例。一般用AS写DataGrid都是动态生成的,数据也不确定,都用遍历添加栏。

3.最后就是使用ComboBox编辑。
传给itemRender和itemEditor都必须是一个实现IFactory接口的东西,IFactory接口很简单,只有一个newInstance()函数,DataGrid在渲染每一栏和每一栏的编辑器时都调用这个函数,返回一个新的渲染器。DataGrid默认的渲染器是DataGridItemRenderer,编辑的渲染器是TextInput。用下面的语句就可以把某一栏的编辑器设定为ComboBox:

查看源代码打印帮助1.var comboboxFactory:ClassFactory = new ClassFactory(ComboBox);
2.col.itemEditor = comboboxFactory;
ClassFactory是实现了IFactory接口的类,上面这样设定后,每次col这一栏编辑的时候就会调用comboboxFactory.newInstance()生成一个ComboBox实例。
如果就只是上面那样设置,结果就是编辑时跳出来的ComboBox没有值,也不允许编辑,怎样传值进去呢?
ClassFactory有个properties属性可以让你传值给每一个ComboBox:

查看源代码打印帮助1.comboboxFactory.properties = { dataProvider: ["officer", "seller", "manager"], editable: true };
编辑后,DataGrid会默认把编辑器的text属性值保存到dataProvider里,并传送到itemRender。如果这里的编辑器没有text属性,例如NumericStepper,就需要给栏目设定editorDataField属性,指定编辑后该去哪里取修改过的值。例如:col.editorDataField = “value”

如果想要有更大的自由度,也可以自己写一个实现IFactory接口的类,在newInstance()里返回一个实例就行了:

查看源代码打印帮助01.package
02.{
03.   
import mx.controls.ComboBox;
04.   
import mx.core.IFactory;
05.   
public class CustomComboBox implements IFactory
06.   
{
07.       
private var customData:Array = ["officer", "seller", "manager"];
08.       
public function CustomComboBox() { }
09.       
public function newInstance():*
10.       
{
11.           
var combobox:ComboBox = new ComboBox();
12.           
combobox.dataProvider = customData;
13.           
combobox.editable = true;
14.           
combobox.setStyle("fontWeight", "normal");
15.           
return combobox;
16.       
}
17.   
}
18.}
然后给itemEditor一个实例:col.itemEditor = new CustomComboBox();

这样,文章开头的那个MXML写的DataGrid就全由AS生成了。完整代码:

查看源代码打印帮助01.<?xml version="1.0" encoding="utf-8"?>
02.<mx:Application xmlns:mx="http://www.adobe.com/2006/mxml" layout="absolute" initialize="init()">
03.   
<mx:Script>
04.       
<![CDATA[
05.           
import mx.controls.dataGridClasses.DataGridColumn;
06.           
import mx.collections.ArrayCollection;
07.           
import mx.controls.DataGrid;
08.           
import mx.events.ListEvent;
09.           
import mx.controls.ComboBox;
10.           
[Bindable]
11.           
private var dgDataArr:Array = [{name: "Jon", job: "officer"},
12.                                     
{name: "James", job: "seller"},
13.                                     
{name: "Jodon", job: "manager"}];
14.

15.           
private function init():void
16.           
{
17.               
var dgData:ArrayCollection = new ArrayCollection(dgDataArr);
18.               
dgData.filterFunction
19.               
var dataGrid:DataGrid = new DataGrid();
20.               
dataGrid.x = 10;
21.               
dataGrid.y = 20;
22.               
dataGrid.editable = true;
23.               
dataGrid.percentWidth = 100;
24.               
dataGrid.setStyle("fontSize", 14);
25.               
dataGrid.styleName
26.               
dataGrid.dataProvider = dgData;
27.               
dataGrid.addEventListener(ListEvent.ITEM_CLICK, itemClickHandler);
28.               
addChild(dataGrid);
29.

30.               
var columns:Array = new Array();
31.               
var col:DataGridColumn;
32.               
for ( var i:* in dgDataArr[0] ) {
33.                   
col = new DataGridColumn(i);
34.                   
if ( i == "name" ) col.editable = false;
35.                   
if ( i == "job" ) {
36.                       
var comboboxFactory:ClassFactory = new ClassFactory(ComboBox);
37.                       
comboboxFactory.properties = { dataProvider: ["officer", "seller", "manager"], editable: true };
38.                       
col.itemEditor = comboboxFactory;
39.                   
}
40.                   
columns.push(col);
41.               
}
42.               
dataGrid.columns = columns;
43.

44.           
}
45.           
private function itemClickHandler(e:ListEvent):void
46.           
{
47.               
trace(e.target);
48.           
}
49.

50.       
]]>
51.   
</mx:Script>
52.</mx:Application>
分享到:
评论

相关推荐

Global site tag (gtag.js) - Google Analytics