Subversion Repositories eFlore/Applications.cel

Rev

Go to most recent revision | Details | Last modification | View Log | RSS feed

Rev Author Line No. Line
27 jpm 1
/*
2
 * Ext JS Library 2.0.2
3
 * Copyright(c) 2006-2008, Ext JS, LLC.
4
 * licensing@extjs.com
5
 *
6
 * http://extjs.com/license
7
 */
8
 
9
/**
10
 * @class Ext.JsonView
11
 * @extends Ext.View
12
 * Shortcut class to create a JSON + {@link Ext.Updater} template view. Usage:
13
<pre><code>
14
var view = new Ext.JsonView("my-element",
15
    '&lt;div id="{id}"&gt;{foo} - {bar}&lt;/div&gt;', // auto create template
16
    { multiSelect: true, jsonRoot: "data" }
17
);
18
 
19
// listen for node click?
20
view.on("click", function(vw, index, node, e){
21
    alert('Node "' + node.id + '" at index: ' + index + " was clicked.");
22
});
23
 
24
// direct load of JSON data
25
view.load("foobar.php");
26
 
27
// Example from my blog list
28
var tpl = new Ext.Template(
29
    '&lt;div class="entry"&gt;' +
30
    '&lt;a class="entry-title" href="{link}"&gt;{title}&lt;/a&gt;' +
31
    "&lt;h4&gt;{date} by {author} | {comments} Comments&lt;/h4&gt;{description}" +
32
    "&lt;/div&gt;&lt;hr /&gt;"
33
);
34
 
35
var moreView = new Ext.JsonView("entry-list", tpl, {
36
    jsonRoot: "posts"
37
});
38
moreView.on("beforerender", this.sortEntries, this);
39
moreView.load({
40
    url: "/blog/get-posts.php",
41
    params: "allposts=true",
42
    text: "Loading Blog Entries..."
43
});
44
</code></pre>
45
 * @constructor
46
 * Create a new JsonView
47
 * @param {Mixed} container The container element where the view is to be rendered.
48
 * @param {Template} tpl The rendering template
49
 * @param {Object} config The config object
50
 */
51
Ext.JsonView = function(container, tpl, config){
52
    Ext.JsonView.superclass.constructor.call(this, container, tpl, config);
53
 
54
    var um = this.el.getUpdater();
55
    um.setRenderer(this);
56
    um.on("update", this.onLoad, this);
57
    um.on("failure", this.onLoadException, this);
58
 
59
    /**
60
     * @event beforerender
61
     * Fires before rendering of the downloaded JSON data.
62
     * @param {Ext.JsonView} this
63
     * @param {Object} data The JSON data loaded
64
     */
65
    /**
66
     * @event load
67
     * Fires when data is loaded.
68
     * @param {Ext.JsonView} this
69
     * @param {Object} data The JSON data loaded
70
     * @param {Object} response The raw Connect response object
71
     */
72
    /**
73
     * @event loadexception
74
     * Fires when loading fails.
75
     * @param {Ext.JsonView} this
76
     * @param {Object} response The raw Connect response object
77
     */
78
    this.addEvents({
79
        'beforerender' : true,
80
        'load' : true,
81
        'loadexception' : true
82
    });
83
};
84
Ext.extend(Ext.JsonView, Ext.View, {
85
    /**
86
     * The root property in the loaded JSON object that contains the data
87
     * @type {String}
88
     */
89
    jsonRoot : "",
90
 
91
    /**
92
     * Refreshes the view.
93
     */
94
    refresh : function(){
95
        this.clearSelections();
96
        this.el.update("");
97
        var html = [];
98
        var o = this.jsonData;
99
        if(o && o.length > 0){
100
            for(var i = 0, len = o.length; i < len; i++){
101
                var data = this.prepareData(o[i], i, o);
102
                html[html.length] = this.tpl.apply(data);
103
            }
104
        }else{
105
            html.push(this.emptyText);
106
        }
107
        this.el.update(html.join(""));
108
        this.nodes = this.el.dom.childNodes;
109
        this.updateIndexes(0);
110
    },
111
 
112
    /**
113
     * Performs an async HTTP request, and loads the JSON from the response. If <i>params</i> are specified it uses POST, otherwise it uses GET.
114
     * @param {Object/String/Function} url The URL for this request, or a function to call to get the URL, or a config object containing any of the following options:
115
     <pre><code>
116
     view.load({
117
         url: "your-url.php",
118
         params: {param1: "foo", param2: "bar"}, // or a URL encoded string
119
         callback: yourFunction,
120
         scope: yourObject, //(optional scope)
121
         discardUrl: false,
122
         nocache: false,
123
         text: "Loading...",
124
         timeout: 30,
125
         scripts: false
126
     });
127
     </code></pre>
128
     * The only required property is <i>url</i>. The optional properties <i>nocache</i>, <i>text</i> and <i>scripts</i>
129
     * are shorthand for <i>disableCaching</i>, <i>indicatorText</i> and <i>loadScripts</i> and are used to set their associated property on this Updater instance.
130
     * @param {String/Object} params (optional) The parameters to pass, as either a URL encoded string "param1=1&amp;param2=2" or an object {param1: 1, param2: 2}
131
     * @param {Function} callback (optional) Callback when transaction is complete - called with signature (oElement, bSuccess)
132
     * @param {Boolean} discardUrl (optional) By default when you execute an update the defaultUrl is changed to the last used URL. If true, it will not store the URL.
133
     */
134
    load : function(){
135
        var um = this.el.getUpdater();
136
        um.update.apply(um, arguments);
137
    },
138
 
139
    render : function(el, response){
140
        this.clearSelections();
141
        this.el.update("");
142
        var o;
143
        try{
144
            o = Ext.util.JSON.decode(response.responseText);
145
            if(this.jsonRoot){
146
                o = eval("o." + this.jsonRoot);
147
            }
148
        } catch(e){
149
        }
150
        /**
151
         * The current JSON data or null
152
         */
153
        this.jsonData = o;
154
        this.beforeRender();
155
        this.refresh();
156
    },
157
 
158
/**
159
 * Get the number of records in the current JSON dataset
160
 * @return {Number}
161
 */
162
    getCount : function(){
163
        return this.jsonData ? this.jsonData.length : 0;
164
    },
165
 
166
/**
167
 * Returns the JSON object for the specified node(s)
168
 * @param {HTMLElement/Array} node The node or an array of nodes
169
 * @return {Object/Array} If you pass in an array, you get an array back, otherwise
170
 * you get the JSON object for the node
171
 */
172
    getNodeData : function(node){
173
        if(Ext.isArray(node)){
174
            var data = [];
175
            for(var i = 0, len = node.length; i < len; i++){
176
                data.push(this.getNodeData(node[i]));
177
            }
178
            return data;
179
        }
180
        return this.jsonData[this.indexOf(node)] || null;
181
    },
182
 
183
    beforeRender : function(){
184
        this.snapshot = this.jsonData;
185
        if(this.sortInfo){
186
            this.sort.apply(this, this.sortInfo);
187
        }
188
        this.fireEvent("beforerender", this, this.jsonData);
189
    },
190
 
191
    onLoad : function(el, o){
192
        this.fireEvent("load", this, this.jsonData, o);
193
    },
194
 
195
    onLoadException : function(el, o){
196
        this.fireEvent("loadexception", this, o);
197
    },
198
 
199
/**
200
 * Filter the data by a specific property.
201
 * @param {String} property A property on your JSON objects
202
 * @param {String/RegExp} value Either string that the property values
203
 * should start with, or a RegExp to test against the property
204
 */
205
    filter : function(property, value){
206
        if(this.jsonData){
207
            var data = [];
208
            var ss = this.snapshot;
209
            if(typeof value == "string"){
210
                var vlen = value.length;
211
                if(vlen == 0){
212
                    this.clearFilter();
213
                    return;
214
                }
215
                value = value.toLowerCase();
216
                for(var i = 0, len = ss.length; i < len; i++){
217
                    var o = ss[i];
218
                    if(o[property].substr(0, vlen).toLowerCase() == value){
219
                        data.push(o);
220
                    }
221
                }
222
            } else if(value.exec){ // regex?
223
                for(var i = 0, len = ss.length; i < len; i++){
224
                    var o = ss[i];
225
                    if(value.test(o[property])){
226
                        data.push(o);
227
                    }
228
                }
229
            } else{
230
                return;
231
            }
232
            this.jsonData = data;
233
            this.refresh();
234
        }
235
    },
236
 
237
/**
238
 * Filter by a function. The passed function will be called with each
239
 * object in the current dataset. If the function returns true the value is kept,
240
 * otherwise it is filtered.
241
 * @param {Function} fn
242
 * @param {Object} scope (optional) The scope of the function (defaults to this JsonView)
243
 */
244
    filterBy : function(fn, scope){
245
        if(this.jsonData){
246
            var data = [];
247
            var ss = this.snapshot;
248
            for(var i = 0, len = ss.length; i < len; i++){
249
                var o = ss[i];
250
                if(fn.call(scope || this, o)){
251
                    data.push(o);
252
                }
253
            }
254
            this.jsonData = data;
255
            this.refresh();
256
        }
257
    },
258
 
259
/**
260
 * Clears the current filter.
261
 */
262
    clearFilter : function(){
263
        if(this.snapshot && this.jsonData != this.snapshot){
264
            this.jsonData = this.snapshot;
265
            this.refresh();
266
        }
267
    },
268
 
269
 
270
/**
271
 * Sorts the data for this view and refreshes it.
272
 * @param {String} property A property on your JSON objects to sort on
273
 * @param {String} direction (optional) "desc" or "asc" (defaults to "asc")
274
 * @param {Function} sortType (optional) A function to call to convert the data to a sortable value.
275
 */
276
    sort : function(property, dir, sortType){
277
        this.sortInfo = Array.prototype.slice.call(arguments, 0);
278
        if(this.jsonData){
279
            var p = property;
280
            var dsc = dir && dir.toLowerCase() == "desc";
281
            var f = function(o1, o2){
282
                var v1 = sortType ? sortType(o1[p]) : o1[p];
283
                var v2 = sortType ? sortType(o2[p]) : o2[p];
284
                ;
285
                if(v1 < v2){
286
                    return dsc ? +1 : -1;
287
                } else if(v1 > v2){
288
                    return dsc ? -1 : +1;
289
                } else{
290
                    return 0;
291
                }
292
            };
293
            this.jsonData.sort(f);
294
            this.refresh();
295
            if(this.jsonData != this.snapshot){
296
                this.snapshot.sort(f);
297
            }
298
        }
299
    }
300
});