@aurodesignsystem-dev/auro-formkit 0.0.0-pr1497.5 → 0.0.0-pr1498.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.
- package/components/checkbox/demo/customize.min.js +2 -2
- package/components/checkbox/demo/getting-started.min.js +2 -2
- package/components/checkbox/demo/index.min.js +2 -2
- package/components/checkbox/dist/index.js +2 -2
- package/components/checkbox/dist/registered.js +2 -2
- package/components/combobox/demo/customize.md +7 -3
- package/components/combobox/demo/customize.min.js +1438 -1668
- package/components/combobox/demo/getting-started.min.js +1440 -1670
- package/components/combobox/demo/index.min.js +1440 -1670
- package/components/combobox/dist/auro-combobox.d.ts +5 -0
- package/components/combobox/dist/index.js +485 -140
- package/components/combobox/dist/registered.js +485 -140
- package/components/counter/demo/customize.min.js +20 -3
- package/components/counter/demo/index.min.js +20 -3
- package/components/counter/dist/index.js +5447 -192
- package/components/counter/dist/registered.js +5447 -192
- package/components/datepicker/demo/customize.min.js +149 -58
- package/components/datepicker/demo/index.min.js +149 -58
- package/components/datepicker/dist/index.js +149 -58
- package/components/datepicker/dist/registered.js +149 -58
- package/components/dropdown/demo/customize.min.js +18 -1
- package/components/dropdown/demo/getting-started.min.js +18 -1
- package/components/dropdown/demo/index.min.js +18 -1
- package/components/dropdown/dist/auro-dropdown.d.ts +1 -0
- package/components/dropdown/dist/index.js +18 -1
- package/components/dropdown/dist/registered.js +18 -1
- package/components/form/demo/customize.min.js +7910 -7909
- package/components/form/demo/getting-started.min.js +7910 -7909
- package/components/form/demo/index.min.js +7910 -7909
- package/components/form/demo/registerDemoDeps.min.js +7872 -7871
- package/components/input/demo/customize.min.js +131 -56
- package/components/input/demo/getting-started.min.js +131 -56
- package/components/input/demo/index.min.js +131 -56
- package/components/input/dist/base-input.d.ts +16 -0
- package/components/input/dist/index.js +131 -56
- package/components/input/dist/registered.js +131 -56
- package/components/menu/demo/api.md +41 -45
- package/components/menu/demo/customize.md +0 -28
- package/components/menu/demo/index.min.js +779 -1354
- package/components/menu/dist/auro-menu.d.ts +95 -110
- package/components/menu/dist/auro-menuoption.d.ts +32 -138
- package/components/menu/dist/index.js +753 -1308
- package/components/menu/dist/registered.js +765 -1308
- package/components/radio/demo/customize.min.js +2 -2
- package/components/radio/demo/getting-started.min.js +2 -2
- package/components/radio/demo/index.min.js +2 -2
- package/components/radio/dist/index.js +2 -2
- package/components/radio/dist/registered.js +2 -2
- package/components/select/demo/customize.md +7 -3
- package/components/select/demo/customize.min.js +1088 -1615
- package/components/select/demo/getting-started.min.js +1088 -1615
- package/components/select/demo/index.min.js +1088 -1615
- package/components/select/dist/index.js +63 -15
- package/components/select/dist/registered.js +63 -15
- package/components/select/dist/selectUtils.d.ts +12 -0
- package/custom-elements.json +2296 -2942
- package/package.json +1 -1
- package/components/menu/dist/auro-menu.context.d.ts +0 -238
|
@@ -4548,7 +4548,7 @@ class AuroFormValidation {
|
|
|
4548
4548
|
} else if (this.runtimeUtils.elementMatch(elem, 'auro-input') && elem.errorMessage === '') {
|
|
4549
4549
|
const input = elem.renderRoot.querySelector('input');
|
|
4550
4550
|
|
|
4551
|
-
if (input.validationMessage.length > 0) {
|
|
4551
|
+
if (input && input.validationMessage.length > 0) {
|
|
4552
4552
|
elem.errorMessage = input.validationMessage;
|
|
4553
4553
|
}
|
|
4554
4554
|
} else if (this.runtimeUtils.elementMatch(elem, 'auro-combobox') && elem.errorMessage === '') {
|
|
@@ -10385,7 +10385,6 @@ class AuroInputUtilities {
|
|
|
10385
10385
|
const maskOptions = this.getMaskOptions('date', normalizedFormat);
|
|
10386
10386
|
|
|
10387
10387
|
if (!(valueObject instanceof Date) || Number.isNaN(valueObject.getTime()) || !maskOptions || typeof maskOptions.format !== 'function') {
|
|
10388
|
-
console.debug('Invalid date object or mask options for formatting', { valueObject, maskOptions }); // eslint-disable-line no-console
|
|
10389
10388
|
return undefined;
|
|
10390
10389
|
}
|
|
10391
10390
|
|
|
@@ -11088,7 +11087,7 @@ class BaseInput extends AuroElement {
|
|
|
11088
11087
|
* @returns {Date|undefined}
|
|
11089
11088
|
*/
|
|
11090
11089
|
get valueObject() {
|
|
11091
|
-
return this._valueObject;
|
|
11090
|
+
return this._valueObject || this._computeDateObjectFallback(this.value);
|
|
11092
11091
|
}
|
|
11093
11092
|
|
|
11094
11093
|
/**
|
|
@@ -11096,7 +11095,7 @@ class BaseInput extends AuroElement {
|
|
|
11096
11095
|
* @returns {Date|undefined}
|
|
11097
11096
|
*/
|
|
11098
11097
|
get minObject() {
|
|
11099
|
-
return this._minObject;
|
|
11098
|
+
return this._minObject || this._computeDateObjectFallback(this.min);
|
|
11100
11099
|
}
|
|
11101
11100
|
|
|
11102
11101
|
/**
|
|
@@ -11104,7 +11103,31 @@ class BaseInput extends AuroElement {
|
|
|
11104
11103
|
* @returns {Date|undefined}
|
|
11105
11104
|
*/
|
|
11106
11105
|
get maxObject() {
|
|
11107
|
-
return this._maxObject;
|
|
11106
|
+
return this._maxObject || this._computeDateObjectFallback(this.max);
|
|
11107
|
+
}
|
|
11108
|
+
|
|
11109
|
+
/**
|
|
11110
|
+
* Parses a date string into a Date object when the corresponding `_*Object`
|
|
11111
|
+
* field hasn't been synced yet by `updated()`. Returns undefined when the
|
|
11112
|
+
* input type/format isn't a full date or the string is not a valid date.
|
|
11113
|
+
*
|
|
11114
|
+
* Why this exists: a parent (datepicker) can call `inputN.validate()` from
|
|
11115
|
+
* inside its own `updated()` before this input's `updated()` has run
|
|
11116
|
+
* `syncDateValues()` — so `_valueObject`/`_maxObject` are still `undefined`
|
|
11117
|
+
* and range checks would otherwise silently no-op (flipping the result to
|
|
11118
|
+
* `valid` or `patternMismatch`).
|
|
11119
|
+
* @private
|
|
11120
|
+
* @param {string|undefined} dateStr - ISO date string from `value`/`min`/`max`.
|
|
11121
|
+
* @returns {Date|undefined}
|
|
11122
|
+
*/
|
|
11123
|
+
_computeDateObjectFallback(dateStr) {
|
|
11124
|
+
if (!dateStr || !this.util || !this.util.isFullDateFormat(this.type, this.format)) {
|
|
11125
|
+
return undefined;
|
|
11126
|
+
}
|
|
11127
|
+
if (!dateFormatter.isValidDate(dateStr)) {
|
|
11128
|
+
return undefined;
|
|
11129
|
+
}
|
|
11130
|
+
return dateFormatter.stringToDateInstance(dateStr);
|
|
11108
11131
|
}
|
|
11109
11132
|
|
|
11110
11133
|
/**
|
|
@@ -11129,8 +11152,30 @@ class BaseInput extends AuroElement {
|
|
|
11129
11152
|
connectedCallback() {
|
|
11130
11153
|
super.connectedCallback();
|
|
11131
11154
|
|
|
11155
|
+
// Mark for query selectors when registered under a versioned tag (e.g. inside
|
|
11156
|
+
// a datepicker/combobox). Must run before parent components call validate() on
|
|
11157
|
+
// their inner inputs — the validation framework matches via tag-or-attribute,
|
|
11158
|
+
// and parents trigger validation during their own updated() cycle, which can
|
|
11159
|
+
// precede this input's firstUpdated().
|
|
11160
|
+
if (this.tagName.toLowerCase() !== 'auro-input' && !this.hasAttribute('auro-input')) {
|
|
11161
|
+
this.setAttribute('auro-input', '');
|
|
11162
|
+
}
|
|
11163
|
+
|
|
11132
11164
|
this.locale = this.domHandler.getLocale(this);
|
|
11133
11165
|
notifyOnLangChange(this);
|
|
11166
|
+
|
|
11167
|
+
// Pre-compute lengthForType and date-object fields so a parent (e.g. datepicker)
|
|
11168
|
+
// calling our validate() synchronously during its own updated() cycle sees
|
|
11169
|
+
// populated values. Without this, range validation silently no-ops because
|
|
11170
|
+
// `max.length === lengthForType` fails when lengthForType is still undefined.
|
|
11171
|
+
// Rebuild util here (constructor seeded with en-US default) so configureDataForType's
|
|
11172
|
+
// locale-derived format lookup uses the actual locale just resolved above.
|
|
11173
|
+
this.util = new AuroInputUtilities({
|
|
11174
|
+
locale: this.locale,
|
|
11175
|
+
format: this.format
|
|
11176
|
+
});
|
|
11177
|
+
this.configureDataForType();
|
|
11178
|
+
this.syncDateValues();
|
|
11134
11179
|
}
|
|
11135
11180
|
|
|
11136
11181
|
disconnectedCallback() {
|
|
@@ -11151,8 +11196,8 @@ class BaseInput extends AuroElement {
|
|
|
11151
11196
|
}
|
|
11152
11197
|
|
|
11153
11198
|
// add attribute for query selectors when auro-input is registered under a custom name
|
|
11154
|
-
if (this.tagName.toLowerCase() !== 'auro-input') {
|
|
11155
|
-
this.setAttribute('auro-input',
|
|
11199
|
+
if (this.tagName.toLowerCase() !== 'auro-input' && !this.hasAttribute('auro-input')) {
|
|
11200
|
+
this.setAttribute('auro-input', '');
|
|
11156
11201
|
}
|
|
11157
11202
|
this.inputId = this.id ? `${this.id}-input` : window.crypto.randomUUID();
|
|
11158
11203
|
|
|
@@ -11200,6 +11245,12 @@ class BaseInput extends AuroElement {
|
|
|
11200
11245
|
return;
|
|
11201
11246
|
}
|
|
11202
11247
|
|
|
11248
|
+
// While configureAutoFormatting is running, imask's internal updateControl
|
|
11249
|
+
// writes el.value to align display with the masked value. A synthetic input
|
|
11250
|
+
// event from that write would re-enter handleInput → processCreditCard mid-setup
|
|
11251
|
+
// and clobber a Lit value that was just pushed by the parent combobox.
|
|
11252
|
+
if (component._configuringMask) return;
|
|
11253
|
+
|
|
11203
11254
|
// If all guard clauses are passed, dispatch the event
|
|
11204
11255
|
const inputEvent = new InputEvent('input', {
|
|
11205
11256
|
bubbles: true,
|
|
@@ -11318,7 +11369,16 @@ class BaseInput extends AuroElement {
|
|
|
11318
11369
|
|
|
11319
11370
|
if (formattedValue !== this.inputElement.value) {
|
|
11320
11371
|
this.skipNextProgrammaticInputEvent = true;
|
|
11321
|
-
if (
|
|
11372
|
+
if (this.maskInstance && this.type === 'credit-card') {
|
|
11373
|
+
// Route through the mask so its _value and el.value stay in lock-step
|
|
11374
|
+
// (set value calls updateControl which writes el.value = displayValue).
|
|
11375
|
+
// Writing el.value directly leaves the mask thinking displayValue is
|
|
11376
|
+
// stale; _saveSelection on the next focus/click then warns. Scoped to
|
|
11377
|
+
// credit-card so date's own formattedValue (raw ISO when calendar-invalid)
|
|
11378
|
+
// isn't re-masked through the mm/dd/yyyy mask, which would truncate it
|
|
11379
|
+
// and flip validity from patternMismatch to tooShort.
|
|
11380
|
+
this.maskInstance.value = formattedValue || '';
|
|
11381
|
+
} else if (formattedValue) {
|
|
11322
11382
|
this.inputElement.value = formattedValue;
|
|
11323
11383
|
} else {
|
|
11324
11384
|
this.inputElement.value = '';
|
|
@@ -11427,58 +11487,73 @@ class BaseInput extends AuroElement {
|
|
|
11427
11487
|
* @returns {void}
|
|
11428
11488
|
*/
|
|
11429
11489
|
configureAutoFormatting() {
|
|
11430
|
-
|
|
11431
|
-
|
|
11432
|
-
|
|
11433
|
-
|
|
11434
|
-
|
|
11435
|
-
this.
|
|
11436
|
-
|
|
11437
|
-
|
|
11438
|
-
|
|
11439
|
-
if (this.inputElement && maskOptions.mask) {
|
|
11440
|
-
|
|
11441
|
-
// Stash and clear any existing value before IMask init.
|
|
11442
|
-
// IMask's constructor processes the current input value which requires
|
|
11443
|
-
// selection state — clearing first avoids that scenario entirely.
|
|
11444
|
-
// When the format changes (e.g. locale switch) and we have a valid ISO
|
|
11445
|
-
// model value, compute the display string for the NEW format instead of
|
|
11446
|
-
// re-using the old display string, which may be invalid in the new mask.
|
|
11447
|
-
let existingValue = this.inputElement.value;
|
|
11448
|
-
if (
|
|
11449
|
-
this.util.isFullDateFormat(this.type, this.format) &&
|
|
11450
|
-
this.value &&
|
|
11451
|
-
dateFormatter.isValidDate(this.value) &&
|
|
11452
|
-
this.valueObject instanceof Date &&
|
|
11453
|
-
!Number.isNaN(this.valueObject.getTime()) &&
|
|
11454
|
-
typeof maskOptions.format === 'function'
|
|
11455
|
-
) {
|
|
11456
|
-
existingValue = maskOptions.format(this.valueObject);
|
|
11490
|
+
// Re-entrancy guard. The patched-setter's synthetic input event (suppressed
|
|
11491
|
+
// by _configuringMask above) could otherwise trigger handleInput →
|
|
11492
|
+
// processCreditCard → configureAutoFormatting before the outer call's
|
|
11493
|
+
// set value has finished its alignCursor pass.
|
|
11494
|
+
if (this._configuringMask) return;
|
|
11495
|
+
this._configuringMask = true;
|
|
11496
|
+
try {
|
|
11497
|
+
if (this.maskInstance) {
|
|
11498
|
+
this.maskInstance.destroy();
|
|
11457
11499
|
}
|
|
11458
11500
|
|
|
11459
|
-
|
|
11460
|
-
this.
|
|
11461
|
-
|
|
11462
|
-
this.maskInstance = IMask(this.inputElement, maskOptions);
|
|
11501
|
+
// Pass new format to util
|
|
11502
|
+
this.util.updateFormat(this.format);
|
|
11463
11503
|
|
|
11464
|
-
this.
|
|
11465
|
-
|
|
11466
|
-
|
|
11467
|
-
|
|
11504
|
+
const maskOptions = this.util.getMaskOptions(this.type, this.format);
|
|
11505
|
+
|
|
11506
|
+
if (this.inputElement && maskOptions.mask) {
|
|
11507
|
+
|
|
11508
|
+
// Stash and clear any existing value before IMask init.
|
|
11509
|
+
// IMask's constructor processes the current input value which requires
|
|
11510
|
+
// selection state — clearing first avoids that scenario entirely.
|
|
11511
|
+
// When the format changes (e.g. locale switch) and we have a valid ISO
|
|
11512
|
+
// model value, compute the display string for the NEW format instead of
|
|
11513
|
+
// re-using the old display string, which may be invalid in the new mask.
|
|
11514
|
+
let existingValue = this.inputElement.value;
|
|
11515
|
+
if (
|
|
11516
|
+
this.util.isFullDateFormat(this.type, this.format) &&
|
|
11517
|
+
this.value &&
|
|
11518
|
+
dateFormatter.isValidDate(this.value) &&
|
|
11519
|
+
this.valueObject instanceof Date &&
|
|
11520
|
+
!Number.isNaN(this.valueObject.getTime()) &&
|
|
11521
|
+
typeof maskOptions.format === 'function'
|
|
11522
|
+
) {
|
|
11523
|
+
existingValue = maskOptions.format(this.valueObject);
|
|
11468
11524
|
}
|
|
11469
|
-
});
|
|
11470
11525
|
|
|
11471
|
-
|
|
11472
|
-
this.value =
|
|
11473
|
-
|
|
11474
|
-
|
|
11475
|
-
|
|
11476
|
-
|
|
11526
|
+
this.skipNextProgrammaticInputEvent = true;
|
|
11527
|
+
this.inputElement.value = '';
|
|
11528
|
+
|
|
11529
|
+
this.maskInstance = IMask(this.inputElement, maskOptions);
|
|
11530
|
+
|
|
11531
|
+
this.maskInstance.on('accept', () => {
|
|
11532
|
+
// Suppress propagation during configureAutoFormatting's own value-restoration
|
|
11533
|
+
// (line below) — the mask emits 'accept' on every value-set, including ours,
|
|
11534
|
+
// and we don't want to overwrite a value the parent just pushed.
|
|
11535
|
+
if (this._configuringMask) return;
|
|
11536
|
+
this.value = this.util.toModelValue(this.maskInstance.value, this.format);
|
|
11537
|
+
if (this.type === "date") {
|
|
11538
|
+
this._rawMaskValue = this.maskInstance.value;
|
|
11539
|
+
}
|
|
11540
|
+
});
|
|
11477
11541
|
|
|
11478
|
-
|
|
11479
|
-
|
|
11480
|
-
|
|
11542
|
+
this.maskInstance.on('complete', () => {
|
|
11543
|
+
if (this._configuringMask) return;
|
|
11544
|
+
this.value = this.util.toModelValue(this.maskInstance.value, this.format);
|
|
11545
|
+
if (this.type === "date") {
|
|
11546
|
+
this._rawMaskValue = this.maskInstance.value;
|
|
11547
|
+
}
|
|
11548
|
+
});
|
|
11549
|
+
|
|
11550
|
+
// Restore the stashed value through IMask so it's properly masked
|
|
11551
|
+
if (existingValue) {
|
|
11552
|
+
this.maskInstance.value = existingValue;
|
|
11553
|
+
}
|
|
11481
11554
|
}
|
|
11555
|
+
} finally {
|
|
11556
|
+
this._configuringMask = false;
|
|
11482
11557
|
}
|
|
11483
11558
|
}
|
|
11484
11559
|
|
|
@@ -11765,10 +11840,10 @@ class BaseInput extends AuroElement {
|
|
|
11765
11840
|
},
|
|
11766
11841
|
{
|
|
11767
11842
|
name: 'Diners club',
|
|
11768
|
-
regex: /^(?<num>36|38)\d{0}/u,
|
|
11843
|
+
regex: /^(?<num>30[0-5]|36|38)\d{0}/u,
|
|
11769
11844
|
formatLength: 16,
|
|
11770
11845
|
errorMessage: CreditCardValidationMessage,
|
|
11771
|
-
cardIcon: '
|
|
11846
|
+
cardIcon: 'cc-dinersclub',
|
|
11772
11847
|
maskFormat: "0000 000000 0000"
|
|
11773
11848
|
},
|
|
11774
11849
|
{
|
|
@@ -12178,7 +12253,7 @@ class AuroHelpText extends i$3 {
|
|
|
12178
12253
|
}
|
|
12179
12254
|
}
|
|
12180
12255
|
|
|
12181
|
-
var formkitVersion = '
|
|
12256
|
+
var formkitVersion = '202606100232';
|
|
12182
12257
|
|
|
12183
12258
|
/**
|
|
12184
12259
|
* @license
|
|
@@ -453,6 +453,21 @@ export default class BaseInput extends AuroElement {
|
|
|
453
453
|
* @returns {Date|undefined}
|
|
454
454
|
*/
|
|
455
455
|
get maxObject(): Date | undefined;
|
|
456
|
+
/**
|
|
457
|
+
* Parses a date string into a Date object when the corresponding `_*Object`
|
|
458
|
+
* field hasn't been synced yet by `updated()`. Returns undefined when the
|
|
459
|
+
* input type/format isn't a full date or the string is not a valid date.
|
|
460
|
+
*
|
|
461
|
+
* Why this exists: a parent (datepicker) can call `inputN.validate()` from
|
|
462
|
+
* inside its own `updated()` before this input's `updated()` has run
|
|
463
|
+
* `syncDateValues()` — so `_valueObject`/`_maxObject` are still `undefined`
|
|
464
|
+
* and range checks would otherwise silently no-op (flipping the result to
|
|
465
|
+
* `valid` or `patternMismatch`).
|
|
466
|
+
* @private
|
|
467
|
+
* @param {string|undefined} dateStr - ISO date string from `value`/`min`/`max`.
|
|
468
|
+
* @returns {Date|undefined}
|
|
469
|
+
*/
|
|
470
|
+
private _computeDateObjectFallback;
|
|
456
471
|
/**
|
|
457
472
|
* Internal setter for readonly date object properties.
|
|
458
473
|
* @private
|
|
@@ -523,6 +538,7 @@ export default class BaseInput extends AuroElement {
|
|
|
523
538
|
* @returns {void}
|
|
524
539
|
*/
|
|
525
540
|
private configureAutoFormatting;
|
|
541
|
+
_configuringMask: boolean | undefined;
|
|
526
542
|
maskInstance: import("imask").InputMask<any> | undefined;
|
|
527
543
|
/**
|
|
528
544
|
* Sends event notifying that the input has changed it's value.
|
|
@@ -4490,7 +4490,7 @@ class AuroFormValidation {
|
|
|
4490
4490
|
} else if (this.runtimeUtils.elementMatch(elem, 'auro-input') && elem.errorMessage === '') {
|
|
4491
4491
|
const input = elem.renderRoot.querySelector('input');
|
|
4492
4492
|
|
|
4493
|
-
if (input.validationMessage.length > 0) {
|
|
4493
|
+
if (input && input.validationMessage.length > 0) {
|
|
4494
4494
|
elem.errorMessage = input.validationMessage;
|
|
4495
4495
|
}
|
|
4496
4496
|
} else if (this.runtimeUtils.elementMatch(elem, 'auro-combobox') && elem.errorMessage === '') {
|
|
@@ -10327,7 +10327,6 @@ class AuroInputUtilities {
|
|
|
10327
10327
|
const maskOptions = this.getMaskOptions('date', normalizedFormat);
|
|
10328
10328
|
|
|
10329
10329
|
if (!(valueObject instanceof Date) || Number.isNaN(valueObject.getTime()) || !maskOptions || typeof maskOptions.format !== 'function') {
|
|
10330
|
-
console.debug('Invalid date object or mask options for formatting', { valueObject, maskOptions }); // eslint-disable-line no-console
|
|
10331
10330
|
return undefined;
|
|
10332
10331
|
}
|
|
10333
10332
|
|
|
@@ -11030,7 +11029,7 @@ class BaseInput extends AuroElement {
|
|
|
11030
11029
|
* @returns {Date|undefined}
|
|
11031
11030
|
*/
|
|
11032
11031
|
get valueObject() {
|
|
11033
|
-
return this._valueObject;
|
|
11032
|
+
return this._valueObject || this._computeDateObjectFallback(this.value);
|
|
11034
11033
|
}
|
|
11035
11034
|
|
|
11036
11035
|
/**
|
|
@@ -11038,7 +11037,7 @@ class BaseInput extends AuroElement {
|
|
|
11038
11037
|
* @returns {Date|undefined}
|
|
11039
11038
|
*/
|
|
11040
11039
|
get minObject() {
|
|
11041
|
-
return this._minObject;
|
|
11040
|
+
return this._minObject || this._computeDateObjectFallback(this.min);
|
|
11042
11041
|
}
|
|
11043
11042
|
|
|
11044
11043
|
/**
|
|
@@ -11046,7 +11045,31 @@ class BaseInput extends AuroElement {
|
|
|
11046
11045
|
* @returns {Date|undefined}
|
|
11047
11046
|
*/
|
|
11048
11047
|
get maxObject() {
|
|
11049
|
-
return this._maxObject;
|
|
11048
|
+
return this._maxObject || this._computeDateObjectFallback(this.max);
|
|
11049
|
+
}
|
|
11050
|
+
|
|
11051
|
+
/**
|
|
11052
|
+
* Parses a date string into a Date object when the corresponding `_*Object`
|
|
11053
|
+
* field hasn't been synced yet by `updated()`. Returns undefined when the
|
|
11054
|
+
* input type/format isn't a full date or the string is not a valid date.
|
|
11055
|
+
*
|
|
11056
|
+
* Why this exists: a parent (datepicker) can call `inputN.validate()` from
|
|
11057
|
+
* inside its own `updated()` before this input's `updated()` has run
|
|
11058
|
+
* `syncDateValues()` — so `_valueObject`/`_maxObject` are still `undefined`
|
|
11059
|
+
* and range checks would otherwise silently no-op (flipping the result to
|
|
11060
|
+
* `valid` or `patternMismatch`).
|
|
11061
|
+
* @private
|
|
11062
|
+
* @param {string|undefined} dateStr - ISO date string from `value`/`min`/`max`.
|
|
11063
|
+
* @returns {Date|undefined}
|
|
11064
|
+
*/
|
|
11065
|
+
_computeDateObjectFallback(dateStr) {
|
|
11066
|
+
if (!dateStr || !this.util || !this.util.isFullDateFormat(this.type, this.format)) {
|
|
11067
|
+
return undefined;
|
|
11068
|
+
}
|
|
11069
|
+
if (!dateFormatter.isValidDate(dateStr)) {
|
|
11070
|
+
return undefined;
|
|
11071
|
+
}
|
|
11072
|
+
return dateFormatter.stringToDateInstance(dateStr);
|
|
11050
11073
|
}
|
|
11051
11074
|
|
|
11052
11075
|
/**
|
|
@@ -11071,8 +11094,30 @@ class BaseInput extends AuroElement {
|
|
|
11071
11094
|
connectedCallback() {
|
|
11072
11095
|
super.connectedCallback();
|
|
11073
11096
|
|
|
11097
|
+
// Mark for query selectors when registered under a versioned tag (e.g. inside
|
|
11098
|
+
// a datepicker/combobox). Must run before parent components call validate() on
|
|
11099
|
+
// their inner inputs — the validation framework matches via tag-or-attribute,
|
|
11100
|
+
// and parents trigger validation during their own updated() cycle, which can
|
|
11101
|
+
// precede this input's firstUpdated().
|
|
11102
|
+
if (this.tagName.toLowerCase() !== 'auro-input' && !this.hasAttribute('auro-input')) {
|
|
11103
|
+
this.setAttribute('auro-input', '');
|
|
11104
|
+
}
|
|
11105
|
+
|
|
11074
11106
|
this.locale = this.domHandler.getLocale(this);
|
|
11075
11107
|
notifyOnLangChange(this);
|
|
11108
|
+
|
|
11109
|
+
// Pre-compute lengthForType and date-object fields so a parent (e.g. datepicker)
|
|
11110
|
+
// calling our validate() synchronously during its own updated() cycle sees
|
|
11111
|
+
// populated values. Without this, range validation silently no-ops because
|
|
11112
|
+
// `max.length === lengthForType` fails when lengthForType is still undefined.
|
|
11113
|
+
// Rebuild util here (constructor seeded with en-US default) so configureDataForType's
|
|
11114
|
+
// locale-derived format lookup uses the actual locale just resolved above.
|
|
11115
|
+
this.util = new AuroInputUtilities({
|
|
11116
|
+
locale: this.locale,
|
|
11117
|
+
format: this.format
|
|
11118
|
+
});
|
|
11119
|
+
this.configureDataForType();
|
|
11120
|
+
this.syncDateValues();
|
|
11076
11121
|
}
|
|
11077
11122
|
|
|
11078
11123
|
disconnectedCallback() {
|
|
@@ -11093,8 +11138,8 @@ class BaseInput extends AuroElement {
|
|
|
11093
11138
|
}
|
|
11094
11139
|
|
|
11095
11140
|
// add attribute for query selectors when auro-input is registered under a custom name
|
|
11096
|
-
if (this.tagName.toLowerCase() !== 'auro-input') {
|
|
11097
|
-
this.setAttribute('auro-input',
|
|
11141
|
+
if (this.tagName.toLowerCase() !== 'auro-input' && !this.hasAttribute('auro-input')) {
|
|
11142
|
+
this.setAttribute('auro-input', '');
|
|
11098
11143
|
}
|
|
11099
11144
|
this.inputId = this.id ? `${this.id}-input` : window.crypto.randomUUID();
|
|
11100
11145
|
|
|
@@ -11142,6 +11187,12 @@ class BaseInput extends AuroElement {
|
|
|
11142
11187
|
return;
|
|
11143
11188
|
}
|
|
11144
11189
|
|
|
11190
|
+
// While configureAutoFormatting is running, imask's internal updateControl
|
|
11191
|
+
// writes el.value to align display with the masked value. A synthetic input
|
|
11192
|
+
// event from that write would re-enter handleInput → processCreditCard mid-setup
|
|
11193
|
+
// and clobber a Lit value that was just pushed by the parent combobox.
|
|
11194
|
+
if (component._configuringMask) return;
|
|
11195
|
+
|
|
11145
11196
|
// If all guard clauses are passed, dispatch the event
|
|
11146
11197
|
const inputEvent = new InputEvent('input', {
|
|
11147
11198
|
bubbles: true,
|
|
@@ -11260,7 +11311,16 @@ class BaseInput extends AuroElement {
|
|
|
11260
11311
|
|
|
11261
11312
|
if (formattedValue !== this.inputElement.value) {
|
|
11262
11313
|
this.skipNextProgrammaticInputEvent = true;
|
|
11263
|
-
if (
|
|
11314
|
+
if (this.maskInstance && this.type === 'credit-card') {
|
|
11315
|
+
// Route through the mask so its _value and el.value stay in lock-step
|
|
11316
|
+
// (set value calls updateControl which writes el.value = displayValue).
|
|
11317
|
+
// Writing el.value directly leaves the mask thinking displayValue is
|
|
11318
|
+
// stale; _saveSelection on the next focus/click then warns. Scoped to
|
|
11319
|
+
// credit-card so date's own formattedValue (raw ISO when calendar-invalid)
|
|
11320
|
+
// isn't re-masked through the mm/dd/yyyy mask, which would truncate it
|
|
11321
|
+
// and flip validity from patternMismatch to tooShort.
|
|
11322
|
+
this.maskInstance.value = formattedValue || '';
|
|
11323
|
+
} else if (formattedValue) {
|
|
11264
11324
|
this.inputElement.value = formattedValue;
|
|
11265
11325
|
} else {
|
|
11266
11326
|
this.inputElement.value = '';
|
|
@@ -11369,58 +11429,73 @@ class BaseInput extends AuroElement {
|
|
|
11369
11429
|
* @returns {void}
|
|
11370
11430
|
*/
|
|
11371
11431
|
configureAutoFormatting() {
|
|
11372
|
-
|
|
11373
|
-
|
|
11374
|
-
|
|
11375
|
-
|
|
11376
|
-
|
|
11377
|
-
this.
|
|
11378
|
-
|
|
11379
|
-
|
|
11380
|
-
|
|
11381
|
-
if (this.inputElement && maskOptions.mask) {
|
|
11382
|
-
|
|
11383
|
-
// Stash and clear any existing value before IMask init.
|
|
11384
|
-
// IMask's constructor processes the current input value which requires
|
|
11385
|
-
// selection state — clearing first avoids that scenario entirely.
|
|
11386
|
-
// When the format changes (e.g. locale switch) and we have a valid ISO
|
|
11387
|
-
// model value, compute the display string for the NEW format instead of
|
|
11388
|
-
// re-using the old display string, which may be invalid in the new mask.
|
|
11389
|
-
let existingValue = this.inputElement.value;
|
|
11390
|
-
if (
|
|
11391
|
-
this.util.isFullDateFormat(this.type, this.format) &&
|
|
11392
|
-
this.value &&
|
|
11393
|
-
dateFormatter.isValidDate(this.value) &&
|
|
11394
|
-
this.valueObject instanceof Date &&
|
|
11395
|
-
!Number.isNaN(this.valueObject.getTime()) &&
|
|
11396
|
-
typeof maskOptions.format === 'function'
|
|
11397
|
-
) {
|
|
11398
|
-
existingValue = maskOptions.format(this.valueObject);
|
|
11432
|
+
// Re-entrancy guard. The patched-setter's synthetic input event (suppressed
|
|
11433
|
+
// by _configuringMask above) could otherwise trigger handleInput →
|
|
11434
|
+
// processCreditCard → configureAutoFormatting before the outer call's
|
|
11435
|
+
// set value has finished its alignCursor pass.
|
|
11436
|
+
if (this._configuringMask) return;
|
|
11437
|
+
this._configuringMask = true;
|
|
11438
|
+
try {
|
|
11439
|
+
if (this.maskInstance) {
|
|
11440
|
+
this.maskInstance.destroy();
|
|
11399
11441
|
}
|
|
11400
11442
|
|
|
11401
|
-
|
|
11402
|
-
this.
|
|
11403
|
-
|
|
11404
|
-
this.maskInstance = IMask(this.inputElement, maskOptions);
|
|
11443
|
+
// Pass new format to util
|
|
11444
|
+
this.util.updateFormat(this.format);
|
|
11405
11445
|
|
|
11406
|
-
this.
|
|
11407
|
-
|
|
11408
|
-
|
|
11409
|
-
|
|
11446
|
+
const maskOptions = this.util.getMaskOptions(this.type, this.format);
|
|
11447
|
+
|
|
11448
|
+
if (this.inputElement && maskOptions.mask) {
|
|
11449
|
+
|
|
11450
|
+
// Stash and clear any existing value before IMask init.
|
|
11451
|
+
// IMask's constructor processes the current input value which requires
|
|
11452
|
+
// selection state — clearing first avoids that scenario entirely.
|
|
11453
|
+
// When the format changes (e.g. locale switch) and we have a valid ISO
|
|
11454
|
+
// model value, compute the display string for the NEW format instead of
|
|
11455
|
+
// re-using the old display string, which may be invalid in the new mask.
|
|
11456
|
+
let existingValue = this.inputElement.value;
|
|
11457
|
+
if (
|
|
11458
|
+
this.util.isFullDateFormat(this.type, this.format) &&
|
|
11459
|
+
this.value &&
|
|
11460
|
+
dateFormatter.isValidDate(this.value) &&
|
|
11461
|
+
this.valueObject instanceof Date &&
|
|
11462
|
+
!Number.isNaN(this.valueObject.getTime()) &&
|
|
11463
|
+
typeof maskOptions.format === 'function'
|
|
11464
|
+
) {
|
|
11465
|
+
existingValue = maskOptions.format(this.valueObject);
|
|
11410
11466
|
}
|
|
11411
|
-
});
|
|
11412
11467
|
|
|
11413
|
-
|
|
11414
|
-
this.value =
|
|
11415
|
-
|
|
11416
|
-
|
|
11417
|
-
|
|
11418
|
-
|
|
11468
|
+
this.skipNextProgrammaticInputEvent = true;
|
|
11469
|
+
this.inputElement.value = '';
|
|
11470
|
+
|
|
11471
|
+
this.maskInstance = IMask(this.inputElement, maskOptions);
|
|
11472
|
+
|
|
11473
|
+
this.maskInstance.on('accept', () => {
|
|
11474
|
+
// Suppress propagation during configureAutoFormatting's own value-restoration
|
|
11475
|
+
// (line below) — the mask emits 'accept' on every value-set, including ours,
|
|
11476
|
+
// and we don't want to overwrite a value the parent just pushed.
|
|
11477
|
+
if (this._configuringMask) return;
|
|
11478
|
+
this.value = this.util.toModelValue(this.maskInstance.value, this.format);
|
|
11479
|
+
if (this.type === "date") {
|
|
11480
|
+
this._rawMaskValue = this.maskInstance.value;
|
|
11481
|
+
}
|
|
11482
|
+
});
|
|
11419
11483
|
|
|
11420
|
-
|
|
11421
|
-
|
|
11422
|
-
|
|
11484
|
+
this.maskInstance.on('complete', () => {
|
|
11485
|
+
if (this._configuringMask) return;
|
|
11486
|
+
this.value = this.util.toModelValue(this.maskInstance.value, this.format);
|
|
11487
|
+
if (this.type === "date") {
|
|
11488
|
+
this._rawMaskValue = this.maskInstance.value;
|
|
11489
|
+
}
|
|
11490
|
+
});
|
|
11491
|
+
|
|
11492
|
+
// Restore the stashed value through IMask so it's properly masked
|
|
11493
|
+
if (existingValue) {
|
|
11494
|
+
this.maskInstance.value = existingValue;
|
|
11495
|
+
}
|
|
11423
11496
|
}
|
|
11497
|
+
} finally {
|
|
11498
|
+
this._configuringMask = false;
|
|
11424
11499
|
}
|
|
11425
11500
|
}
|
|
11426
11501
|
|
|
@@ -11707,10 +11782,10 @@ class BaseInput extends AuroElement {
|
|
|
11707
11782
|
},
|
|
11708
11783
|
{
|
|
11709
11784
|
name: 'Diners club',
|
|
11710
|
-
regex: /^(?<num>36|38)\d{0}/u,
|
|
11785
|
+
regex: /^(?<num>30[0-5]|36|38)\d{0}/u,
|
|
11711
11786
|
formatLength: 16,
|
|
11712
11787
|
errorMessage: CreditCardValidationMessage,
|
|
11713
|
-
cardIcon: '
|
|
11788
|
+
cardIcon: 'cc-dinersclub',
|
|
11714
11789
|
maskFormat: "0000 000000 0000"
|
|
11715
11790
|
},
|
|
11716
11791
|
{
|
|
@@ -12120,7 +12195,7 @@ class AuroHelpText extends LitElement {
|
|
|
12120
12195
|
}
|
|
12121
12196
|
}
|
|
12122
12197
|
|
|
12123
|
-
var formkitVersion = '
|
|
12198
|
+
var formkitVersion = '202606100232';
|
|
12124
12199
|
|
|
12125
12200
|
// Copyright (c) 2025 Alaska Airlines. All right reserved. Licensed under the Apache-2.0 license
|
|
12126
12201
|
// See LICENSE in the project root for license information.
|