@vaadin/date-picker 24.0.0-alpha1 → 24.0.0-alpha11

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/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@vaadin/date-picker",
3
- "version": "24.0.0-alpha1",
3
+ "version": "24.0.0-alpha11",
4
4
  "publishConfig": {
5
5
  "access": "public"
6
6
  },
@@ -36,14 +36,14 @@
36
36
  "dependencies": {
37
37
  "@open-wc/dedupe-mixin": "^1.3.0",
38
38
  "@polymer/polymer": "^3.2.0",
39
- "@vaadin/button": "24.0.0-alpha1",
40
- "@vaadin/component-base": "24.0.0-alpha1",
41
- "@vaadin/field-base": "24.0.0-alpha1",
42
- "@vaadin/input-container": "24.0.0-alpha1",
43
- "@vaadin/overlay": "24.0.0-alpha1",
44
- "@vaadin/vaadin-lumo-styles": "24.0.0-alpha1",
45
- "@vaadin/vaadin-material-styles": "24.0.0-alpha1",
46
- "@vaadin/vaadin-themable-mixin": "24.0.0-alpha1"
39
+ "@vaadin/button": "24.0.0-alpha11",
40
+ "@vaadin/component-base": "24.0.0-alpha11",
41
+ "@vaadin/field-base": "24.0.0-alpha11",
42
+ "@vaadin/input-container": "24.0.0-alpha11",
43
+ "@vaadin/overlay": "24.0.0-alpha11",
44
+ "@vaadin/vaadin-lumo-styles": "24.0.0-alpha11",
45
+ "@vaadin/vaadin-material-styles": "24.0.0-alpha11",
46
+ "@vaadin/vaadin-themable-mixin": "24.0.0-alpha11"
47
47
  },
48
48
  "devDependencies": {
49
49
  "@esm-bundle/chai": "^4.3.4",
@@ -54,5 +54,5 @@
54
54
  "web-types.json",
55
55
  "web-types.lit.json"
56
56
  ],
57
- "gitHead": "427527c27c4b27822d61fd41d38d7b170134770b"
57
+ "gitHead": "641b3d96ceeb3e503a093682ebe686afdd8c3a68"
58
58
  }
@@ -48,3 +48,20 @@ declare function extractDateParts(date: Date): { day: number; month: number; yea
48
48
  declare function dateAfterXMonths(months: number): number;
49
49
 
50
50
  export { dateAfterXMonths };
51
+
52
+ /**
53
+ * Calculate the year of the date based on the provided reference date
54
+ * Gets a two-digit year and returns a full year.
55
+ */
56
+ declare function getAdjustedYear(referenceDate: Date, year: number, month?: number, day?: number): Date;
57
+
58
+ export { getAdjustedYear };
59
+
60
+ /**
61
+ * Parse date string of one of the following date formats:
62
+ * - ISO 8601 `"YYYY-MM-DD"`
63
+ * - 6-digit extended ISO 8601 `"+YYYYYY-MM-DD"`, `"-YYYYYY-MM-DD"`
64
+ */
65
+ declare function parseDate(str: string): Date;
66
+
67
+ export { parseDate };
@@ -1,6 +1,6 @@
1
1
  /**
2
2
  * @license
3
- * Copyright (c) 2016 - 2022 Vaadin Ltd.
3
+ * Copyright (c) 2016 - 2023 Vaadin Ltd.
4
4
  * This program is available under Apache License Version 2.0, available at https://vaadin.com/license/
5
5
  */
6
6
 
@@ -117,3 +117,50 @@ export function dateAfterXMonths(months) {
117
117
  result.setMonth(parseInt(months) + today.getMonth());
118
118
  return result;
119
119
  }
120
+
121
+ /**
122
+ * Calculate the year of the date based on the provided reference date.
123
+ * Gets a two-digit year and returns a full year.
124
+ * @param {!Date} referenceDate The date to act as basis in the calculation
125
+ * @param {!number} year Should be in the range of [0, 99]
126
+ * @param {number} month
127
+ * @param {number} day
128
+ * @return {!number} Adjusted year value
129
+ */
130
+ export function getAdjustedYear(referenceDate, year, month = 0, day = 1) {
131
+ if (year > 99) {
132
+ throw new Error('The provided year cannot have more than 2 digits.');
133
+ }
134
+ if (year < 0) {
135
+ throw new Error('The provided year cannot be negative.');
136
+ }
137
+ // Year values up to 2 digits are parsed based on the reference date.
138
+ let adjustedYear = year + Math.floor(referenceDate.getFullYear() / 100) * 100;
139
+ if (referenceDate < new Date(adjustedYear - 50, month, day)) {
140
+ adjustedYear -= 100;
141
+ } else if (referenceDate > new Date(adjustedYear + 50, month, day)) {
142
+ adjustedYear += 100;
143
+ }
144
+ return adjustedYear;
145
+ }
146
+
147
+ /**
148
+ * Parse date string of one of the following date formats:
149
+ * - ISO 8601 `"YYYY-MM-DD"`
150
+ * - 6-digit extended ISO 8601 `"+YYYYYY-MM-DD"`, `"-YYYYYY-MM-DD"`
151
+ * @param {!string} str Date string to parse
152
+ * @return {Date} Parsed date
153
+ */
154
+ export function parseDate(str) {
155
+ // Parsing with RegExp to ensure correct format
156
+ const parts = /^([-+]\d{1}|\d{2,4}|[-+]\d{6})-(\d{1,2})-(\d{1,2})$/u.exec(str);
157
+ if (!parts) {
158
+ return undefined;
159
+ }
160
+
161
+ const date = new Date(0, 0); // Wrong date (1900-01-01), but with midnight in local time
162
+ date.setFullYear(parseInt(parts[1], 10));
163
+ date.setMonth(parseInt(parts[2], 10) - 1);
164
+ date.setDate(parseInt(parts[3], 10));
165
+ return date;
166
+ }
@@ -1,6 +1,6 @@
1
1
  /**
2
2
  * @license
3
- * Copyright (c) 2016 - 2022 Vaadin Ltd.
3
+ * Copyright (c) 2016 - 2023 Vaadin Ltd.
4
4
  * This program is available under Apache License Version 2.0, available at https://vaadin.com/license/
5
5
  */
6
6
  import { ValidateMixin } from '@vaadin/field-base/src/validate-mixin.js';
@@ -1,6 +1,6 @@
1
1
  /**
2
2
  * @license
3
- * Copyright (c) 2016 - 2022 Vaadin Ltd.
3
+ * Copyright (c) 2016 - 2023 Vaadin Ltd.
4
4
  * This program is available under Apache License Version 2.0, available at https://vaadin.com/license/
5
5
  */
6
6
  import './vaadin-date-picker-overlay.js';
@@ -96,14 +96,6 @@ class DatePickerLight extends ThemableMixin(DatePickerMixin(ValidateMixin(Polyme
96
96
  };
97
97
  }
98
98
 
99
- /** @protected */
100
- connectedCallback() {
101
- super.connectedCallback();
102
- const cssSelector = 'vaadin-text-field,.input';
103
- this._setInputElement(this.querySelector(cssSelector));
104
- this._setFocusElement(this.inputElement);
105
- }
106
-
107
99
  /** @return {string | undefined} */
108
100
  get _inputValue() {
109
101
  return this.inputElement && this.inputElement[dashToCamelCase(this.attrForValue)];
@@ -115,6 +107,14 @@ class DatePickerLight extends ThemableMixin(DatePickerMixin(ValidateMixin(Polyme
115
107
  }
116
108
  }
117
109
 
110
+ /** @protected */
111
+ connectedCallback() {
112
+ super.connectedCallback();
113
+ const cssSelector = 'vaadin-text-field,.input';
114
+ this._setInputElement(this.querySelector(cssSelector));
115
+ this._setFocusElement(this.inputElement);
116
+ }
117
+
118
118
  // Workaround https://github.com/vaadin/web-components/issues/2855
119
119
  /** @protected */
120
120
  _openedChanged(opened) {
@@ -1,13 +1,14 @@
1
1
  /**
2
2
  * @license
3
- * Copyright (c) 2016 - 2022 Vaadin Ltd.
3
+ * Copyright (c) 2016 - 2023 Vaadin Ltd.
4
4
  * This program is available under Apache License Version 2.0, available at https://vaadin.com/license/
5
5
  */
6
6
  import type { Constructor } from '@open-wc/dedupe-mixin';
7
+ import type { DelegateFocusMixinClass } from '@vaadin/component-base/src/delegate-focus-mixin.js';
7
8
  import type { DisabledMixinClass } from '@vaadin/component-base/src/disabled-mixin.js';
8
9
  import type { FocusMixinClass } from '@vaadin/component-base/src/focus-mixin.js';
9
10
  import type { KeyboardMixinClass } from '@vaadin/component-base/src/keyboard-mixin.js';
10
- import type { DelegateFocusMixinClass } from '@vaadin/field-base/src/delegate-focus-mixin.js';
11
+ import type { OverlayClassMixinClass } from '@vaadin/component-base/src/overlay-class-mixin.js';
11
12
  import type { InputConstraintsMixinClass } from '@vaadin/field-base/src/input-constraints-mixin.js';
12
13
  import type { InputMixinClass } from '@vaadin/field-base/src/input-mixin.js';
13
14
 
@@ -18,14 +19,69 @@ export interface DatePickerDate {
18
19
  }
19
20
 
20
21
  export interface DatePickerI18n {
22
+ /**
23
+ * An array with the full names of months starting
24
+ * with January.
25
+ */
21
26
  monthNames: string[];
27
+ /**
28
+ * An array of weekday names starting with Sunday. Used
29
+ * in screen reader announcements.
30
+ */
22
31
  weekdays: string[];
32
+ /**
33
+ * An array of short weekday names starting with Sunday.
34
+ * Displayed in the calendar.
35
+ */
23
36
  weekdaysShort: string[];
37
+ /**
38
+ * An integer indicating the first day of the week
39
+ * (0 = Sunday, 1 = Monday, etc.).
40
+ */
24
41
  firstDayOfWeek: number;
42
+ /**
43
+ * Translation of the Today shortcut button text.
44
+ */
25
45
  today: string;
46
+ /**
47
+ * Translation of the Cancel button text.
48
+ */
26
49
  cancel: string;
50
+ /**
51
+ * Used for adjusting the year value when parsing dates with short years.
52
+ * The year values between 0 and 99 are evaluated and adjusted.
53
+ * Example: for a referenceDate of 1970-10-30;
54
+ * dateToBeParsed: 40-10-30, result: 1940-10-30
55
+ * dateToBeParsed: 80-10-30, result: 1980-10-30
56
+ * dateToBeParsed: 10-10-30, result: 2010-10-30
57
+ * Supported date format: ISO 8601 `"YYYY-MM-DD"` (default)
58
+ * The default value is the current date.
59
+ */
60
+ referenceDate: string;
61
+
62
+ /**
63
+ * A function to parse the given text to an `Object` in the format `{ day: ..., month: ..., year: ... }`.
64
+ * Must properly parse (at least) text formatted by `formatDate`.
65
+ * Setting the property to null will disable keyboard input feature.
66
+ * Note: The argument month is 0-based. This means that January = 0 and December = 11.
67
+ * @param date
68
+ */
27
69
  parseDate(date: string): DatePickerDate | undefined;
70
+
71
+ /**
72
+ * A function to format given `Object` as
73
+ * date string. Object is in the format `{ day: ..., month: ..., year: ... }`
74
+ * Note: The argument month is 0-based. This means that January = 0 and December = 11.
75
+ * @param date
76
+ */
28
77
  formatDate(date: DatePickerDate): string;
78
+
79
+ /**
80
+ * A function to format given `monthName` and
81
+ * `fullYear` integer as calendar title string.
82
+ * @param monthName
83
+ * @param fullYear
84
+ */
29
85
  formatTitle(monthName: string, fullYear: number): string;
30
86
  }
31
87
 
@@ -38,6 +94,7 @@ export declare function DatePickerMixin<T extends Constructor<HTMLElement>>(
38
94
  Constructor<InputConstraintsMixinClass> &
39
95
  Constructor<InputMixinClass> &
40
96
  Constructor<KeyboardMixinClass> &
97
+ Constructor<OverlayClassMixinClass> &
41
98
  T;
42
99
 
43
100
  export declare class DatePickerMixinClass {
@@ -125,6 +182,16 @@ export declare class DatePickerMixinClass {
125
182
  * // Translation of the Cancel button text.
126
183
  * cancel: 'Cancel',
127
184
  *
185
+ * // Used for adjusting the year value when parsing dates with short years.
186
+ * // The year values between 0 and 99 are evaluated and adjusted.
187
+ * // Example: for a referenceDate of 1970-10-30;
188
+ * // dateToBeParsed: 40-10-30, result: 1940-10-30
189
+ * // dateToBeParsed: 80-10-30, result: 1980-10-30
190
+ * // dateToBeParsed: 10-10-30, result: 2010-10-30
191
+ * // Supported date format: ISO 8601 `"YYYY-MM-DD"` (default)
192
+ * // The default value is the current date.
193
+ * referenceDate: '',
194
+ *
128
195
  * // A function to format given `Object` as
129
196
  * // date string. Object is in the format `{ day: ..., month: ..., year: ... }`
130
197
  * // Note: The argument month is 0-based. This means that January = 0 and December = 11.
@@ -1,24 +1,37 @@
1
1
  /**
2
2
  * @license
3
- * Copyright (c) 2016 - 2022 Vaadin Ltd.
3
+ * Copyright (c) 2016 - 2023 Vaadin Ltd.
4
4
  * This program is available under Apache License Version 2.0, available at https://vaadin.com/license/
5
5
  */
6
6
  import { isIOS } from '@vaadin/component-base/src/browser-utils.js';
7
7
  import { ControllerMixin } from '@vaadin/component-base/src/controller-mixin.js';
8
+ import { DelegateFocusMixin } from '@vaadin/component-base/src/delegate-focus-mixin.js';
8
9
  import { KeyboardMixin } from '@vaadin/component-base/src/keyboard-mixin.js';
9
10
  import { MediaQueryController } from '@vaadin/component-base/src/media-query-controller.js';
10
- import { DelegateFocusMixin } from '@vaadin/field-base/src/delegate-focus-mixin.js';
11
+ import { OverlayClassMixin } from '@vaadin/component-base/src/overlay-class-mixin.js';
11
12
  import { InputConstraintsMixin } from '@vaadin/field-base/src/input-constraints-mixin.js';
12
13
  import { VirtualKeyboardController } from '@vaadin/field-base/src/virtual-keyboard-controller.js';
13
- import { dateAllowed, dateEquals, extractDateParts, getClosestDate } from './vaadin-date-picker-helper.js';
14
+ import {
15
+ dateAllowed,
16
+ dateEquals,
17
+ extractDateParts,
18
+ getAdjustedYear,
19
+ getClosestDate,
20
+ parseDate,
21
+ } from './vaadin-date-picker-helper.js';
14
22
 
15
23
  /**
16
24
  * @polymerMixin
25
+ * @mixes ControllerMixin
26
+ * @mixes DelegateFocusMixin
27
+ * @mixes InputConstraintsMixin
28
+ * @mixes KeyboardMixin
29
+ * @mixes OverlayClassMixin
17
30
  * @param {function(new:HTMLElement)} subclass
18
31
  */
19
32
  export const DatePickerMixin = (subclass) =>
20
- class VaadinDatePickerMixin extends ControllerMixin(
21
- DelegateFocusMixin(InputConstraintsMixin(KeyboardMixin(subclass))),
33
+ class DatePickerMixinClass extends OverlayClassMixin(
34
+ ControllerMixin(DelegateFocusMixin(InputConstraintsMixin(KeyboardMixin(subclass)))),
22
35
  ) {
23
36
  static get properties() {
24
37
  return {
@@ -152,6 +165,16 @@ export const DatePickerMixin = (subclass) =>
152
165
  * // Translation of the Cancel button text.
153
166
  * cancel: 'Cancel',
154
167
  *
168
+ * // Used for adjusting the year value when parsing dates with short years.
169
+ * // The year values between 0 and 99 are evaluated and adjusted.
170
+ * // Example: for a referenceDate of 1970-10-30;
171
+ * // dateToBeParsed: 40-10-30, result: 1940-10-30
172
+ * // dateToBeParsed: 80-10-30, result: 1980-10-30
173
+ * // dateToBeParsed: 10-10-30, result: 2010-10-30
174
+ * // Supported date format: ISO 8601 `"YYYY-MM-DD"` (default)
175
+ * // The default value is the current date.
176
+ * referenceDate: '',
177
+ *
155
178
  * // A function to format given `Object` as
156
179
  * // date string. Object is in the format `{ day: ..., month: ..., year: ... }`
157
180
  * // Note: The argument month is 0-based. This means that January = 0 and December = 11.
@@ -203,11 +226,12 @@ export const DatePickerMixin = (subclass) =>
203
226
  firstDayOfWeek: 0,
204
227
  today: 'Today',
205
228
  cancel: 'Cancel',
206
- formatDate: (d) => {
207
- const yearStr = String(d.year).replace(/\d+/, (y) => '0000'.substr(y.length) + y);
229
+ referenceDate: '',
230
+ formatDate(d) {
231
+ const yearStr = String(d.year).replace(/\d+/u, (y) => '0000'.substr(y.length) + y);
208
232
  return [d.month + 1, d.day, yearStr].join('/');
209
233
  },
210
- parseDate: (text) => {
234
+ parseDate(text) {
211
235
  const parts = text.split('/');
212
236
  const today = new Date();
213
237
  let date,
@@ -215,12 +239,13 @@ export const DatePickerMixin = (subclass) =>
215
239
  year = today.getFullYear();
216
240
 
217
241
  if (parts.length === 3) {
242
+ month = parseInt(parts[0]) - 1;
243
+ date = parseInt(parts[1]);
218
244
  year = parseInt(parts[2]);
219
245
  if (parts[2].length < 3 && year >= 0) {
220
- year += year < 50 ? 2000 : 1900;
246
+ const usedReferenceDate = this.referenceDate ? parseDate(this.referenceDate) : new Date();
247
+ year = getAdjustedYear(usedReferenceDate, year, month, date);
221
248
  }
222
- month = parseInt(parts[0]) - 1;
223
- date = parseInt(parts[1]);
224
249
  } else if (parts.length === 2) {
225
250
  month = parseInt(parts[0]) - 1;
226
251
  date = parseInt(parts[1]);
@@ -319,6 +344,14 @@ export const DatePickerMixin = (subclass) =>
319
344
  return [...super.constraints, 'min', 'max'];
320
345
  }
321
346
 
347
+ constructor() {
348
+ super();
349
+
350
+ this._boundOnClick = this._onClick.bind(this);
351
+ this._boundOnScroll = this._onScroll.bind(this);
352
+ this._boundOverlayRenderer = this._overlayRenderer.bind(this);
353
+ }
354
+
322
355
  /**
323
356
  * Override a getter from `InputControlMixin` to make it optional
324
357
  * and to prevent warning when a clear button is missing,
@@ -330,18 +363,6 @@ export const DatePickerMixin = (subclass) =>
330
363
  return null;
331
364
  }
332
365
 
333
- /** @protected */
334
- get _inputValue() {
335
- return this.inputElement ? this.inputElement.value : undefined;
336
- }
337
-
338
- /** @protected */
339
- set _inputValue(value) {
340
- if (this.inputElement) {
341
- this.inputElement.value = value;
342
- }
343
- }
344
-
345
366
  /** @private */
346
367
  get _nativeInput() {
347
368
  if (this.inputElement) {
@@ -351,12 +372,16 @@ export const DatePickerMixin = (subclass) =>
351
372
  return null;
352
373
  }
353
374
 
354
- constructor() {
355
- super();
375
+ /** @protected */
376
+ get _inputValue() {
377
+ return this.inputElement ? this.inputElement.value : undefined;
378
+ }
356
379
 
357
- this._boundOnClick = this._onClick.bind(this);
358
- this._boundOnScroll = this._onScroll.bind(this);
359
- this._boundOverlayRenderer = this._overlayRenderer.bind(this);
380
+ /** @protected */
381
+ set _inputValue(value) {
382
+ if (this.inputElement) {
383
+ this.inputElement.value = value;
384
+ }
360
385
  }
361
386
 
362
387
  /**
@@ -380,10 +405,7 @@ export const DatePickerMixin = (subclass) =>
380
405
 
381
406
  if (!this.opened) {
382
407
  if (this.autoOpenDisabled) {
383
- const parsedDate = this._getParsedDate();
384
- if (this._isValidDate(parsedDate)) {
385
- this._selectDate(parsedDate);
386
- }
408
+ this._selectParsedOrFocusedDate();
387
409
  }
388
410
 
389
411
  this.validate();
@@ -408,7 +430,10 @@ export const DatePickerMixin = (subclass) =>
408
430
 
409
431
  this.addController(new VirtualKeyboardController(this));
410
432
 
411
- this.$.overlay.renderer = this._boundOverlayRenderer;
433
+ const overlay = this.$.overlay;
434
+ this._overlayElement = overlay;
435
+
436
+ overlay.renderer = this._boundOverlayRenderer;
412
437
 
413
438
  this.addEventListener('mousedown', () => this.__bringToFront());
414
439
  this.addEventListener('touchstart', () => this.__bringToFront());
@@ -606,21 +631,6 @@ export const DatePickerMixin = (subclass) =>
606
631
  });
607
632
  }
608
633
 
609
- /** @private */
610
- _parseDate(str) {
611
- // Parsing with RegExp to ensure correct format
612
- const parts = /^([-+]\d{1}|\d{2,4}|[-+]\d{6})-(\d{1,2})-(\d{1,2})$/.exec(str);
613
- if (!parts) {
614
- return;
615
- }
616
-
617
- const date = new Date(0, 0); // Wrong date (1900-01-01), but with midnight in local time
618
- date.setFullYear(parseInt(parts[1], 10));
619
- date.setMonth(parseInt(parts[2], 10) - 1);
620
- date.setDate(parseInt(parts[3], 10));
621
- return date;
622
- }
623
-
624
634
  /** @private */
625
635
  // eslint-disable-next-line max-params
626
636
  _isNoInput(inputElement, fullscreen, ios, i18n, opened, autoOpenDisabled) {
@@ -723,7 +733,7 @@ export const DatePickerMixin = (subclass) =>
723
733
  * @override
724
734
  */
725
735
  _valueChanged(value, oldValue) {
726
- const newDate = this._parseDate(value);
736
+ const newDate = parseDate(value);
727
737
 
728
738
  if (value && !newDate) {
729
739
  // The new value cannot be parsed, revert the old value.
@@ -790,21 +800,17 @@ export const DatePickerMixin = (subclass) =>
790
800
 
791
801
  /** @protected */
792
802
  _onOverlayOpened() {
793
- const parsedInitialPosition = this._parseDate(this.initialPosition);
794
-
795
- const initialPosition =
796
- this._selectedDate || this._overlayContent.initialPosition || parsedInitialPosition || new Date();
803
+ // Detect which date to show
804
+ const initialPosition = this._getInitialPosition();
805
+ this._overlayContent.initialPosition = initialPosition;
797
806
 
798
- if (parsedInitialPosition || dateAllowed(initialPosition, this._minDate, this._maxDate)) {
799
- this._overlayContent.initialPosition = initialPosition;
800
- } else {
801
- this._overlayContent.initialPosition = getClosestDate(initialPosition, [this._minDate, this._maxDate]);
802
- }
807
+ // Scroll the date into view
808
+ const scrollFocusDate = this._overlayContent.focusedDate || initialPosition;
809
+ this._overlayContent.scrollToDate(scrollFocusDate);
803
810
 
804
- this._overlayContent.scrollToDate(this._overlayContent.focusedDate || this._overlayContent.initialPosition);
805
- // Have a default focused date
811
+ // Ensure the date is focused
806
812
  this._ignoreFocusedDateChange = true;
807
- this._overlayContent.focusedDate = this._overlayContent.focusedDate || this._overlayContent.initialPosition;
813
+ this._overlayContent.focusedDate = scrollFocusDate;
808
814
  this._ignoreFocusedDateChange = false;
809
815
 
810
816
  window.addEventListener('scroll', this._boundOnScroll, true);
@@ -822,6 +828,18 @@ export const DatePickerMixin = (subclass) =>
822
828
  }
823
829
  }
824
830
 
831
+ /** @private */
832
+ _getInitialPosition() {
833
+ const parsedInitialPosition = parseDate(this.initialPosition);
834
+
835
+ const initialPosition =
836
+ this._selectedDate || this._overlayContent.initialPosition || parsedInitialPosition || new Date();
837
+
838
+ return parsedInitialPosition || dateAllowed(initialPosition, this._minDate, this._maxDate)
839
+ ? initialPosition
840
+ : getClosestDate(initialPosition, [this._minDate, this._maxDate]);
841
+ }
842
+
825
843
  /** @private */
826
844
  _selectParsedOrFocusedDate() {
827
845
  // Select the parsed input or focused date
@@ -1019,21 +1037,15 @@ export const DatePickerMixin = (subclass) =>
1019
1037
  * @override
1020
1038
  */
1021
1039
  _onEnter(_event) {
1022
- const parsedDate = this._getParsedDate();
1023
- const isValidDate = this._isValidDate(parsedDate);
1040
+ const oldValue = this.value;
1024
1041
  if (this.opened) {
1025
- if (this._overlayContent && this._overlayContent.focusedDate && isValidDate) {
1026
- this._selectDate(this._overlayContent.focusedDate);
1027
- }
1042
+ // Closing will implicitly select parsed or focused date
1028
1043
  this.close();
1029
- } else if (!isValidDate && this.inputElement.value !== '') {
1030
- this.validate();
1031
1044
  } else {
1032
- const oldValue = this.value;
1033
1045
  this._selectParsedOrFocusedDate();
1034
- if (oldValue === this.value) {
1035
- this.validate();
1036
- }
1046
+ }
1047
+ if (oldValue === this.value) {
1048
+ this.validate();
1037
1049
  }
1038
1050
  }
1039
1051
 
@@ -1075,7 +1087,7 @@ export const DatePickerMixin = (subclass) =>
1075
1087
  /** @private */
1076
1088
  _getParsedDate(inputValue = this._inputValue) {
1077
1089
  const dateObject = this.i18n.parseDate && this.i18n.parseDate(inputValue);
1078
- const parsedDate = dateObject && this._parseDate(`${dateObject.year}-${dateObject.month + 1}-${dateObject.day}`);
1090
+ const parsedDate = dateObject && parseDate(`${dateObject.year}-${dateObject.month + 1}-${dateObject.day}`);
1079
1091
  return parsedDate;
1080
1092
  }
1081
1093
 
@@ -1112,7 +1124,7 @@ export const DatePickerMixin = (subclass) =>
1112
1124
 
1113
1125
  /** @private */
1114
1126
  __computeMinOrMaxDate(dateString) {
1115
- return this._parseDate(dateString);
1127
+ return parseDate(dateString);
1116
1128
  }
1117
1129
 
1118
1130
  /**
@@ -1,6 +1,6 @@
1
1
  /**
2
2
  * @license
3
- * Copyright (c) 2016 - 2022 Vaadin Ltd.
3
+ * Copyright (c) 2016 - 2023 Vaadin Ltd.
4
4
  * This program is available under Apache License Version 2.0, available at https://vaadin.com/license/
5
5
  */
6
6
  import { html } from '@polymer/polymer/lib/utils/html-tag.js';