Ext.data.Connection
Ext.data.Connection是对Ext.lib.Ajax的封装,它提供了配置使用Ajax的通用方式,它在内部通过Ext.lib.Ajax实现与后台的异步调用。与底层的Ext.lib.Ajax相比,Ext.data.Connection提供了更简洁的配置方式,使用起来更方便。
Ext.data.Connection主要用于在Ext.data.HttpProxy和Ext.data.ScriptTagProxy中执行与后台交互的任务,它会从指定的URL获取数据,并把后台返回的数据交给HttpProxy或ScriptTagPrxoy处理。
1var conn = new Ext.data.Connection({
2 autoAbort:false,
3 defaultHeaders:{
4 referer:'http://localhost:8080'
5 },
6 disableCaching:false,
7 extraParams:{
8 name:'name'
9 },
10 method:'GET',
11 timeout:300,
12 url:'01-01.txt'
13});
14
15conn.request({
16 success:function(response){
17 Ext.Msg.alert('info',response.responseText);
18 },
19 failure:function(){
20 Ext.Msg.alert('warn','failure');
21 }
22});
url:String: 请求url。
params:Object/String/Function: 请求传递的参数。
methos:String:请求方法,通常为GET或POST
callback:Function:请求完成后的回调函数,无论是否成功还是失败,都会执行。
success:Function:请求成功时的回调函数。
failure:Function:请求失败时的回调函数。
scope:Object:回调函数的作用域。
form:Object:绑定的form表单。
isUpload:Boolean:是否执行文件上传。
headers:Object:请求首部信息
xmlData:Object:XML文档对象,可以通过URL附加参数的方式发起请求。
disableCaching:Boolean:是否禁用缓存,默认为禁用。
Ext.data.Connection还提供了abort([Number transactionId]函数),当同时有多个请求发生时,根据指定的事务id放弃其中的某一个请求。如果不指定事务id,就会放弃最后一个请求。isLoading(Number transactionId)函数的用法与abort()类似,可以根据事务id判断对应的请求是否完成。如果未指定事务id,就判断最后一个请求是否完成。
Ext.data.Record
Ext.data.Record就是一个设定了内部数据类型的对象,它是Ext.data.Store的最基本组成部分。如果Ext.data.Store看作是二维表,那么它的每一行就对应一个Ext.data.Record实例。
1var PersonRecord = Ext.data.Record.create({
2 {name:'name',type:'string'},
3 {name:'sex',type:'int'}
4});
5
6var boy = new PersonRecord({
7 name:'boy',
8 sex:0
9});
10
11alert(boy.data.name);
12alert(boy.data['name']);
13alert(boy.get('name'));
14
15boy.data.name = 'boy name';
16boy.data['name'] = 'boy name';
17boy.set('name','boy name');
实例中,15--17行都对属性赋值,但建议使用set()方法。因为set()函数会判断属性值是否发生了变化,如果改变了,就要将当前对象的dirty属性设置为true,并将修改之前的原始值放入modified对象中,供其他函数调用。
Record的属性数据被修改后,可以执行如下几种操作:
commit():这个函数的效果是设置dirty为false,并删除modified中保存的原始数据。
reject():这个函数的效果是将data中已经修改的属性值恢复为modified的原始数据,然后设置dirty为false,并删除保存在原始数据的modified对象。
getChanges():这个函数会把data中经过修改的属性和数据放在一个JSON对象并返回。
我们还可以调用isModified()判断当前record中的数据是否被修改。还可以使用copy()函数复制record实例。
Ext.data.Store
Ext.data.Store中有一个Ext.data.Record数组,所有数据都存放在这些Ext.data.Record实例中。
//Ext.data.Store的基本用法
var data = [
['boy',0],
['girl',1]
];
var store = new Ext.data.Store({
proxy:new Ext.data.MemoryProxy(data),
render:new Ext.data.ArrayReader({}, PersonRecord)
});
store.load();
每个store最少需要两个组件的支持,分别是proxy和reader,proxy用于从某个途径读取原始数据,reader用于将原始数据转换成Record实例。实例中使用Ext.data.MemoryProxy和Ext.data.ArrayReader,将data数组中的数据转换成对应的几个PersonRecord实例,然后放入store中。store创建完毕后,执行store.load()实现这个转换过程。
//对name字段进行降序排列
var store = new Ext.data.Store({
proxy:new Ext.data.MemoryProxy(data),
reader:new Ext.data.ArrayReader({},PersonRecord),
sortInfo:{field:'name',direction:'DESC'}
});
1//更新store中的数据
2store.add(new PersonRecord({
3 name:'other',
4 sex:0
5}));
6
7//add()也可以添加一个record数组
8store.add([new PersonRecord({
9 name:'other1',
10 sex:0
11}),new PersonRecord({
12 name:'other2',
13 sex:1
14})]);
15
16//add()方法会将数据添加入最后一条数据,这样破坏了原本的排序方式
17//addSorted()可以保证数据有序
18store.addSorted(new PersonRecord({
19 name:'other',
20 sex:0
21}));
22
23//使用insert()指定插入位置
24store.insert(3,new PersonRecord({
25 name:'other',
26 sex:0
27}));
28
29//删除操作
30store.remove(store.getAt(0));
31store.removeAll();
32
33//修改数据
34store.getAt(0).set('name','xxx');
35
36
修改record的内部数据之后有两种选择:执行rejectChanges()撤销所有修改,将修改过的record恢复到原来的状态;执行commitChanges()提交数据修改。在执行撤销和提交操作之前,可以使用getModifiedRecords()获得store中修改过的record数组。与修改数据相关的参数是pruneModifiedRecoreds,如果将它设置为true,当每次执行删除或reload操作时,都会清空所有修改。这样,在每次执行删除或reload操作之后,getModifiedRecords()返回的就是一个空数组,否则仍然会得到上次修改过的record记录。
1store.load({
2 params:{start:0,limit:20} //参数
3 callback:function(records,options,success){
4 Ext.Msg.alert('info','加载完毕'); //回调函数
5}
6 scope:store,
7 add:true
8});
callback是加载完毕时执行的回调函数,records参数表示获得的数据;options表示执行load()时传递的参数,success表示加载是否成功。
为store加载数据之后,有时不需要把所有的数据都显示出来,这是可以使用函数filter和filterBy对store中的数据进行过滤,只显示符合条件的部分;如果想取消过滤,则使用clearFilter()函数。
store还有其他一些有用的函数:
collect(String dataIndex, [Boolean allowNull], [Boolean bypassFilter]):Array 获得指定的dataIndex对应的那一列的数据。当allowNull参数为true时,返回的结果中可能会包含null, undefined或空字符串,否则collect函数会自动将这些空数据过滤掉。当bypassFilter参数为true时,collect的结果不会受查询条件的影响,无论查询条件是什么都会忽略掉,返回的信息是所有的数据
getTotalCount():用于翻页时获得后台传递过来的数据总数。如果没有设置翻页,getTotalCount()结果与getCount()相同,都是返回当前的数据总数。
indexOf(Ext.data.Record record)和indexOfId(String id)函数根据record或record的id获得record对应的行号。
loadData(object data,[Boolean append])从本地JavaScript变量中读取数据,append为true时,将读取的数据附加到原数据后,否则执行整体更新。
Sum(String property, Number start, Number end):用于计算某一列从start到end的总数
MemoryProxy
MemoryProxy只能从JavaScript对象获得数据,可以直接把数组,或JSON和XML格式的数据交给它处理。
HttpProxy
HttpProxy使用Http协议,通过Ajax去后台取数据,构造它时需要设置
url:'xxx.jsp'参数。需要注意的是,HttpProxy不支持跨域,只能从同一域中获取数据。如果想跨域,参考ScriptTagProxy。
ScriptTagPrxoy
ScriptTagProxy的用法几乎和HttpProxy一样,var proxy = new Ext.data.ScriptTagProxy({url:'xxx.jsp'});
前台看不出它是如何支持跨域的,我们还需要在后台进行相应的处理,如:
1String cb = request.getParameter("callback");
2response.setContentType("text/javascript");
3Writer out = response.getWriter();
4out.write(cb + "(");
5out.print("[" +
6 "['id1','name1','descn1']" +
7 "['id2','name2','descn2']" +
8"]");
9out.wirte(");");
其中的关键就在于从请求中获得的callback参数,这个参数叫做回调函数。ScriptTagProxy会在当前的HTML页面添加一个<script type="text/javascript" scr="xxx.jsp"></script>标签,然后把后台返回的内容添加到这个标签中,这样就可以解决跨域访问数据的问题。为了让后台返回的内容可以再动态生成的标签中运行,EXT会生成一个名为callback的回调函数,并把回调函数的名称传递给后台,由后台生成callback(data)形式的响应内容,然后返回给前台自动运行。