pickadate-rails 1.3.2 → 1.4.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/README.md +1 -1
- data/Rakefile +2 -2
- data/lib/pickadate-rails/version.rb +1 -1
- data/vendor/assets/javascripts/pickadate/picker.date.js +456 -240
- data/vendor/assets/javascripts/pickadate/picker.js +282 -169
- data/vendor/assets/javascripts/pickadate/picker.time.js +457 -234
- data/vendor/assets/javascripts/pickadate/translations/es_ES.js +3 -3
- data/vendor/assets/javascripts/pickadate/translations/gl_ES.js +13 -0
- data/vendor/assets/javascripts/pickadate/translations/is_IS.js +13 -0
- data/vendor/assets/javascripts/pickadate/translations/sl_SI.js +13 -0
- data/vendor/assets/stylesheets/pickadate/classic.date.css +0 -1
- data/vendor/assets/stylesheets/pickadate/default.date.css +0 -1
- metadata +15 -12
@@ -1,21 +1,11 @@
|
|
1
1
|
|
2
2
|
/*!
|
3
|
-
* pickadate.js v3.
|
3
|
+
* pickadate.js v3.4.0, 2014/02/15
|
4
4
|
* By Amsul, http://amsul.ca
|
5
5
|
* Hosted on http://amsul.github.io/pickadate.js
|
6
6
|
* Licensed under MIT
|
7
7
|
*/
|
8
8
|
|
9
|
-
/*jshint
|
10
|
-
debug: true,
|
11
|
-
devel: true,
|
12
|
-
browser: true,
|
13
|
-
asi: true,
|
14
|
-
unused: true,
|
15
|
-
boss: true,
|
16
|
-
eqnull: true
|
17
|
-
*/
|
18
|
-
|
19
9
|
(function ( factory ) {
|
20
10
|
|
21
11
|
// Register as an anonymous module.
|
@@ -42,7 +32,7 @@ function PickerConstructor( ELEMENT, NAME, COMPONENT, OPTIONS ) {
|
|
42
32
|
var
|
43
33
|
// The state of the picker.
|
44
34
|
STATE = {
|
45
|
-
id: Math.abs( ~~(
|
35
|
+
id: ELEMENT.id || 'P' + Math.abs( ~~(Math.random() * new Date()) )
|
46
36
|
},
|
47
37
|
|
48
38
|
|
@@ -93,162 +83,26 @@ function PickerConstructor( ELEMENT, NAME, COMPONENT, OPTIONS ) {
|
|
93
83
|
ELEMENT.autofocus = ELEMENT == document.activeElement
|
94
84
|
ELEMENT.type = 'text'
|
95
85
|
ELEMENT.readOnly = !SETTINGS.editable
|
86
|
+
ELEMENT.id = ELEMENT.id || STATE.id
|
96
87
|
|
97
88
|
|
98
89
|
// Create a new picker component with the settings.
|
99
|
-
P.component = new COMPONENT(
|
100
|
-
|
101
|
-
|
102
|
-
// Create the picker root with a new wrapped holder and bind the events.
|
103
|
-
P.$root = $( PickerConstructor._.node( 'div', createWrappedComponent(), CLASSES.picker ) ).
|
104
|
-
on({
|
105
|
-
|
106
|
-
// When something within the root is focused, stop from bubbling
|
107
|
-
// to the doc and remove the “focused” state from the root.
|
108
|
-
focusin: function( event ) {
|
109
|
-
P.$root.removeClass( CLASSES.focused )
|
110
|
-
event.stopPropagation()
|
111
|
-
},
|
112
|
-
|
113
|
-
// When something within the root holder is clicked, stop it
|
114
|
-
// from bubbling to the doc.
|
115
|
-
'mousedown click': function( event ) {
|
116
|
-
|
117
|
-
var target = event.target
|
118
|
-
|
119
|
-
// Make sure the target isn’t the root holder so it can bubble up.
|
120
|
-
if ( target != P.$root.children()[ 0 ] ) {
|
121
|
-
|
122
|
-
event.stopPropagation()
|
90
|
+
P.component = new COMPONENT(P, SETTINGS)
|
123
91
|
|
124
|
-
// * For mousedown events, cancel the default action in order to
|
125
|
-
// prevent cases where focus is shifted onto external elements
|
126
|
-
// when using things like jQuery mobile or MagnificPopup (ref: #249 & #120).
|
127
|
-
// Also, for Firefox, don’t prevent action on the `option` element.
|
128
|
-
if ( event.type == 'mousedown' && !$( target ).is( ':input' ) && target.nodeName != 'OPTION' ) {
|
129
92
|
|
130
|
-
|
131
|
-
|
132
|
-
|
133
|
-
// from elements focused within the picker.
|
134
|
-
ELEMENT.focus()
|
135
|
-
}
|
136
|
-
}
|
137
|
-
}
|
138
|
-
}).
|
139
|
-
|
140
|
-
// If there’s a click on an actionable element, carry out the actions.
|
141
|
-
on( 'click', '[data-pick], [data-nav], [data-clear]', function() {
|
142
|
-
|
143
|
-
var $target = $( this ),
|
144
|
-
targetData = $target.data(),
|
145
|
-
targetDisabled = $target.hasClass( CLASSES.navDisabled ) || $target.hasClass( CLASSES.disabled ),
|
146
|
-
|
147
|
-
// * For IE, non-focusable elements can be active elements as well
|
148
|
-
// (http://stackoverflow.com/a/2684561).
|
149
|
-
activeElement = document.activeElement
|
150
|
-
activeElement = activeElement && ( activeElement.type || activeElement.href )
|
151
|
-
|
152
|
-
// If it’s disabled or nothing inside is actively focused, re-focus the element.
|
153
|
-
if ( targetDisabled || activeElement && !$.contains( P.$root[0], activeElement ) ) {
|
154
|
-
ELEMENT.focus()
|
155
|
-
}
|
156
|
-
|
157
|
-
// If something is superficially changed, update the `highlight` based on the `nav`.
|
158
|
-
if ( targetData.nav && !targetDisabled ) {
|
159
|
-
P.set( 'highlight', P.component.item.highlight, { nav: targetData.nav } )
|
160
|
-
}
|
161
|
-
|
162
|
-
// If something is picked, set `select` then close with focus.
|
163
|
-
else if ( PickerConstructor._.isInteger( targetData.pick ) && !targetDisabled ) {
|
164
|
-
P.set( 'select', targetData.pick ).close( true )
|
165
|
-
}
|
166
|
-
|
167
|
-
// If a “clear” button is pressed, empty the values and close with focus.
|
168
|
-
else if ( targetData.clear ) {
|
169
|
-
P.clear().close( true )
|
170
|
-
}
|
171
|
-
}) //P.$root
|
93
|
+
// Create the picker root with a holder and then prepare it.
|
94
|
+
P.$root = $( PickerConstructor._.node('div', createWrappedComponent(), CLASSES.picker, 'id="' + ELEMENT.id + '_root"') )
|
95
|
+
prepareElementRoot()
|
172
96
|
|
173
97
|
|
174
98
|
// If there’s a format for the hidden input element, create the element.
|
175
99
|
if ( SETTINGS.formatSubmit ) {
|
176
|
-
|
177
|
-
P._hidden = $(
|
178
|
-
'<input ' +
|
179
|
-
'type=hidden ' +
|
180
|
-
|
181
|
-
// Create the name by using the original input plus a prefix and suffix.
|
182
|
-
'name="' + ( typeof SETTINGS.hiddenPrefix == 'string' ? SETTINGS.hiddenPrefix : '' ) +
|
183
|
-
ELEMENT.name +
|
184
|
-
( typeof SETTINGS.hiddenSuffix == 'string' ? SETTINGS.hiddenSuffix : '_submit' ) +
|
185
|
-
'"' +
|
186
|
-
|
187
|
-
// If the element has a value, set the hidden value as well.
|
188
|
-
( $ELEMENT.data( 'value' ) || ELEMENT.value ?
|
189
|
-
' value="' + PickerConstructor._.trigger( P.component.formats.toString, P.component, [ SETTINGS.formatSubmit, P.component.item.select ] ) + '"' :
|
190
|
-
''
|
191
|
-
) +
|
192
|
-
'>'
|
193
|
-
)[ 0 ]
|
100
|
+
prepareElementHidden()
|
194
101
|
}
|
195
102
|
|
196
103
|
|
197
104
|
// Prepare the input element.
|
198
|
-
|
199
|
-
|
200
|
-
// Store the picker data by component name.
|
201
|
-
data( NAME, P ).
|
202
|
-
|
203
|
-
// Add the “input” class name.
|
204
|
-
addClass( CLASSES.input ).
|
205
|
-
|
206
|
-
// If there’s a `data-value`, update the value of the element.
|
207
|
-
val( $ELEMENT.data( 'value' ) ? PickerConstructor._.trigger( P.component.formats.toString, P.component, [ SETTINGS.format, P.component.item.select ] ) : ELEMENT.value ).
|
208
|
-
|
209
|
-
// Insert the hidden input after the element.
|
210
|
-
after( P._hidden ).
|
211
|
-
|
212
|
-
// On focus/click, open the picker and adjust the root “focused” state.
|
213
|
-
on( 'focus.P' + STATE.id + ' click.P' + STATE.id, focusToOpen ).
|
214
|
-
|
215
|
-
// If the value changes, update the hidden input with the correct format.
|
216
|
-
on( 'change.P' + STATE.id, function() {
|
217
|
-
if ( P._hidden ) {
|
218
|
-
P._hidden.value = ELEMENT.value ? PickerConstructor._.trigger( P.component.formats.toString, P.component, [ SETTINGS.formatSubmit, P.component.item.select ] ) : ''
|
219
|
-
}
|
220
|
-
})
|
221
|
-
|
222
|
-
// Only bind keydown events if the element isn’t editable.
|
223
|
-
if ( !SETTINGS.editable ) $ELEMENT.
|
224
|
-
|
225
|
-
// Handle keyboard event based on the picker being opened or not.
|
226
|
-
on( 'keydown.P' + STATE.id, function( event ) {
|
227
|
-
|
228
|
-
var keycode = event.keyCode,
|
229
|
-
|
230
|
-
// Check if one of the delete keys was pressed.
|
231
|
-
isKeycodeDelete = /^(8|46)$/.test( keycode )
|
232
|
-
|
233
|
-
// For some reason IE clears the input value on “escape”.
|
234
|
-
if ( keycode == 27 ) {
|
235
|
-
P.close()
|
236
|
-
return false
|
237
|
-
}
|
238
|
-
|
239
|
-
// Check if `space` or `delete` was pressed or the picker is closed with a key movement.
|
240
|
-
if ( keycode == 32 || isKeycodeDelete || !STATE.open && P.component.key[ keycode ] ) {
|
241
|
-
|
242
|
-
// Prevent it from moving the page and bubbling to doc.
|
243
|
-
event.preventDefault()
|
244
|
-
event.stopPropagation()
|
245
|
-
|
246
|
-
// If `delete` was pressed, clear the values and close the picker.
|
247
|
-
// Otherwise open the picker.
|
248
|
-
if ( isKeycodeDelete ) { P.clear().close() }
|
249
|
-
else { P.open() }
|
250
|
-
}
|
251
|
-
})
|
105
|
+
prepareElement()
|
252
106
|
|
253
107
|
|
254
108
|
// Insert the root as specified in the settings.
|
@@ -322,7 +176,7 @@ function PickerConstructor( ELEMENT, NAME, COMPONENT, OPTIONS ) {
|
|
322
176
|
// the events (after a tick for IE - see `P.close`).
|
323
177
|
$ELEMENT.removeClass( CLASSES.input ).removeData( NAME )
|
324
178
|
setTimeout( function() {
|
325
|
-
$ELEMENT.off( '.
|
179
|
+
$ELEMENT.off( '.' + STATE.id )
|
326
180
|
}, 0)
|
327
181
|
|
328
182
|
// Restore the element state
|
@@ -350,9 +204,11 @@ function PickerConstructor( ELEMENT, NAME, COMPONENT, OPTIONS ) {
|
|
350
204
|
|
351
205
|
// Add the “active” class.
|
352
206
|
$ELEMENT.addClass( CLASSES.active )
|
207
|
+
aria( ELEMENT, 'expanded', true )
|
353
208
|
|
354
209
|
// Add the “opened” class to the picker root.
|
355
210
|
P.$root.addClass( CLASSES.opened )
|
211
|
+
aria( P.$root[0], 'hidden', false )
|
356
212
|
|
357
213
|
// If we have to give focus, bind the element and doc events.
|
358
214
|
if ( dontGiveFocus !== false ) {
|
@@ -364,7 +220,7 @@ function PickerConstructor( ELEMENT, NAME, COMPONENT, OPTIONS ) {
|
|
364
220
|
$ELEMENT.trigger( 'focus' )
|
365
221
|
|
366
222
|
// Bind the document events.
|
367
|
-
$document.on( 'click.
|
223
|
+
$document.on( 'click.' + STATE.id + ' focusin.' + STATE.id, function( event ) {
|
368
224
|
|
369
225
|
var target = event.target
|
370
226
|
|
@@ -372,14 +228,17 @@ function PickerConstructor( ELEMENT, NAME, COMPONENT, OPTIONS ) {
|
|
372
228
|
// * Don’t worry about clicks or focusins on the root because those don’t bubble up.
|
373
229
|
// Also, for Firefox, a click on an `option` element bubbles up directly
|
374
230
|
// to the doc. So make sure the target wasn't the doc.
|
375
|
-
|
231
|
+
// * In Firefox stopPropagation() doesn’t prevent right-click events from bubbling,
|
232
|
+
// which causes the picker to unexpectedly close when right-clicking it. So make
|
233
|
+
// sure the event wasn’t a right-click.
|
234
|
+
if ( target != ELEMENT && target != document && event.which != 3 ) {
|
376
235
|
|
377
236
|
// If the target was the holder that covers the screen,
|
378
237
|
// keep the element focused to maintain tabindex.
|
379
238
|
P.close( target === P.$root.children()[0] )
|
380
239
|
}
|
381
240
|
|
382
|
-
}).on( 'keydown.
|
241
|
+
}).on( 'keydown.' + STATE.id, function( event ) {
|
383
242
|
|
384
243
|
var
|
385
244
|
// Get the keycode.
|
@@ -440,17 +299,20 @@ function PickerConstructor( ELEMENT, NAME, COMPONENT, OPTIONS ) {
|
|
440
299
|
// ....ah yes! It would’ve been incomplete without a crazy workaround for IE :|
|
441
300
|
// The focus is triggered *after* the close has completed - causing it
|
442
301
|
// to open again. So unbind and rebind the event at the next tick.
|
443
|
-
$ELEMENT.off( 'focus.
|
302
|
+
$ELEMENT.off( 'focus.' + STATE.id ).trigger( 'focus' )
|
444
303
|
setTimeout( function() {
|
445
|
-
$ELEMENT.on( 'focus.
|
304
|
+
$ELEMENT.on( 'focus.' + STATE.id, focusToOpen )
|
446
305
|
}, 0 )
|
447
306
|
}
|
448
307
|
|
449
308
|
// Remove the “active” class.
|
450
309
|
$ELEMENT.removeClass( CLASSES.active )
|
310
|
+
aria( ELEMENT, 'expanded', false )
|
451
311
|
|
452
312
|
// Remove the “opened” and “focused” class from the picker root.
|
453
313
|
P.$root.removeClass( CLASSES.opened + ' ' + CLASSES.focused )
|
314
|
+
aria( P.$root[0], 'hidden', true )
|
315
|
+
aria( P.$root[0], 'selected', false )
|
454
316
|
|
455
317
|
// If it’s already closed, do nothing more.
|
456
318
|
if ( !STATE.open ) return P
|
@@ -459,7 +321,7 @@ function PickerConstructor( ELEMENT, NAME, COMPONENT, OPTIONS ) {
|
|
459
321
|
STATE.open = false
|
460
322
|
|
461
323
|
// Unbind the document events.
|
462
|
-
$document.off( '.
|
324
|
+
$document.off( '.' + STATE.id )
|
463
325
|
|
464
326
|
// Trigger the queued “close” events.
|
465
327
|
return P.trigger( 'close' )
|
@@ -500,14 +362,14 @@ function PickerConstructor( ELEMENT, NAME, COMPONENT, OPTIONS ) {
|
|
500
362
|
thingValue = thingObject[ thingItem ]
|
501
363
|
|
502
364
|
// First, if the item exists and there’s a value, set it.
|
503
|
-
if ( P.component.item
|
365
|
+
if ( thingItem in P.component.item ) {
|
504
366
|
P.component.set( thingItem, thingValue, options )
|
505
367
|
}
|
506
368
|
|
507
369
|
// Then, check to update the element value and broadcast a change.
|
508
370
|
if ( thingItem == 'select' || thingItem == 'clear' ) {
|
509
|
-
$ELEMENT.val( thingItem == 'clear' ?
|
510
|
-
|
371
|
+
$ELEMENT.val( thingItem == 'clear' ?
|
372
|
+
'' : P.get( thingItem, SETTINGS.format )
|
511
373
|
).trigger( 'change' )
|
512
374
|
}
|
513
375
|
}
|
@@ -540,9 +402,13 @@ function PickerConstructor( ELEMENT, NAME, COMPONENT, OPTIONS ) {
|
|
540
402
|
}
|
541
403
|
|
542
404
|
// Check if a component item exists, return that.
|
543
|
-
if ( P.component.item
|
405
|
+
if ( thing in P.component.item ) {
|
544
406
|
if ( typeof format == 'string' ) {
|
545
|
-
return PickerConstructor._.trigger(
|
407
|
+
return PickerConstructor._.trigger(
|
408
|
+
P.component.formats.toString,
|
409
|
+
P.component,
|
410
|
+
[ format, P.component.get( thing ) ]
|
411
|
+
)
|
546
412
|
}
|
547
413
|
return P.component.get( thing )
|
548
414
|
}
|
@@ -584,6 +450,23 @@ function PickerConstructor( ELEMENT, NAME, COMPONENT, OPTIONS ) {
|
|
584
450
|
}, //on
|
585
451
|
|
586
452
|
|
453
|
+
|
454
|
+
/**
|
455
|
+
* Unbind events on the things.
|
456
|
+
*/
|
457
|
+
off: function() {
|
458
|
+
var i, thingName,
|
459
|
+
names = arguments;
|
460
|
+
for ( i = 0, namesCount = names.length; i < namesCount; i += 1 ) {
|
461
|
+
thingName = names[i]
|
462
|
+
if ( thingName in STATE.methods ) {
|
463
|
+
delete STATE.methods[thingName]
|
464
|
+
}
|
465
|
+
}
|
466
|
+
return P
|
467
|
+
},
|
468
|
+
|
469
|
+
|
587
470
|
/**
|
588
471
|
* Fire off method events.
|
589
472
|
*/
|
@@ -637,6 +520,196 @@ function PickerConstructor( ELEMENT, NAME, COMPONENT, OPTIONS ) {
|
|
637
520
|
} //createWrappedComponent
|
638
521
|
|
639
522
|
|
523
|
+
|
524
|
+
/**
|
525
|
+
* Prepare the input element with all bindings.
|
526
|
+
*/
|
527
|
+
function prepareElement() {
|
528
|
+
|
529
|
+
$ELEMENT.
|
530
|
+
|
531
|
+
// Store the picker data by component name.
|
532
|
+
data(NAME, P).
|
533
|
+
|
534
|
+
// Add the “input” class name.
|
535
|
+
addClass(CLASSES.input).
|
536
|
+
|
537
|
+
// If there’s a `data-value`, update the value of the element.
|
538
|
+
val( $ELEMENT.data('value') ?
|
539
|
+
P.get('select', SETTINGS.format) :
|
540
|
+
ELEMENT.value
|
541
|
+
).
|
542
|
+
|
543
|
+
// On focus/click, open the picker and adjust the root “focused” state.
|
544
|
+
on('focus.' + STATE.id + ' click.' + STATE.id, focusToOpen)
|
545
|
+
|
546
|
+
|
547
|
+
// Only bind keydown events if the element isn’t editable.
|
548
|
+
if ( !SETTINGS.editable ) {
|
549
|
+
|
550
|
+
// Handle keyboard event based on the picker being opened or not.
|
551
|
+
$ELEMENT.on('keydown.' + STATE.id, function(event) {
|
552
|
+
|
553
|
+
var keycode = event.keyCode,
|
554
|
+
|
555
|
+
// Check if one of the delete keys was pressed.
|
556
|
+
isKeycodeDelete = /^(8|46)$/.test(keycode)
|
557
|
+
|
558
|
+
// For some reason IE clears the input value on “escape”.
|
559
|
+
if ( keycode == 27 ) {
|
560
|
+
P.close()
|
561
|
+
return false
|
562
|
+
}
|
563
|
+
|
564
|
+
// Check if `space` or `delete` was pressed or the picker is closed with a key movement.
|
565
|
+
if ( keycode == 32 || isKeycodeDelete || !STATE.open && P.component.key[keycode] ) {
|
566
|
+
|
567
|
+
// Prevent it from moving the page and bubbling to doc.
|
568
|
+
event.preventDefault()
|
569
|
+
event.stopPropagation()
|
570
|
+
|
571
|
+
// If `delete` was pressed, clear the values and close the picker.
|
572
|
+
// Otherwise open the picker.
|
573
|
+
if ( isKeycodeDelete ) { P.clear().close() }
|
574
|
+
else { P.open() }
|
575
|
+
}
|
576
|
+
})
|
577
|
+
}
|
578
|
+
|
579
|
+
|
580
|
+
// Update the aria attributes.
|
581
|
+
aria(ELEMENT, {
|
582
|
+
haspopup: true,
|
583
|
+
expanded: false,
|
584
|
+
readonly: false,
|
585
|
+
owns: ELEMENT.id + '_root' + (P._hidden ? ' ' + P._hidden.id : '')
|
586
|
+
})
|
587
|
+
}
|
588
|
+
|
589
|
+
|
590
|
+
/**
|
591
|
+
* Prepare the root picker element with all bindings.
|
592
|
+
*/
|
593
|
+
function prepareElementRoot() {
|
594
|
+
|
595
|
+
P.$root.
|
596
|
+
|
597
|
+
on({
|
598
|
+
|
599
|
+
// When something within the root is focused, stop from bubbling
|
600
|
+
// to the doc and remove the “focused” state from the root.
|
601
|
+
focusin: function( event ) {
|
602
|
+
P.$root.removeClass( CLASSES.focused )
|
603
|
+
aria( P.$root[0], 'selected', false )
|
604
|
+
event.stopPropagation()
|
605
|
+
},
|
606
|
+
|
607
|
+
// When something within the root holder is clicked, stop it
|
608
|
+
// from bubbling to the doc.
|
609
|
+
'mousedown click': function( event ) {
|
610
|
+
|
611
|
+
var target = event.target
|
612
|
+
|
613
|
+
// Make sure the target isn’t the root holder so it can bubble up.
|
614
|
+
if ( target != P.$root.children()[ 0 ] ) {
|
615
|
+
|
616
|
+
event.stopPropagation()
|
617
|
+
|
618
|
+
// * For mousedown events, cancel the default action in order to
|
619
|
+
// prevent cases where focus is shifted onto external elements
|
620
|
+
// when using things like jQuery mobile or MagnificPopup (ref: #249 & #120).
|
621
|
+
// Also, for Firefox, don’t prevent action on the `option` element.
|
622
|
+
if ( event.type == 'mousedown' && !$( target ).is( ':input' ) && target.nodeName != 'OPTION' ) {
|
623
|
+
|
624
|
+
event.preventDefault()
|
625
|
+
|
626
|
+
// Re-focus onto the element so that users can click away
|
627
|
+
// from elements focused within the picker.
|
628
|
+
ELEMENT.focus()
|
629
|
+
}
|
630
|
+
}
|
631
|
+
}
|
632
|
+
}).
|
633
|
+
|
634
|
+
// If there’s a click on an actionable element, carry out the actions.
|
635
|
+
on( 'click', '[data-pick], [data-nav], [data-clear]', function() {
|
636
|
+
|
637
|
+
var $target = $( this ),
|
638
|
+
targetData = $target.data(),
|
639
|
+
targetDisabled = $target.hasClass( CLASSES.navDisabled ) || $target.hasClass( CLASSES.disabled ),
|
640
|
+
|
641
|
+
// * For IE, non-focusable elements can be active elements as well
|
642
|
+
// (http://stackoverflow.com/a/2684561).
|
643
|
+
activeElement = document.activeElement
|
644
|
+
activeElement = activeElement && ( activeElement.type || activeElement.href ) && activeElement
|
645
|
+
|
646
|
+
// If it’s disabled or nothing inside is actively focused, re-focus the element.
|
647
|
+
if ( targetDisabled || activeElement && !$.contains( P.$root[0], activeElement ) ) {
|
648
|
+
ELEMENT.focus()
|
649
|
+
}
|
650
|
+
|
651
|
+
// If something is superficially changed, update the `highlight` based on the `nav`.
|
652
|
+
if ( targetData.nav && !targetDisabled ) {
|
653
|
+
P.set( 'highlight', P.component.item.highlight, { nav: targetData.nav } )
|
654
|
+
}
|
655
|
+
|
656
|
+
// If something is picked, set `select` then close with focus.
|
657
|
+
else if ( PickerConstructor._.isInteger( targetData.pick ) && !targetDisabled ) {
|
658
|
+
P.set( 'select', targetData.pick ).close( true )
|
659
|
+
}
|
660
|
+
|
661
|
+
// If a “clear” button is pressed, empty the values and close with focus.
|
662
|
+
else if ( targetData.clear ) {
|
663
|
+
P.clear().close( true )
|
664
|
+
}
|
665
|
+
}) //P.$root
|
666
|
+
|
667
|
+
aria( P.$root[0], 'hidden', true )
|
668
|
+
}
|
669
|
+
|
670
|
+
|
671
|
+
/**
|
672
|
+
* Prepare the hidden input element along with all bindings.
|
673
|
+
*/
|
674
|
+
function prepareElementHidden() {
|
675
|
+
|
676
|
+
var id = [
|
677
|
+
typeof SETTINGS.hiddenPrefix == 'string' ? SETTINGS.hiddenPrefix : '',
|
678
|
+
typeof SETTINGS.hiddenSuffix == 'string' ? SETTINGS.hiddenSuffix : '_submit'
|
679
|
+
]
|
680
|
+
|
681
|
+
P._hidden = $(
|
682
|
+
'<input ' +
|
683
|
+
'type=hidden ' +
|
684
|
+
|
685
|
+
// Create the name and ID by using the original
|
686
|
+
// input’s with a prefix and suffix.
|
687
|
+
'name="' + id[0] + ELEMENT.name + id[1] + '"' +
|
688
|
+
'id="' + id[0] + ELEMENT.id + id[1] + '"' +
|
689
|
+
|
690
|
+
// If the element has a value, set the hidden value as well.
|
691
|
+
(
|
692
|
+
$ELEMENT.data('value') || ELEMENT.value ?
|
693
|
+
' value="' + P.get('select', SETTINGS.formatSubmit) + '"' :
|
694
|
+
''
|
695
|
+
) +
|
696
|
+
'>'
|
697
|
+
)[0]
|
698
|
+
|
699
|
+
$ELEMENT.
|
700
|
+
|
701
|
+
// If the value changes, update the hidden input with the correct format.
|
702
|
+
on('change.' + STATE.id, function() {
|
703
|
+
P._hidden.value = ELEMENT.value ?
|
704
|
+
P.get('select', SETTINGS.formatSubmit) :
|
705
|
+
''
|
706
|
+
}).
|
707
|
+
|
708
|
+
// Insert the hidden input after the element.
|
709
|
+
after(P._hidden)
|
710
|
+
}
|
711
|
+
|
712
|
+
|
640
713
|
// Separated for IE
|
641
714
|
function focusToOpen( event ) {
|
642
715
|
|
@@ -644,7 +717,10 @@ function PickerConstructor( ELEMENT, NAME, COMPONENT, OPTIONS ) {
|
|
644
717
|
event.stopPropagation()
|
645
718
|
|
646
719
|
// If it’s a focus event, add the “focused” class to the root.
|
647
|
-
if ( event.type == 'focus' )
|
720
|
+
if ( event.type == 'focus' ) {
|
721
|
+
P.$root.addClass( CLASSES.focused )
|
722
|
+
aria( P.$root[0], 'selected', true )
|
723
|
+
}
|
648
724
|
|
649
725
|
// And then finally open the picker.
|
650
726
|
P.open()
|
@@ -791,7 +867,13 @@ PickerConstructor._ = {
|
|
791
867
|
*/
|
792
868
|
isInteger: function( value ) {
|
793
869
|
return {}.toString.call( value ).indexOf( 'Number' ) > -1 && value % 1 === 0
|
794
|
-
}
|
870
|
+
},
|
871
|
+
|
872
|
+
|
873
|
+
/**
|
874
|
+
* Create ARIA attribute strings.
|
875
|
+
*/
|
876
|
+
ariaAttr: ariaAttr
|
795
877
|
} //PickerConstructor._
|
796
878
|
|
797
879
|
|
@@ -835,6 +917,37 @@ PickerConstructor.extend = function( name, Component ) {
|
|
835
917
|
|
836
918
|
|
837
919
|
|
920
|
+
function aria(element, attribute, value) {
|
921
|
+
if ( $.isPlainObject(attribute) ) {
|
922
|
+
for ( var key in attribute ) {
|
923
|
+
ariaSet(element, key, attribute[key])
|
924
|
+
}
|
925
|
+
}
|
926
|
+
else {
|
927
|
+
ariaSet(element, attribute, value)
|
928
|
+
}
|
929
|
+
}
|
930
|
+
function ariaSet(element, attribute, value) {
|
931
|
+
element.setAttribute(
|
932
|
+
(attribute == 'role' ? '' : 'aria-') + attribute,
|
933
|
+
value
|
934
|
+
)
|
935
|
+
}
|
936
|
+
function ariaAttr(attribute, data) {
|
937
|
+
if ( !$.isPlainObject(attribute) ) {
|
938
|
+
attribute = { attribute: data }
|
939
|
+
}
|
940
|
+
data = ''
|
941
|
+
for ( var key in attribute ) {
|
942
|
+
var attr = (key == 'role' ? '' : 'aria-') + key,
|
943
|
+
attrVal = attribute[key]
|
944
|
+
data += attrVal == null ? '' : attr + '="' + attribute[key] + '"'
|
945
|
+
}
|
946
|
+
return data
|
947
|
+
}
|
948
|
+
|
949
|
+
|
950
|
+
|
838
951
|
// Expose the picker constructor.
|
839
952
|
return PickerConstructor
|
840
953
|
|