最近空闲时间在学习Ext2.0框架,只有一个字的感叹“强”,我从未想到JS代码能够写出这么绚丽的Web页面出来,以前看到YUI,惊若天人,如今看到EXT2.0的东西,更是感觉震撼。 Ext2.0是一个JS框架,它的Grid控件和其它可以显示数据的控件,能够支持多种数据类型,如二维数组、Json数据和XML数据,甚至包括我们自定义的数据类型。Ext为我们提供了一个桥梁Ext.data.Store,通过它我们可以把任何格式的数据转化成grid可以使用的形式,这样就不需要为每种数据格式写一个grid的实现了。首先,一个表格应该有列定义,即定义表头ColumnModel:// 定义一个ColumnModel,表头中有四列var cm = new Ext.grid.ColumnModel([ {header:"编号",dataIndex:"id"}, {header:"性别",dataIndex:"sex"}, {header:"名称",dataIndex:"name"}, {header:"描述",dataIndex:"descn"}]);cm.defaultSortable = true; 该ColumnModel定义了表格的四个列,其每列的名称和对应的数据键。请注意defaultSortable属性,即为每个列都安上一个可以排序的功能。如果只想某些列举有该功能,可以设置:{header:"编号",dataIndex:"id",Sortable:true},现在就来看看这个Ext.data.Store是如何转换三种数据的。1.二维数组:// ArrayDatavar data = [ ["1","male","name1","descn1"], ["2","male","name1","descn2"], ["3","male","name3","descn3"], ["4","male","name4","descn4"], ["5","male","name5","descn5"]];// ArrayReadervar ds = new Ext.data.Store({ proxy: new Ext.data.MemoryProxy(data), reader: new Ext.data.ArrayReader({}, [ {name: "id",mapping: 0}, {name: "sex",mapping: 1}, {name: "name",mapping: 2}, {name: "descn",mapping: 3} ])});ds.load();ds要对应两个部分:proxy和reader。proxy告诉我们从哪里获得数据,reader告诉我们如何解析这个数据。现在用的是Ext.data.MemoryProxy,它将内存中的数据data作为参数传递。Ext.data.ArrayReader专门用来解析数组,并且告诉我们它会按照定义的规范进行解析,每行按顺序读取四个数据,第一个叫id,第二个叫sex,第三个叫name,第四个descn。这些是跟cm定义中的dataIndex对应的。这样cm就知道哪列应该显示那条数据了。mapping属性用于标记data中的读取后的数据与标头的映射关系,一般是不用设置的。但如果我们想让sex的数据中name栏中出现,可以设置mapping值。即id的mapping为2,后者为0。记得要执行一次ds.load(),对数据进行初始化。数据的显示显得非常简单:HTML文件: < div id ="grid" ></ div > JS文件:var grid = new Ext.grid.GridPanel({ el: "grid", ds: ds, cm: cm});grid.render();其显示结果为:2.如何在表格中添加CheckBox呢?var sm = new Ext.grid.CheckboxSelectionModel();var cm = new Ext.grid.ColumnModel([ new Ext.grid.RowNumberer(),//自动行号 sm,//添加的地方 {header:"编号",dataIndex:"id"}, {header:"性别",dataIndex:"sex"}, {header:"名称",dataIndex:"name"}, {header:"描述",dataIndex:"descn"}]);var grid = new Ext.grid.GridPanel({ el: "grid3", ds: ds, cm: cm, sm: sm,//添加的地方 title: "HelloWorld"});3. 如何做Grid上触发事件呢?下面是一个cellclick事件grid.addListener("cellclick", cellclick);function cellclick(grid, rowIndex, columnIndex, e) { var record = grid.getStore().getAt(rowIndex); //Get the Record var fieldName = grid.getColumnModel().getDataIndex(columnIndex); //Get field name var data = record.get(fieldName); Ext.MessageBox.alert("show","当前选中的数据是"+data);}4.如何做Grid中做出快捷菜单效果:grid.addListener("rowcontextmenu", rightClickFn);//右键菜单代码关键部分var rightClick = new Ext.menu.Menu({ id:"rightClickCont", //在HTML文件中必须有个rightClickCont的DIV元素 items: [ { id: "rMenu1", handler: rMenu1Fn,//点击后触发的事件 text: "右键菜单1" }, { //id: "rMenu2", //handler: rMenu2Fn, text: "右键菜单2" } ]});function rightClickFn(grid,rowindex,e){ e.preventDefault(); rightClick.showAt(e.getXY());}function rMenu1Fn(){ Ext.MessageBox.alert("right","rightClick");}其Grid如下:5.如何将一列中的数据根据要求进行改变呢?比如说性别字段根据其male或female改变显示的颜色,这种ColumnMode中设计:var cm = new Ext.grid.ColumnModel([ new Ext.grid.RowNumberer(), sm, {header:"编号",dataIndex:"id"}, {header:"性别",dataIndex:"sex",renderer:changeSex}, {header:"名称",dataIndex:"name"}, {header:"描述",dataIndex:"descn"}]);cm.defaultSortable = true;function changeSex(value){ if (value == "male") { return " < span style ="color:red;font-weight:bold;" > 红男 </ span > "; } else { return " < span style ="color:green;font-weight:bold;" > 绿女 </ span > "; }}其它两种数据的Grid显示是相同的,其不同之处在于数据获取的过程: 6.Json数据至于这种数据的类型请大家自己看Ajax的书籍://JsonDatavar data = { "coders": [ { "id": "1", "sex": "male", "name":"McLaughlin", "descn": "brett@newInstance.com" }, { "id": "2", "sex": "male","name":"Hunter", "descn": "jason@servlets.com" }, { "id": "3", "sex": "female","name":"Harold", "descn": "elharo@macfaq.com" }, { "id": "4", "sex": "male","name":"Harolds", "descn": "elhaross@macfaq.com" } ], "musicians": [ { "id": "1", "name": "Clapton", "descn": "guitar" }, { "id": "2", "name": "Rachmaninoff", "descn": "piano" } ]}//ds使用的MemoryProxy对象和JsonReader对象var ds = new Ext.data.Store({ proxy: new Ext.data.MemoryProxy(data), reader: new Ext.data.JsonReader({root: "coders"}, [ {name: "id"}, {name: "sex"}, {name: "name"}, {name: "descn"} ]) });ds.load();var grid = new Ext.grid.GridPanel({ el: "grid3", ds: ds, cm: cm, sm: sm, title: "HelloWorld", autoHeight: true//一定要写,否则显示的数据会少一行});grid.render();7.使用XML数据:注意,读取XML数据必须在服务器上进行。XML数据test.xml的内容: <? xml version="1.0" encoding="UTF-8" ?> < dataset > < results > 2 </ results > < item > < id > 1 </ id > < sex > male </ sex > < name > Taylor </ name > < descn > Coder </ descn > </ item > </ dataset > var ds3 = new Ext.data.Store({ url: "test.xml", //XML数据 reader: new Ext.data.XmlReader({record: "item"}, [ //使用XmlReader对象 {name: "id"}, {name: "sex"}, {name: "name"}, {name: "descn"} ])});8.从服务器获取数据和数据翻页控件从一个服务器文件,如ASP、JSP或Servlet中获得数据二维Array、JSON或XML数据,也可以被Ext读取,并被Grid显示:服务器文件data.asp: <% ... start = cint(request("start")) limit = cint(request("limit")) dim json json=cstr("{totalProperty:100,root:[") for i = start to limit + start-1 json =json + cstr("{"id":"") +cstr(i) + cstr("","name":"name") + cstr(i) + cstr("","descn":"descn") + cstr(i) + cstr(""}") if i <> limit + start - 1 then json =json + "," end if next json = json +"]}" response.write(json) %> 我们可以看到,这个页面会根据传入的start和limit的不同,返回不同的数据,其实质是个分页的代码。下面是start=0,limit=10的JSON数据:{totalProperty:100,root:[{"id":"0","name":"name0","descn":"descn0"},{"id":"1","name":"name1","descn":"descn1"},{"id":"2","name":"name2","descn":"descn2"},{"id":"3","name":"name3","descn":"descn3"},{"id":"4","name":"name4","descn":"descn4"},{"id":"5","name":"name5","descn":"descn5"},{"id":"6","name":"name6","descn":"descn6"},{"id":"7","name":"name7","descn":"descn7"},{"id":"8","name":"name8","descn":"descn8"},{"id":"9","name":"name9","descn":"descn9"}]}我们使用分页控件来控制Grid的数据:Ext.onReady(function(){ var sm = new Ext.grid.CheckboxSelectionModel(); var cm = new Ext.grid.ColumnModel([ new Ext.grid.RowNumberer(), sm, {header:"编号",dataIndex:"id"}, {header:"性别",dataIndex:"sex"}, {header:"名称",dataIndex:"name"}, {header:"描述",dataIndex:"descn"} ]); cm.defaultSortable = true; var ds = new Ext.data.Store({ proxy: new Ext.data.HttpProxy({url:"data.asp"}), reader: new Ext.data.JsonReader({ totalProperty: "totalProperty", root: "root" }, [ {name: "id"}, {name: "name"}, {name: "descn"} ]) }); ds.load({params:{start:0,limit:10}}); var grid = new Ext.grid.GridPanel({ el: "grid3", ds: ds, cm: cm, sm: sm, title: "ASP->JSON", bbar: new Ext.PagingToolbar({ pageSize: 10, store: ds, displayInfo: true, displayMsg: "显示第 {0} 条到 {1} 条记录,一共 {2} 条", emptyMsg: "没有记录" }), tbar: new Ext.PagingToolbar({ pageSize: 10, store: ds, displayInfo: true, displayMsg: "显示第 {0} 条到 {1} 条记录,一共 {2} 条", emptyMsg: "没有记录" }) }); grid.render();})10.如何在Grid的上方添加按钮呢?添加按钮的关键之处在于tbar或bbar属性设置Toolbar工具条:var grid = new Ext.grid.GridPanel({ el: "grid3", ds: ds, cm: cm, sm: sm, title: "HelloWorld", tbar: new Ext.Toolbar({ items:[ { id:"buttonA" ,text:"Button A" ,handler: function(){ alert("You clicked Button A"); } } , new Ext.Toolbar.SplitButton({}) ,{ id:"buttonB" ,text:"Button B" ,handler: function(){ alert("You clicked Button B"); } } , "-" ,{ id:"buttonc" ,text:"Button c" } ] }) });11.将GridPanel放入一个Panel或TabPanel中var tabs = new Ext.TabPanel({ collapsible: true ,renderTo: "product-exceptions" ,width: 450 ,height:400 ,activeTab: 0 ,items:[ { title: "Unmatched" },{ title: "Matched" } ]});tabs.doLayout();var panel = new Ext.Panel({ renderTo: "panel", title:"panel", collapsible:true, width:450, height:400, items:[grid] //管理grid});Panel必须有DIV存在。其包含的Component有items管理。