Upgrade to ExtJS 4.0.0 - Released 04/26/2011
[extjs.git] / examples / form / checkout.js
1 Ext.require([
2     'Ext.form.*',
3     'Ext.data.*',
4     'Ext.window.MessageBox'
5 ]);
6
7 Ext.onReady(function() {
8
9     var formPanel,
10
11         // The data store for the State comboboxes
12         statesStore = Ext.create('Ext.data.ArrayStore', {
13             fields: ['abbr'],
14             data : Ext.example.states // from states.js
15         }),
16
17         // The data store for the Month combobox 
18         monthsStore = Ext.create('Ext.data.Store', {
19             fields: ['name', 'num'],
20             data: (function() {
21                 var data = [];
22                 Ext.Array.forEach(Ext.Date.monthNames, function(name, i) {
23                     data[i] = {name: name, num: i + 1};
24                 });
25                 return data;
26             })()
27         });
28
29     /**
30      * Common change listener for the Mailing Address fields - if the checkbox to use the same
31      * values for Billing Address is checked, this copies the values over as they change.
32      */
33     function onMailingAddrFieldChange(field) {
34         var copyToBilling = formPanel.down('[name=billingSameAsMailing]').getValue();
35         if (copyToBilling) {
36             formPanel.down('[name=' + field.billingFieldName + ']').setValue(field.getValue());
37         }
38     }
39
40
41     formPanel = Ext.widget('form', {
42         renderTo: Ext.getBody(),
43         title: 'Complete Check Out',
44         frame: true,
45         width: 550,
46         bodyPadding: 5,
47         fieldDefaults: {
48             labelAlign: 'right',
49             labelWidth: 90,
50             msgTarget: 'qtip'
51         },
52
53         items: [
54             // Contact info
55             {
56                 xtype: 'fieldset',
57                 title: 'Your Contact Information',
58                 defaultType: 'textfield',
59                 layout: 'anchor',
60                 defaults: {
61                     anchor: '100%'
62                 },
63                 items: [{
64                     xtype: 'fieldcontainer',
65                     fieldLabel: 'Name',
66                     layout: 'hbox',
67                     combineErrors: true,
68                     defaultType: 'textfield',
69                     defaults: {
70                         hideLabel: 'true'
71                     },
72                     items: [{
73                         name: 'firstName',
74                         fieldLabel: 'First Name',
75                         flex: 2,
76                         emptyText: 'First',
77                         allowBlank: false
78                     }, {
79                         name: 'lastName',
80                         fieldLabel: 'Last Name',
81                         flex: 3,
82                         margins: '0 0 0 6',
83                         emptyText: 'Last',
84                         allowBlank: false
85                     }]
86                 }, {
87                     xtype: 'container',
88                     layout: 'hbox',
89                     defaultType: 'textfield',
90                     items: [{
91                         fieldLabel: 'Email Address',
92                         name: 'email',
93                         vtype: 'email',
94                         flex: 1,
95                         allowBlank: false
96                     }, {
97                         fieldLabel: 'Phone Number',
98                         labelWidth: 100,
99                         name: 'phone',
100                         width: 190,
101                         emptyText: 'xxx-xxx-xxxx',
102                         maskRe: /[\d\-]/,
103                         regex: /^\d{3}-\d{3}-\d{4}$/,
104                         regexText: 'Must be in the format xxx-xxx-xxxx'
105                     }]
106                 }]
107             },
108
109             // Mailing Address
110             {
111                 xtype: 'fieldset',
112                 title: 'Mailing Address',
113                 defaultType: 'textfield',
114                 layout: 'anchor',
115                 defaults: {
116                     anchor: '100%'
117                 },
118                 items: [{
119                     fieldLabel: 'Street Address',
120                     name: 'mailingStreet',
121                     listeners: {change: onMailingAddrFieldChange},
122                     billingFieldName: 'billingStreet',
123                     allowBlank: false
124                 }, {
125                     xtype: 'container',
126                     layout: 'hbox',
127                     items: [{
128                         xtype: 'textfield',
129                         fieldLabel: 'City',
130                         name: 'mailingCity',
131                         listeners: {change: onMailingAddrFieldChange},
132                         billingFieldName: 'billingCity',
133                         flex: 1,
134                         allowBlank: false
135                     }, {
136                         xtype: 'combobox',
137                         name: 'mailingState',
138                         listeners: {change: onMailingAddrFieldChange},
139                         billingFieldName: 'billingState',
140                         fieldLabel: 'State',
141                         labelWidth: 50,
142                         width: 100,
143                         store: statesStore,
144                         valueField: 'abbr',
145                         displayField: 'abbr',
146                         typeAhead: true,
147                         queryMode: 'local',
148                         allowBlank: false,
149                         forceSelection: true
150                     }, {
151                         xtype: 'textfield',
152                         fieldLabel: 'Postal Code',
153                         labelWidth: 80,
154                         name: 'mailingPostalCode',
155                         listeners: {change: onMailingAddrFieldChange},
156                         billingFieldName: 'billingPostalCode',
157                         width: 160,
158                         allowBlank: false,
159                         maxLength: 10,
160                         enforceMaxLength: true,
161                         maskRe: /[\d\-]/,
162                         regex: /^\d{5}(\-\d{4})?$/,
163                         regexText: 'Must be in the format xxxxx or xxxxx-xxxx'
164                     }]
165                 }]
166             },
167
168             // Billing Address
169             {
170                 xtype: 'fieldset',
171                 title: 'Billing Address',
172                 layout: 'anchor',
173                 defaults: {
174                     anchor: '100%'
175                 },
176                 items: [{
177                     xtype: 'checkbox',
178                     name: 'billingSameAsMailing',
179                     boxLabel: 'Same as Mailing Address?',
180                     hideLabel: true,
181                     checked: true,
182                     style: 'margin-bottom:10px',
183
184                     /**
185                      * Enables or disables the billing address fields according to whether the checkbox is checked.
186                      * In addition to disabling the fields, they are animated to a low opacity so they don't take
187                      * up visual attention.
188                      */
189                     handler: function(me, checked) {
190                         var fieldset = me.ownerCt;
191                         Ext.Array.forEach(fieldset.previousSibling().query('textfield'), onMailingAddrFieldChange);
192                         Ext.Array.forEach(fieldset.query('textfield'), function(field) {
193                             field.setDisabled(checked);
194                             // Animate the opacity on each field. Would be more efficient to wrap them in a container
195                             // and animate the opacity on just the single container element, but IE has a bug where
196                             // the alpha filter does not get applied on position:relative children.
197                             field.el.animate({opacity: checked ? .3 : 1});
198                         });
199                     }
200                 }, {
201                     xtype: 'textfield',
202                     fieldLabel: 'Street Address',
203                     name: 'billingStreet',
204                     style: 'opacity:.3',
205                     disabled: true,
206                     allowBlank: false
207                 }, {
208                     xtype: 'container',
209                     layout: 'hbox',
210                     items: [{
211                         xtype: 'textfield',
212                         fieldLabel: 'City',
213                         name: 'billingCity',
214                         style: 'opacity:.3',
215                         flex: 1,
216                         disabled: true,
217                         allowBlank: false
218                     }, {
219                         xtype: 'combobox',
220                         name: 'billingState',
221                         style: 'opacity:.3',
222                         fieldLabel: 'State',
223                         labelWidth: 50,
224                         width: 100,
225                         store: statesStore,
226                         valueField: 'abbr',
227                         displayField: 'abbr',
228                         typeAhead: true,
229                         queryMode: 'local',
230                         disabled: true,
231                         allowBlank: false,
232                         forceSelection: true
233                     }, {
234                         xtype: 'textfield',
235                         fieldLabel: 'Postal Code',
236                         labelWidth: 80,
237                         name: 'billingPostalCode',
238                         style: 'opacity:.3',
239                         width: 160,
240                         disabled: true,
241                         allowBlank: false,
242                         maxLength: 10,
243                         enforceMaxLength: true,
244                         maskRe: /[\d\-]/,
245                         regex: /^\d{5}(\-\d{4})?$/,
246                         regexText: 'Must be in the format xxxxx or xxxxx-xxxx'
247                     }]
248                 }]
249             },
250
251             // Credit card info
252             {
253                 xtype: 'fieldset',
254                 title: 'Payment',
255                 layout: 'anchor',
256                 defaults: {
257                     anchor: '100%'
258                 },
259                 items: [{
260                     xtype: 'radiogroup',
261                     layout: 'hbox',
262                     defaults: {
263                         name: 'ccType',
264                         margins: '0 15 0 0'
265                     },
266                     items: [{
267                         inputValue: 'visa',
268                         boxLabel: 'VISA',
269                         checked: true
270                     }, {
271                         inputValue: 'mastercard',
272                         boxLabel: 'MasterCard'
273                     }, {
274                         inputValue: 'amex',
275                         boxLabel: 'American Express'
276                     }, {
277                         inputValue: 'discover',
278                         boxLabel: 'Discover'
279                     }]
280                 }, {
281                     xtype: 'textfield',
282                     name: 'ccName',
283                     fieldLabel: 'Name On Card',
284                     allowBlank: false
285                 }, {
286                     xtype: 'container',
287                     layout: 'hbox',
288                     items: [{
289                         xtype: 'textfield',
290                         name: 'ccNumber',
291                         fieldLabel: 'Card Number',
292                         flex: 1,
293                         allowBlank: false,
294                         minLength: 15,
295                         maxLength: 16,
296                         enforceMaxLength: true,
297                         maskRe: /\d/
298                     }, {
299                         xtype: 'fieldcontainer',
300                         fieldLabel: 'Expiration',
301                         labelWidth: 75,
302                         layout: 'hbox',
303                         width: 235,
304                         items: [{
305                             xtype: 'combobox',
306                             name: 'ccExpireMonth',
307                             displayField: 'name',
308                             valueField: 'num',
309                             queryMode: 'local',
310                             emptyText: 'Month',
311                             hideLabel: true,
312                             margins: '0 6 0 0',
313                             store: monthsStore,
314                             flex: 1,
315                             allowBlank: false,
316                             forceSelection: true
317                         }, {
318                             xtype: 'numberfield',
319                             name: 'ccExpireYear',
320                             hideLabel: true,
321                             width: 55,
322                             value: new Date().getFullYear(),
323                             minValue: new Date().getFullYear(),
324                             allowBlank: false
325                         }]
326                     }]
327                 }]
328             }
329         ],
330
331         buttons: [{
332             text: 'Reset',
333             handler: function() {
334                 this.up('form').getForm().reset();
335             }
336         }, {
337             text: 'Complete Purchase',
338             width: 150,
339             handler: function() {
340                 var form = this.up('form').getForm();
341                 if (form.isValid()) {
342                     Ext.MessageBox.alert('Submitted Values', form.getValues(true));
343                 }
344             }
345         }]
346
347     });
348
349 });