4 <meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
5 <title>The source code</title>
6 <link href="../prettify/prettify.css" type="text/css" rel="stylesheet" />
7 <script type="text/javascript" src="../prettify/prettify.js"></script>
8 <style type="text/css">
9 .highlight { display: block; background-color: #ddd; }
11 <script type="text/javascript">
12 function highlight() {
13 document.getElementById(location.hash.replace(/#/, "")).className = "highlight";
17 <body onload="prettyPrint(); highlight();">
18 <pre class="prettyprint lang-js"><span id='Ext-picker-Month-method-constructor'><span id='Ext-picker-Month'>/**
19 </span></span> * @private
20 * @class Ext.picker.Month
21 * @extends Ext.Component
22 * <p>A month picker component. This class is used by the {@link Ext.picker.Date DatePicker} class
23 * to allow browsing and selection of year/months combinations.</p>
25 * Create a new MonthPicker
26 * @param {Object} config The config object
30 Ext.define('Ext.picker.Month', {
31 extend: 'Ext.Component',
32 requires: ['Ext.XTemplate', 'Ext.util.ClickRepeater', 'Ext.Date', 'Ext.button.Button'],
33 alias: 'widget.monthpicker',
34 alternateClassName: 'Ext.MonthPicker',
37 '<div class="{baseCls}-body">',
38 '<div class="{baseCls}-months">',
39 '<tpl for="months">',
40 '<div class="{parent.baseCls}-item {parent.baseCls}-month"><a href="#" hidefocus="on">{.}</a></div>',
43 '<div class="{baseCls}-years">',
44 '<div class="{baseCls}-yearnav">',
45 '<button class="{baseCls}-yearnav-prev"></button>',
46 '<button class="{baseCls}-yearnav-next"></button>',
48 '<tpl for="years">',
49 '<div class="{parent.baseCls}-item {parent.baseCls}-year"><a href="#" hidefocus="on">{.}</a></div>',
53 '<div class="' + Ext.baseCSSPrefix + 'clear"></div>',
54 '<tpl if="showButtons">',
55 '<div class="{baseCls}-buttons"></div>',
59 <span id='Ext-picker-Month-cfg-okText'> /**
60 </span> * @cfg {String} okText The text to display on the ok button. Defaults to <tt>'OK'</tt>
64 <span id='Ext-picker-Month-cfg-cancelText'> /**
65 </span> * @cfg {String} cancelText The text to display on the cancel button. Defaults to <tt>'Cancel'</tt>
69 <span id='Ext-picker-Month-cfg-baseCls'> /**
70 </span> * @cfg {String} baseCls The base CSS class to apply to the picker element. Defaults to <tt>'x-monthpicker'</tt>
72 baseCls: Ext.baseCSSPrefix + 'monthpicker',
74 <span id='Ext-picker-Month-cfg-showButtons'> /**
75 </span> * @cfg {Boolean} showButtons True to show ok and cancel buttons below the picker. Defaults to <tt>true</tt>.
79 <span id='Ext-picker-Month-cfg-selectedCls'> /**
80 </span> * @cfg {String} selectedCls The class to be added to selected items in the picker. Defaults to
81 * <tt>'x-monthpicker-selected'</tt>
84 <span id='Ext-picker-Month-cfg-value'> /**
85 </span> * @cfg {Date/Array} value The default value to set. See {#setValue setValue}
95 yearOffset: 5, // 10 years in total, 2 per row
96 monthOffset: 6, // 12 months, 2 per row
98 // private, inherit docs
99 initComponent: function(){
102 me.selectedCls = me.baseCls + '-selected';
104 <span id='Ext-picker-Month-event-cancelclick'> /**
105 </span> * @event cancelclick
106 * Fires when the cancel button is pressed.
107 * @param {Ext.picker.Month} this
111 <span id='Ext-picker-Month-event-monthclick'> /**
112 </span> * @event monthclick
113 * Fires when a month is clicked.
114 * @param {Ext.picker.Month} this
115 * @param {Array} value The current value
119 <span id='Ext-picker-Month-event-monthdblclick'> /**
120 </span> * @event monthdblclick
121 * Fires when a month is clicked.
122 * @param {Ext.picker.Month} this
123 * @param {Array} value The current value
127 <span id='Ext-picker-Month-event-okclick'> /**
128 </span> * @event okclick
129 * Fires when the ok button is pressed.
130 * @param {Ext.picker.Month} this
131 * @param {Array} value The current value
135 <span id='Ext-picker-Month-event-select'> /**
136 </span> * @event select
137 * Fires when a month/year is selected.
138 * @param {Ext.picker.Month} this
139 * @param {Array} value The current value
143 <span id='Ext-picker-Month-event-yearclick'> /**
144 </span> * @event yearclick
145 * Fires when a year is clicked.
146 * @param {Ext.picker.Month} this
147 * @param {Array} value The current value
151 <span id='Ext-picker-Month-event-yeardblclick'> /**
152 </span> * @event yeardblclick
153 * Fires when a year is clicked.
154 * @param {Ext.picker.Month} this
155 * @param {Array} value The current value
160 me.setValue(me.value);
161 me.activeYear = me.getYear(new Date().getFullYear() - 4, -4);
165 // private, inherit docs
166 onRender: function(ct, position){
170 shortName = Ext.Date.getShortMonthName,
171 monthLen = me.monthOffset;
173 for (; i < monthLen; ++i) {
174 months.push(shortName(i), shortName(i + monthLen));
177 Ext.apply(me.renderData, {
179 years: me.getYears(),
180 showButtons: me.showButtons
183 Ext.apply(me.renderSelectors, {
184 bodyEl: '.' + me.baseCls + '-body',
185 prevEl: '.' + me.baseCls + '-yearnav-prev',
186 nextEl: '.' + me.baseCls + '-yearnav-next',
187 buttonsEl: '.' + me.baseCls + '-buttons'
189 this.callParent([ct, position]);
192 // private, inherit docs
193 afterRender: function(){
196 buttonsEl = me.buttonsEl;
200 me.mon(body, 'click', me.onBodyClick, me);
201 me.mon(body, 'dblclick', me.onBodyClick, me);
203 // keep a reference to the year/month elements since we'll be re-using them
204 me.years = body.select('.' + me.baseCls + '-year a');
205 me.months = body.select('.' + me.baseCls + '-month a');
207 if (me.showButtons) {
208 me.okBtn = Ext.create('Ext.button.Button', {
211 handler: me.onOkClick,
214 me.cancelBtn = Ext.create('Ext.button.Button', {
217 handler: me.onCancelClick,
222 me.backRepeater = Ext.create('Ext.util.ClickRepeater', me.prevEl, {
223 handler: Ext.Function.bind(me.adjustYear, me, [-me.totalYears])
226 me.prevEl.addClsOnOver(me.baseCls + '-yearnav-prev-over');
227 me.nextRepeater = Ext.create('Ext.util.ClickRepeater', me.nextEl, {
228 handler: Ext.Function.bind(me.adjustYear, me, [me.totalYears])
230 me.nextEl.addClsOnOver(me.baseCls + '-yearnav-next-over');
234 <span id='Ext-picker-Month-method-setValue'> /**
235 </span> * Set the value for the picker.
236 * @param {Date/Array} value The value to set. It can be a Date object, where the month/year will be extracted, or
237 * it can be an array, with the month as the first index and the year as the second.
238 * @return {Ext.picker.Month} this
240 setValue: function(value){
242 active = me.activeYear,
243 offset = me.monthOffset,
248 me.value = [null, null];
249 } else if (Ext.isDate(value)) {
250 me.value = [value.getMonth(), value.getFullYear()];
252 me.value = [value[0], value[1]];
258 if ((year < active || year > active + me.yearOffset)) {
259 me.activeYear = year - me.yearOffset + 1;
268 <span id='Ext-picker-Month-method-getValue'> /**
269 </span> * Gets the selected value. It is returned as an array [month, year]. It may
270 * be a partial value, for example [null, 2010]. The month is returned as
272 * @return {Array} The selected value
274 getValue: function(){
278 <span id='Ext-picker-Month-method-hasSelection'> /**
279 </span> * Checks whether the picker has a selection
280 * @return {Boolean} Returns true if both a month and year have been selected
282 hasSelection: function(){
283 var value = this.value;
284 return value[0] !== null && value[1] !== null;
287 <span id='Ext-picker-Month-method-getYears'> /**
288 </span> * Get an array of years to be pushed in the template. It is not in strict
289 * numerical order because we want to show them in columns.
291 * @return {Array} An array of years
293 getYears: function(){
295 offset = me.yearOffset,
296 start = me.activeYear, // put the "active" year on the left
297 end = start + offset,
301 for (; i < end; ++i) {
302 years.push(i, i + offset);
308 <span id='Ext-picker-Month-method-updateBody'> /**
309 </span> * Update the years in the body based on any change
312 updateBody: function(){
316 yearNumbers = me.getYears(),
317 cls = me.selectedCls,
318 value = me.getYear(null),
320 monthOffset = me.monthOffset,
324 years.removeCls(cls);
325 months.removeCls(cls);
326 years.each(function(el, all, index){
327 year = yearNumbers[index];
328 el.dom.innerHTML = year;
330 el.dom.className = cls;
333 if (month !== null) {
334 if (month < monthOffset) {
337 month = (month - monthOffset) * 2 + 1;
339 months.item(month).addCls(cls);
344 <span id='Ext-picker-Month-method-getYear'> /**
345 </span> * Gets the current year value, or the default.
347 * @param {Number} defaultValue The default value to use if the year is not defined.
348 * @param {Number} offset A number to offset the value by
349 * @return {Number} The year value
351 getYear: function(defaultValue, offset) {
352 var year = this.value[1];
353 offset = offset || 0;
354 return year === null ? defaultValue : year + offset;
357 <span id='Ext-picker-Month-method-onBodyClick'> /**
358 </span> * React to clicks on the body
361 onBodyClick: function(e, t) {
363 isDouble = e.type == 'dblclick';
365 if (e.getTarget('.' + me.baseCls + '-month')) {
367 me.onMonthClick(t, isDouble);
368 } else if (e.getTarget('.' + me.baseCls + '-year')) {
370 me.onYearClick(t, isDouble);
374 <span id='Ext-picker-Month-method-adjustYear'> /**
375 </span> * Modify the year display by passing an offset.
376 * @param {Number} offset The offset to move by. If not specified, it defaults to 10.
378 adjustYear: function(offset){
379 if (typeof offset != 'number') {
380 offset = this.totalYears;
382 this.activeYear += offset;
386 <span id='Ext-picker-Month-method-onOkClick'> /**
387 </span> * React to the ok button being pressed
390 onOkClick: function(){
391 this.fireEvent('okclick', this, this.value);
394 <span id='Ext-picker-Month-method-onCancelClick'> /**
395 </span> * React to the cancel button being pressed
398 onCancelClick: function(){
399 this.fireEvent('cancelclick', this);
402 <span id='Ext-picker-Month-method-onMonthClick'> /**
403 </span> * React to a month being clicked
405 * @param {HTMLElement} target The element that was clicked
406 * @param {Boolean} isDouble True if the event was a doubleclick
408 onMonthClick: function(target, isDouble){
410 me.value[0] = me.resolveOffset(me.months.indexOf(target), me.monthOffset);
412 me.fireEvent('month' + (isDouble ? 'dbl' : '') + 'click', me, me.value);
413 me.fireEvent('select', me, me.value);
416 <span id='Ext-picker-Month-method-onYearClick'> /**
417 </span> * React to a year being clicked
419 * @param {HTMLElement} target The element that was clicked
420 * @param {Boolean} isDouble True if the event was a doubleclick
422 onYearClick: function(target, isDouble){
424 me.value[1] = me.activeYear + me.resolveOffset(me.years.indexOf(target), me.yearOffset);
426 me.fireEvent('year' + (isDouble ? 'dbl' : '') + 'click', me, me.value);
427 me.fireEvent('select', me, me.value);
431 <span id='Ext-picker-Month-method-resolveOffset'> /**
432 </span> * Returns an offsetted number based on the position in the collection. Since our collections aren't
433 * numerically ordered, this function helps to normalize those differences.
435 * @param {Object} index
436 * @param {Object} offset
437 * @return {Number} The correctly offsetted number
439 resolveOffset: function(index, offset){
440 if (index % 2 === 0) {
443 return offset + Math.floor(index / 2);
447 // private, inherit docs
448 beforeDestroy: function(){
450 me.years = me.months = null;
451 Ext.destroyMembers('backRepeater', 'nextRepeater', 'okBtn', 'cancelBtn');