Upgrade to ExtJS 4.0.7 - Released 10/19/2011
[extjs.git] / docs / source / GroupingSummary.html
1 <!DOCTYPE html>
2 <html>
3 <head>
4   <meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
5   <title>The source code</title>
6   <link href="../resources/prettify/prettify.css" type="text/css" rel="stylesheet" />
7   <script type="text/javascript" src="../resources/prettify/prettify.js"></script>
8   <style type="text/css">
9     .highlight { display: block; background-color: #ddd; }
10   </style>
11   <script type="text/javascript">
12     function highlight() {
13       document.getElementById(location.hash.replace(/#/, "")).className = "highlight";
14     }
15   </script>
16 </head>
17 <body onload="prettyPrint(); highlight();">
18   <pre class="prettyprint lang-js"><span id='Ext-grid-feature-GroupingSummary'>/**
19 </span> * @class Ext.grid.feature.GroupingSummary
20  * @extends Ext.grid.feature.Grouping
21  *
22  * This feature adds an aggregate summary row at the bottom of each group that is provided
23  * by the {@link Ext.grid.feature.Grouping} feature. There are two aspects to the summary:
24  *
25  * ## Calculation
26  *
27  * The summary value needs to be calculated for each column in the grid. This is controlled
28  * by the summaryType option specified on the column. There are several built in summary types,
29  * which can be specified as a string on the column configuration. These call underlying methods
30  * on the store:
31  *
32  *  - {@link Ext.data.Store#count count}
33  *  - {@link Ext.data.Store#sum sum}
34  *  - {@link Ext.data.Store#min min}
35  *  - {@link Ext.data.Store#max max}
36  *  - {@link Ext.data.Store#average average}
37  *
38  * Alternatively, the summaryType can be a function definition. If this is the case,
39  * the function is called with an array of records to calculate the summary value.
40  *
41  * ## Rendering
42  *
43  * Similar to a column, the summary also supports a summaryRenderer function. This
44  * summaryRenderer is called before displaying a value. The function is optional, if
45  * not specified the default calculated value is shown. The summaryRenderer is called with:
46  *
47  *  - value {Object} - The calculated value.
48  *  - summaryData {Object} - Contains all raw summary values for the row.
49  *  - field {String} - The name of the field we are calculating
50  *
51  * ## Example Usage
52  *
53  *     @example
54  *     Ext.define('TestResult', {
55  *         extend: 'Ext.data.Model',
56  *         fields: ['student', 'subject', {
57  *             name: 'mark',
58  *             type: 'int'
59  *         }]
60  *     });
61  *
62  *     Ext.create('Ext.grid.Panel', {
63  *         width: 200,
64  *         height: 240,
65  *         renderTo: document.body,
66  *         features: [{
67  *             groupHeaderTpl: 'Subject: {name}',
68  *             ftype: 'groupingsummary'
69  *         }],
70  *         store: {
71  *             model: 'TestResult',
72  *             groupField: 'subject',
73  *             data: [{
74  *                 student: 'Student 1',
75  *                 subject: 'Math',
76  *                 mark: 84
77  *             },{
78  *                 student: 'Student 1',
79  *                 subject: 'Science',
80  *                 mark: 72
81  *             },{
82  *                 student: 'Student 2',
83  *                 subject: 'Math',
84  *                 mark: 96
85  *             },{
86  *                 student: 'Student 2',
87  *                 subject: 'Science',
88  *                 mark: 68
89  *             }]
90  *         },
91  *         columns: [{
92  *             dataIndex: 'student',
93  *             text: 'Name',
94  *             summaryType: 'count',
95  *             summaryRenderer: function(value){
96  *                 return Ext.String.format('{0} student{1}', value, value !== 1 ? 's' : '');
97  *             }
98  *         }, {
99  *             dataIndex: 'mark',
100  *             text: 'Mark',
101  *             summaryType: 'average'
102  *         }]
103  *     });
104  */
105 Ext.define('Ext.grid.feature.GroupingSummary', {
106
107     /* Begin Definitions */
108
109     extend: 'Ext.grid.feature.Grouping',
110
111     alias: 'feature.groupingsummary',
112
113     mixins: {
114         summary: 'Ext.grid.feature.AbstractSummary'
115     },
116
117     /* End Definitions */
118
119
120 <span id='Ext-grid-feature-GroupingSummary-method-getFeatureTpl'>   /**
121 </span>    * Modifies the row template to include the summary row.
122     * @private
123     * @return {String} The modified template
124     */
125    getFeatureTpl: function() {
126         var tpl = this.callParent(arguments);
127
128         if (this.showSummaryRow) {
129             // lop off the end &lt;/tpl&gt; so we can attach it
130             tpl = tpl.replace('&lt;/tpl&gt;', '');
131             tpl += '{[this.printSummaryRow(xindex)]}&lt;/tpl&gt;';
132         }
133         return tpl;
134     },
135
136 <span id='Ext-grid-feature-GroupingSummary-method-getFragmentTpl'>    /**
137 </span>     * Gets any fragments needed for the template.
138      * @private
139      * @return {Object} The fragments
140      */
141     getFragmentTpl: function() {
142         var me = this,
143             fragments = me.callParent();
144
145         Ext.apply(fragments, me.getSummaryFragments());
146         if (me.showSummaryRow) {
147             // this gets called before render, so we'll setup the data here.
148             me.summaryGroups = me.view.store.getGroups();
149             me.summaryData = me.generateSummaryData();
150         }
151         return fragments;
152     },
153
154 <span id='Ext-grid-feature-GroupingSummary-method-getPrintData'>    /**
155 </span>     * Gets the data for printing a template row
156      * @private
157      * @param {Number} index The index in the template
158      * @return {Array} The template values
159      */
160     getPrintData: function(index){
161         var me = this,
162             columns = me.view.headerCt.getColumnsForTpl(),
163             i = 0,
164             length = columns.length,
165             data = [],
166             name = me.summaryGroups[index - 1].name,
167             active = me.summaryData[name],
168             column;
169
170         for (; i &lt; length; ++i) {
171             column = columns[i];
172             column.gridSummaryValue = this.getColumnValue(column, active);
173             data.push(column);
174         }
175         return data;
176     },
177
178 <span id='Ext-grid-feature-GroupingSummary-method-generateSummaryData'>    /**
179 </span>     * Generates all of the summary data to be used when processing the template
180      * @private
181      * @return {Object} The summary data
182      */
183     generateSummaryData: function(){
184         var me = this,
185             data = {},
186             remoteData = {},
187             store = me.view.store,
188             groupField = this.getGroupField(),
189             reader = store.proxy.reader,
190             groups = me.summaryGroups,
191             columns = me.view.headerCt.getColumnsForTpl(),
192             remote,
193             i,
194             length,
195             fieldData,
196             root,
197             key,
198             comp;
199
200         for (i = 0, length = groups.length; i &lt; length; ++i) {
201             data[groups[i].name] = {};
202         }
203
204 <span id='Ext-grid-feature-GroupingSummary-cfg-remoteRoot'>        /**
205 </span>         * @cfg {String} [remoteRoot=undefined]  The name of the property which contains the Array of
206          * summary objects. It allows to use server-side calculated summaries.
207          */
208         if (me.remoteRoot &amp;&amp; reader.rawData) {
209             // reset reader root and rebuild extractors to extract summaries data
210             root = reader.root;
211             reader.root = me.remoteRoot;
212             reader.buildExtractors(true);
213             Ext.Array.each(reader.getRoot(reader.rawData), function(value) {
214                  remoteData[value[groupField]] = value;
215             });
216             // restore initial reader configuration
217             reader.root = root;
218             reader.buildExtractors(true);
219         }
220
221         for (i = 0, length = columns.length; i &lt; length; ++i) {
222             comp = Ext.getCmp(columns[i].id);
223             fieldData = me.getSummary(store, comp.summaryType, comp.dataIndex, true);
224
225             for (key in fieldData) {
226                 if (fieldData.hasOwnProperty(key)) {
227                     data[key][comp.id] = fieldData[key];
228                 }
229             }
230
231             for (key in remoteData) {
232                 if (remoteData.hasOwnProperty(key)) {
233                     remote = remoteData[key][comp.dataIndex];
234                     if (remote !== undefined &amp;&amp; data[key] !== undefined) {
235                         data[key][comp.id] = remote;
236                     }
237                 }
238             }
239         }
240         return data;
241     }
242 });
243 </pre>
244 </body>
245 </html>