@universal-material/web 3.7.2 → 3.8.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/app-bar/top-app-bar.d.ts +15 -0
- package/app-bar/top-app-bar.d.ts.map +1 -1
- package/app-bar/top-app-bar.js +15 -0
- package/app-bar/top-app-bar.js.map +1 -1
- package/badge/badge.d.ts +3 -0
- package/badge/badge.d.ts.map +1 -1
- package/badge/badge.js +3 -0
- package/badge/badge.js.map +1 -1
- package/bundle.min.js +600 -482
- package/button/button-base.d.ts +7 -0
- package/button/button-base.d.ts.map +1 -1
- package/button/button-base.js +7 -0
- package/button/button-base.js.map +1 -1
- package/button/button.d.ts +3 -0
- package/button/button.d.ts.map +1 -1
- package/button/button.js +3 -0
- package/button/button.js.map +1 -1
- package/button/icon-button.d.ts +6 -0
- package/button/icon-button.d.ts.map +1 -1
- package/button/icon-button.js +6 -0
- package/button/icon-button.js.map +1 -1
- package/button-field/button-field.d.ts +3 -0
- package/button-field/button-field.d.ts.map +1 -1
- package/button-field/button-field.js +3 -0
- package/button-field/button-field.js.map +1 -1
- package/calendar/calendar-adapter.d.ts +3 -0
- package/calendar/calendar-adapter.d.ts.map +1 -1
- package/calendar/calendar-adapter.js.map +1 -1
- package/calendar/calendar-base.d.ts +17 -0
- package/calendar/calendar-base.d.ts.map +1 -1
- package/calendar/calendar-base.js +182 -19
- package/calendar/calendar-base.js.map +1 -1
- package/calendar/calendar.d.ts +4 -0
- package/calendar/calendar.d.ts.map +1 -1
- package/calendar/calendar.js +4 -0
- package/calendar/calendar.js.map +1 -1
- package/calendar/default-calendar-adapter.d.ts +3 -0
- package/calendar/default-calendar-adapter.d.ts.map +1 -1
- package/calendar/default-calendar-adapter.js +17 -5
- package/calendar/default-calendar-adapter.js.map +1 -1
- package/card/card-content.d.ts +5 -0
- package/card/card-content.d.ts.map +1 -1
- package/card/card-content.js +5 -0
- package/card/card-content.js.map +1 -1
- package/card/card-media.d.ts +3 -0
- package/card/card-media.d.ts.map +1 -1
- package/card/card-media.js +3 -0
- package/card/card-media.js.map +1 -1
- package/checkbox/checkbox.d.ts +7 -0
- package/checkbox/checkbox.d.ts.map +1 -1
- package/checkbox/checkbox.js +7 -0
- package/checkbox/checkbox.js.map +1 -1
- package/chip/chip.d.ts +3 -0
- package/chip/chip.d.ts.map +1 -1
- package/chip/chip.js +3 -0
- package/chip/chip.js.map +1 -1
- package/chip-field/chip-field.d.ts +3 -0
- package/chip-field/chip-field.d.ts.map +1 -1
- package/chip-field/chip-field.js.map +1 -1
- package/custom-elements.json +12881 -9853
- package/datepicker/datepicker.d.ts +51 -2
- package/datepicker/datepicker.d.ts.map +1 -1
- package/datepicker/datepicker.js +185 -3
- package/datepicker/datepicker.js.map +1 -1
- package/datepicker/format.d.ts +19 -0
- package/datepicker/format.d.ts.map +1 -0
- package/datepicker/format.js +47 -0
- package/datepicker/format.js.map +1 -0
- package/datepicker/range-datepicker.d.ts +56 -0
- package/datepicker/range-datepicker.d.ts.map +1 -0
- package/datepicker/range-datepicker.js +198 -0
- package/datepicker/range-datepicker.js.map +1 -0
- package/dialog/dialog.d.ts +8 -0
- package/dialog/dialog.d.ts.map +1 -1
- package/dialog/dialog.js +8 -0
- package/dialog/dialog.js.map +1 -1
- package/field/field-base.d.ts +14 -0
- package/field/field-base.d.ts.map +1 -1
- package/field/field-base.js +10 -0
- package/field/field-base.js.map +1 -1
- package/field/field.d.ts +4 -0
- package/field/field.d.ts.map +1 -1
- package/field/field.js +4 -0
- package/field/field.js.map +1 -1
- package/index.d.ts +5 -0
- package/index.d.ts.map +1 -1
- package/index.js +5 -0
- package/index.js.map +1 -1
- package/list/list-item.d.ts +3 -0
- package/list/list-item.d.ts.map +1 -1
- package/list/list-item.js +3 -0
- package/list/list-item.js.map +1 -1
- package/menu/menu-item.d.ts +6 -0
- package/menu/menu-item.d.ts.map +1 -1
- package/menu/menu-item.js +6 -0
- package/menu/menu-item.js.map +1 -1
- package/menu/menu.d.ts +16 -0
- package/menu/menu.d.ts.map +1 -1
- package/menu/menu.js +24 -5
- package/menu/menu.js.map +1 -1
- package/menu/menu.styles.d.ts.map +1 -1
- package/menu/menu.styles.js +5 -0
- package/menu/menu.styles.js.map +1 -1
- package/navigation/drawer-headline.styles.js +1 -1
- package/navigation/drawer-headline.styles.js.map +1 -1
- package/overflow-menu/overflow-menu-item.d.ts +8 -0
- package/overflow-menu/overflow-menu-item.d.ts.map +1 -1
- package/overflow-menu/overflow-menu-item.js +8 -0
- package/overflow-menu/overflow-menu-item.js.map +1 -1
- package/package.json +3 -3
- package/progress/circular-progress.d.ts +7 -0
- package/progress/circular-progress.d.ts.map +1 -1
- package/progress/circular-progress.js +3 -0
- package/progress/circular-progress.js.map +1 -1
- package/progress/progress-bar.d.ts +7 -0
- package/progress/progress-bar.d.ts.map +1 -1
- package/progress/progress-bar.js +3 -0
- package/progress/progress-bar.js.map +1 -1
- package/radio/radio.d.ts +3 -0
- package/radio/radio.d.ts.map +1 -1
- package/radio/radio.js +3 -0
- package/radio/radio.js.map +1 -1
- package/search/search.d.ts +3 -0
- package/search/search.d.ts.map +1 -1
- package/search/search.js +3 -0
- package/search/search.js.map +1 -1
- package/select/option.d.ts +6 -0
- package/select/option.d.ts.map +1 -1
- package/select/option.js +6 -0
- package/select/option.js.map +1 -1
- package/select/select.d.ts +4 -0
- package/select/select.d.ts.map +1 -1
- package/select/select.js +4 -0
- package/select/select.js.map +1 -1
- package/shared/button-wrapper.d.ts +3 -0
- package/shared/button-wrapper.d.ts.map +1 -1
- package/shared/button-wrapper.js.map +1 -1
- package/shared/char-count-text-field/native-text-field-wrapper.d.ts +13 -0
- package/shared/char-count-text-field/native-text-field-wrapper.d.ts.map +1 -1
- package/shared/char-count-text-field/native-text-field-wrapper.js +10 -0
- package/shared/char-count-text-field/native-text-field-wrapper.js.map +1 -1
- package/shared/selection-control/selection-control-list-item.d.ts.map +1 -1
- package/shared/selection-control/selection-control-list-item.js +4 -0
- package/shared/selection-control/selection-control-list-item.js.map +1 -1
- package/shared/selection-control/selection-control.d.ts +9 -0
- package/shared/selection-control/selection-control.d.ts.map +1 -1
- package/shared/selection-control/selection-control.js +9 -0
- package/shared/selection-control/selection-control.js.map +1 -1
- package/shared/text-field-base/text-field-base.d.ts +3 -0
- package/shared/text-field-base/text-field-base.d.ts.map +1 -1
- package/shared/text-field-base/text-field-base.js +3 -0
- package/shared/text-field-base/text-field-base.js.map +1 -1
- package/snackbar/snackbar.d.ts +9 -0
- package/snackbar/snackbar.d.ts.map +1 -1
- package/snackbar/snackbar.js +9 -0
- package/snackbar/snackbar.js.map +1 -1
- package/tab-bar/tab-bar.d.ts +3 -0
- package/tab-bar/tab-bar.d.ts.map +1 -1
- package/tab-bar/tab-bar.js +3 -0
- package/tab-bar/tab-bar.js.map +1 -1
- package/tab-bar/tab.d.ts +5 -0
- package/tab-bar/tab.d.ts.map +1 -1
- package/tab-bar/tab.js +5 -0
- package/tab-bar/tab.js.map +1 -1
- package/text-area/text-area.d.ts +3 -0
- package/text-area/text-area.d.ts.map +1 -1
- package/text-area/text-area.js +3 -0
- package/text-area/text-area.js.map +1 -1
- package/text-field/text-field.d.ts +16 -0
- package/text-field/text-field.d.ts.map +1 -1
- package/text-field/text-field.js +7 -0
- package/text-field/text-field.js.map +1 -1
- package/typeahead/typeahead-template-render.d.ts +4 -0
- package/typeahead/typeahead-template-render.d.ts.map +1 -1
- package/typeahead/typeahead-template-render.js +4 -0
- package/typeahead/typeahead-template-render.js.map +1 -1
- package/typeahead/typeahead.d.ts +7 -0
- package/typeahead/typeahead.d.ts.map +1 -1
- package/typeahead/typeahead.js +7 -0
- package/typeahead/typeahead.js.map +1 -1
- package/vscode.html-custom-data.json +661 -230
|
@@ -1,5 +1,54 @@
|
|
|
1
|
-
import {
|
|
2
|
-
|
|
1
|
+
import { CSSResultGroup } from '@lit/reactive-element/css-tag';
|
|
2
|
+
import { HTMLTemplateResult } from 'lit';
|
|
3
|
+
import { UmNativeTextFieldWrapper } from '../shared/char-count-text-field/native-text-field-wrapper.js';
|
|
4
|
+
import { DatepickerFormat } from './format.js';
|
|
5
|
+
import '../calendar/calendar.js';
|
|
6
|
+
import '../menu/menu.js';
|
|
7
|
+
export declare class UmDatepicker extends UmNativeTextFieldWrapper {
|
|
8
|
+
#private;
|
|
9
|
+
static styles: CSSResultGroup;
|
|
10
|
+
/**
|
|
11
|
+
* The BCP 47 locale tag forwarded to the underlying calendar and used for
|
|
12
|
+
* non-editable display formatting.
|
|
13
|
+
* When `null`, the calendar falls back to the browser's `navigator.language`.
|
|
14
|
+
*/
|
|
15
|
+
locale: string | null;
|
|
16
|
+
/**
|
|
17
|
+
* Format used when displaying the value while the field is not editable.
|
|
18
|
+
* Accepts the named presets `'short'`, `'medium'`, `'long'`, `'full'`,
|
|
19
|
+
* the literal `'iso'` (keeps the ISO `YYYY-MM-DD` value), or an
|
|
20
|
+
* `Intl.DateTimeFormatOptions` object for custom formatting.
|
|
21
|
+
* In editable mode the input uses the browser's native `type="date"` mask
|
|
22
|
+
* and ignores this property.
|
|
23
|
+
*/
|
|
24
|
+
format: DatepickerFormat;
|
|
25
|
+
/**
|
|
26
|
+
* Whether the input accepts manually-typed dates. When `false` (default),
|
|
27
|
+
* the field is read-only and clicking anywhere opens the calendar popover.
|
|
28
|
+
* When `true`, the input uses native `type="date"` and accepts keyboard input;
|
|
29
|
+
* the calendar popover is opened via the trailing icon.
|
|
30
|
+
*/
|
|
31
|
+
editable: boolean;
|
|
32
|
+
/**
|
|
33
|
+
* Whether the input is read-only. When set, manual typing is disabled even
|
|
34
|
+
* if `editable` is `true`; the calendar popover remains available.
|
|
35
|
+
*/
|
|
36
|
+
readOnly: boolean;
|
|
37
|
+
/**
|
|
38
|
+
* The positioning strategy used by the calendar popover. Use `'fixed'`
|
|
39
|
+
* when the datepicker is rendered inside a clipped/scrollable container.
|
|
40
|
+
*/
|
|
41
|
+
menuPositioning: 'relative' | 'fixed';
|
|
42
|
+
input: HTMLInputElement;
|
|
43
|
+
private _menu;
|
|
44
|
+
private _calendar;
|
|
45
|
+
private _trailingSlot;
|
|
46
|
+
protected renderControl(): HTMLTemplateResult;
|
|
47
|
+
protected renderDefaultTrailingIcon(): import("lit-html").TemplateResult<2>;
|
|
48
|
+
protected renderAfterContent(): import("lit-html").TemplateResult<1>;
|
|
49
|
+
connectedCallback(): void;
|
|
50
|
+
disconnectedCallback(): void;
|
|
51
|
+
protected _handleInput(): void;
|
|
3
52
|
}
|
|
4
53
|
declare global {
|
|
5
54
|
interface HTMLElementTagNameMap {
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"datepicker.d.ts","sourceRoot":"","sources":["../../src/datepicker/datepicker.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,
|
|
1
|
+
{"version":3,"file":"datepicker.d.ts","sourceRoot":"","sources":["../../src/datepicker/datepicker.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,cAAc,EAAE,MAAM,+BAA+B,CAAC;AAE/D,OAAO,EAAQ,kBAAkB,EAAgB,MAAM,KAAK,CAAC;AAM7D,OAAO,EAAE,wBAAwB,EAAE,MAAM,8DAA8D,CAAC;AAKxG,OAAO,EAAE,gBAAgB,EAAiB,MAAM,aAAa,CAAC;AAE9D,OAAO,yBAAyB,CAAC;AACjC,OAAO,iBAAiB,CAAC;AAIzB,qBACa,YAAa,SAAQ,wBAAwB;;IACxD,OAAgB,MAAM,EAAE,cAAc,CAAqD;IAE3F;;;;OAIG;IACS,MAAM,EAAE,MAAM,GAAG,IAAI,CAAQ;IAEzC;;;;;;;OAOG;IACS,MAAM,EAAE,gBAAgB,CAAW;IAE/C;;;;;OAKG;IACyC,QAAQ,UAAS;IAE7D;;;OAGG;IACyC,QAAQ,UAAS;IAE7D;;;OAGG;IACyD,eAAe,EAAE,UAAU,GAAG,OAAO,CAAc;IAE/F,KAAK,EAAG,gBAAgB,CAAC;IAClB,OAAO,CAAC,KAAK,CAAU;IACnB,OAAO,CAAC,SAAS,CAAc;IAC3B,OAAO,CAAC,aAAa,CAAmB;cAEpD,aAAa,IAAI,kBAAkB;cAmCnC,yBAAyB;cAOzB,kBAAkB;IAkB5B,iBAAiB,IAAI,IAAI;IAKzB,oBAAoB,IAAI,IAAI;cAKlB,YAAY,IAAI,IAAI;CAmDxC;AAED,OAAO,CAAC,MAAM,CAAC;IACb,UAAU,qBAAqB;QAC7B,cAAc,EAAE,YAAY,CAAC;KAC9B;CACF"}
|
package/datepicker/datepicker.js
CHANGED
|
@@ -1,8 +1,190 @@
|
|
|
1
1
|
import { __decorate } from "tslib";
|
|
2
|
-
import {
|
|
3
|
-
import { customElement } from 'lit/decorators.js';
|
|
4
|
-
|
|
2
|
+
import { html, nothing, svg } from 'lit';
|
|
3
|
+
import { customElement, property, query } from 'lit/decorators.js';
|
|
4
|
+
import { live } from 'lit/directives/live.js';
|
|
5
|
+
import { UmNativeTextFieldWrapper } from '../shared/char-count-text-field/native-text-field-wrapper.js';
|
|
6
|
+
import { UmTextFieldBase } from '../shared/text-field-base/text-field-base.js';
|
|
7
|
+
import { styles as textFieldStyles } from '../text-field/text-field.styles.js';
|
|
8
|
+
import { styles } from './datepicker.styles.js';
|
|
9
|
+
import { formatIsoDate } from './format.js';
|
|
10
|
+
import '../calendar/calendar.js';
|
|
11
|
+
import '../menu/menu.js';
|
|
12
|
+
const ISO_DATE = /^\d{4}-\d{2}-\d{2}$/;
|
|
13
|
+
let UmDatepicker = class UmDatepicker extends UmNativeTextFieldWrapper {
|
|
14
|
+
constructor() {
|
|
15
|
+
super(...arguments);
|
|
16
|
+
/**
|
|
17
|
+
* The BCP 47 locale tag forwarded to the underlying calendar and used for
|
|
18
|
+
* non-editable display formatting.
|
|
19
|
+
* When `null`, the calendar falls back to the browser's `navigator.language`.
|
|
20
|
+
*/
|
|
21
|
+
this.locale = null;
|
|
22
|
+
/**
|
|
23
|
+
* Format used when displaying the value while the field is not editable.
|
|
24
|
+
* Accepts the named presets `'short'`, `'medium'`, `'long'`, `'full'`,
|
|
25
|
+
* the literal `'iso'` (keeps the ISO `YYYY-MM-DD` value), or an
|
|
26
|
+
* `Intl.DateTimeFormatOptions` object for custom formatting.
|
|
27
|
+
* In editable mode the input uses the browser's native `type="date"` mask
|
|
28
|
+
* and ignores this property.
|
|
29
|
+
*/
|
|
30
|
+
this.format = 'short';
|
|
31
|
+
/**
|
|
32
|
+
* Whether the input accepts manually-typed dates. When `false` (default),
|
|
33
|
+
* the field is read-only and clicking anywhere opens the calendar popover.
|
|
34
|
+
* When `true`, the input uses native `type="date"` and accepts keyboard input;
|
|
35
|
+
* the calendar popover is opened via the trailing icon.
|
|
36
|
+
*/
|
|
37
|
+
this.editable = false;
|
|
38
|
+
/**
|
|
39
|
+
* Whether the input is read-only. When set, manual typing is disabled even
|
|
40
|
+
* if `editable` is `true`; the calendar popover remains available.
|
|
41
|
+
*/
|
|
42
|
+
this.readOnly = false;
|
|
43
|
+
/**
|
|
44
|
+
* The positioning strategy used by the calendar popover. Use `'fixed'`
|
|
45
|
+
* when the datepicker is rendered inside a clipped/scrollable container.
|
|
46
|
+
*/
|
|
47
|
+
this.menuPositioning = 'relative';
|
|
48
|
+
this.#handleKeyDown = (e) => {
|
|
49
|
+
if (e.key === 'ArrowDown' && !this._menu.open) {
|
|
50
|
+
e.preventDefault();
|
|
51
|
+
this._menu.show();
|
|
52
|
+
return;
|
|
53
|
+
}
|
|
54
|
+
if (e.key === 'Escape' && this._menu.open) {
|
|
55
|
+
e.preventDefault();
|
|
56
|
+
this._menu.close();
|
|
57
|
+
return;
|
|
58
|
+
}
|
|
59
|
+
this._handleKeyDown(e);
|
|
60
|
+
};
|
|
61
|
+
this.#handleCalendarInput = (e) => {
|
|
62
|
+
e.stopPropagation();
|
|
63
|
+
const value = e.target.value;
|
|
64
|
+
this.value = value;
|
|
65
|
+
this.dispatchEvent(new InputEvent('input', { bubbles: true, composed: true }));
|
|
66
|
+
this.dispatchEvent(new Event('change', { bubbles: true }));
|
|
67
|
+
this._menu.close();
|
|
68
|
+
};
|
|
69
|
+
this.#stopPropagation = (e) => {
|
|
70
|
+
e.stopPropagation();
|
|
71
|
+
};
|
|
72
|
+
this.#toggleMenu = () => {
|
|
73
|
+
if (this.disabled) {
|
|
74
|
+
return;
|
|
75
|
+
}
|
|
76
|
+
this._menu.toggle();
|
|
77
|
+
};
|
|
78
|
+
}
|
|
79
|
+
static { this.styles = [UmTextFieldBase.styles, textFieldStyles, styles]; }
|
|
80
|
+
renderControl() {
|
|
81
|
+
const displayValue = this.editable
|
|
82
|
+
? this._value
|
|
83
|
+
: formatIsoDate(this._value, this.format, this.locale);
|
|
84
|
+
return html `
|
|
85
|
+
${this.editable
|
|
86
|
+
? nothing
|
|
87
|
+
: html `
|
|
88
|
+
<button
|
|
89
|
+
class="trigger"
|
|
90
|
+
type="button"
|
|
91
|
+
aria-haspopup="dialog"
|
|
92
|
+
?disabled=${this.disabled}
|
|
93
|
+
@click=${this.#toggleMenu}></button>
|
|
94
|
+
`}
|
|
95
|
+
<div class="input">
|
|
96
|
+
<input
|
|
97
|
+
type=${this.editable ? 'date' : 'text'}
|
|
98
|
+
part="input"
|
|
99
|
+
id=${this.id || nothing}
|
|
100
|
+
aria-labelledby="label"
|
|
101
|
+
aria-describedby="supporting-text"
|
|
102
|
+
aria-haspopup="dialog"
|
|
103
|
+
tabindex=${this.editable ? nothing : -1}
|
|
104
|
+
?readonly=${this.readOnly || !this.editable}
|
|
105
|
+
?disabled=${this.disabled}
|
|
106
|
+
placeholder=${this.placeholder ?? nothing}
|
|
107
|
+
.value=${live(displayValue)}
|
|
108
|
+
@input=${this._handleInput}
|
|
109
|
+
@keydown=${this.#handleKeyDown} />
|
|
110
|
+
</div>
|
|
111
|
+
`;
|
|
112
|
+
}
|
|
113
|
+
renderDefaultTrailingIcon() {
|
|
114
|
+
return svg `
|
|
115
|
+
<svg xmlns="http://www.w3.org/2000/svg" height="1.25em" viewBox="0 -960 960 960" width="1.25em" fill="currentColor">
|
|
116
|
+
<path d="M200-80q-33 0-56.5-23.5T120-160v-560q0-33 23.5-56.5T200-800h40v-80h80v80h320v-80h80v80h40q33 0 56.5 23.5T840-720v560q0 33-23.5 56.5T760-80H200Zm0-80h560v-400H200v400Zm0-480h560v-80H200v80Zm0 0v-80 80Z"/>
|
|
117
|
+
</svg>`;
|
|
118
|
+
}
|
|
119
|
+
renderAfterContent() {
|
|
120
|
+
return html `
|
|
121
|
+
<u-menu
|
|
122
|
+
positioning=${this.menuPositioning}
|
|
123
|
+
autoclose="outside"
|
|
124
|
+
anchor-corner="end-start"
|
|
125
|
+
direction="down-start"
|
|
126
|
+
allow-overflow
|
|
127
|
+
manualFocus
|
|
128
|
+
@click=${this.#stopPropagation}>
|
|
129
|
+
<u-calendar
|
|
130
|
+
.value=${this._value}
|
|
131
|
+
.locale=${this.locale}
|
|
132
|
+
@input=${this.#handleCalendarInput}></u-calendar>
|
|
133
|
+
</u-menu>
|
|
134
|
+
`;
|
|
135
|
+
}
|
|
136
|
+
connectedCallback() {
|
|
137
|
+
super.connectedCallback();
|
|
138
|
+
void this.#attach();
|
|
139
|
+
}
|
|
140
|
+
disconnectedCallback() {
|
|
141
|
+
super.disconnectedCallback();
|
|
142
|
+
this._trailingSlot?.removeEventListener('click', this.#toggleMenu);
|
|
143
|
+
}
|
|
144
|
+
_handleInput() {
|
|
145
|
+
super._handleInput();
|
|
146
|
+
if (ISO_DATE.test(this._value)) {
|
|
147
|
+
this._calendar.value = this._value;
|
|
148
|
+
}
|
|
149
|
+
this.dispatchEvent(new InputEvent('input', { bubbles: true, composed: true }));
|
|
150
|
+
}
|
|
151
|
+
#handleKeyDown;
|
|
152
|
+
#handleCalendarInput;
|
|
153
|
+
#stopPropagation;
|
|
154
|
+
#toggleMenu;
|
|
155
|
+
async #attach() {
|
|
156
|
+
await this.updateComplete;
|
|
157
|
+
this._menu.anchorElement = this._container;
|
|
158
|
+
this._trailingSlot.addEventListener('click', this.#toggleMenu);
|
|
159
|
+
}
|
|
5
160
|
};
|
|
161
|
+
__decorate([
|
|
162
|
+
property()
|
|
163
|
+
], UmDatepicker.prototype, "locale", void 0);
|
|
164
|
+
__decorate([
|
|
165
|
+
property()
|
|
166
|
+
], UmDatepicker.prototype, "format", void 0);
|
|
167
|
+
__decorate([
|
|
168
|
+
property({ type: Boolean, reflect: true })
|
|
169
|
+
], UmDatepicker.prototype, "editable", void 0);
|
|
170
|
+
__decorate([
|
|
171
|
+
property({ type: Boolean, reflect: true })
|
|
172
|
+
], UmDatepicker.prototype, "readOnly", void 0);
|
|
173
|
+
__decorate([
|
|
174
|
+
property({ reflect: true, attribute: 'menu-positioning' })
|
|
175
|
+
], UmDatepicker.prototype, "menuPositioning", void 0);
|
|
176
|
+
__decorate([
|
|
177
|
+
query('input')
|
|
178
|
+
], UmDatepicker.prototype, "input", void 0);
|
|
179
|
+
__decorate([
|
|
180
|
+
query('u-menu', true)
|
|
181
|
+
], UmDatepicker.prototype, "_menu", void 0);
|
|
182
|
+
__decorate([
|
|
183
|
+
query('u-calendar', true)
|
|
184
|
+
], UmDatepicker.prototype, "_calendar", void 0);
|
|
185
|
+
__decorate([
|
|
186
|
+
query('.trailing-icon', true)
|
|
187
|
+
], UmDatepicker.prototype, "_trailingSlot", void 0);
|
|
6
188
|
UmDatepicker = __decorate([
|
|
7
189
|
customElement('u-datepicker')
|
|
8
190
|
], UmDatepicker);
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"datepicker.js","sourceRoot":"","sources":["../../src/datepicker/datepicker.ts"],"names":[],"mappings":";AAAA,OAAO,EAAE,UAAU,EAAE,MAAM,KAAK,CAAC;AACjC,OAAO,EAAE,aAAa,EAAE,MAAM,mBAAmB,CAAC;AAG3C,IAAM,YAAY,GAAlB,MAAM,YAAa,SAAQ,UAAU;CAE3C,CAAA;AAFY,YAAY;IADxB,aAAa,CAAC,cAAc,CAAC;GACjB,YAAY,CAExB","sourcesContent":["import { LitElement } from 'lit';\nimport { customElement } from 'lit/decorators.js';\n\n@customElement('u-datepicker')\nexport class UmDatepicker extends LitElement {\n\n}\n\ndeclare global {\n interface HTMLElementTagNameMap {\n 'u-datepicker': UmDatepicker;\n }\n}\n"]}
|
|
1
|
+
{"version":3,"file":"datepicker.js","sourceRoot":"","sources":["../../src/datepicker/datepicker.ts"],"names":[],"mappings":"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","sourcesContent":["import { CSSResultGroup } from '@lit/reactive-element/css-tag';\n\nimport { html, HTMLTemplateResult, nothing, svg } from 'lit';\nimport { customElement, property, query } from 'lit/decorators.js';\nimport { live } from 'lit/directives/live.js';\n\nimport { UmCalendar } from '../calendar/calendar.js';\nimport { UmMenu } from '../menu/menu.js';\nimport { UmNativeTextFieldWrapper } from '../shared/char-count-text-field/native-text-field-wrapper.js';\nimport { UmTextFieldBase } from '../shared/text-field-base/text-field-base.js';\n\nimport { styles as textFieldStyles } from '../text-field/text-field.styles.js';\nimport { styles } from './datepicker.styles.js';\nimport { DatepickerFormat, formatIsoDate } from './format.js';\n\nimport '../calendar/calendar.js';\nimport '../menu/menu.js';\n\nconst ISO_DATE = /^\\d{4}-\\d{2}-\\d{2}$/;\n\n@customElement('u-datepicker')\nexport class UmDatepicker extends UmNativeTextFieldWrapper {\n static override styles: CSSResultGroup = [UmTextFieldBase.styles, textFieldStyles, styles];\n\n /**\n * The BCP 47 locale tag forwarded to the underlying calendar and used for\n * non-editable display formatting.\n * When `null`, the calendar falls back to the browser's `navigator.language`.\n */\n @property() locale: string | null = null;\n\n /**\n * Format used when displaying the value while the field is not editable.\n * Accepts the named presets `'short'`, `'medium'`, `'long'`, `'full'`,\n * the literal `'iso'` (keeps the ISO `YYYY-MM-DD` value), or an\n * `Intl.DateTimeFormatOptions` object for custom formatting.\n * In editable mode the input uses the browser's native `type=\"date\"` mask\n * and ignores this property.\n */\n @property() format: DatepickerFormat = 'short';\n\n /**\n * Whether the input accepts manually-typed dates. When `false` (default),\n * the field is read-only and clicking anywhere opens the calendar popover.\n * When `true`, the input uses native `type=\"date\"` and accepts keyboard input;\n * the calendar popover is opened via the trailing icon.\n */\n @property({ type: Boolean, reflect: true }) editable = false;\n\n /**\n * Whether the input is read-only. When set, manual typing is disabled even\n * if `editable` is `true`; the calendar popover remains available.\n */\n @property({ type: Boolean, reflect: true }) readOnly = false;\n\n /**\n * The positioning strategy used by the calendar popover. Use `'fixed'`\n * when the datepicker is rendered inside a clipped/scrollable container.\n */\n @property({ reflect: true, attribute: 'menu-positioning' }) menuPositioning: 'relative' | 'fixed' = 'relative';\n\n @query('input') input!: HTMLInputElement;\n @query('u-menu', true) private _menu!: UmMenu;\n @query('u-calendar', true) private _calendar!: UmCalendar;\n @query('.trailing-icon', true) private _trailingSlot!: HTMLSlotElement;\n\n protected override renderControl(): HTMLTemplateResult {\n const displayValue = this.editable\n ? this._value\n : formatIsoDate(this._value, this.format, this.locale);\n\n return html`\n ${this.editable\n ? nothing\n : html`\n <button\n class=\"trigger\"\n type=\"button\"\n aria-haspopup=\"dialog\"\n ?disabled=${this.disabled}\n @click=${this.#toggleMenu}></button>\n `}\n <div class=\"input\">\n <input\n type=${this.editable ? 'date' : 'text'}\n part=\"input\"\n id=${this.id || nothing}\n aria-labelledby=\"label\"\n aria-describedby=\"supporting-text\"\n aria-haspopup=\"dialog\"\n tabindex=${this.editable ? nothing : -1}\n ?readonly=${this.readOnly || !this.editable}\n ?disabled=${this.disabled}\n placeholder=${this.placeholder ?? nothing}\n .value=${live(displayValue)}\n @input=${this._handleInput}\n @keydown=${this.#handleKeyDown} />\n </div>\n `;\n }\n\n protected override renderDefaultTrailingIcon() {\n return svg`\n <svg xmlns=\"http://www.w3.org/2000/svg\" height=\"1.25em\" viewBox=\"0 -960 960 960\" width=\"1.25em\" fill=\"currentColor\">\n <path d=\"M200-80q-33 0-56.5-23.5T120-160v-560q0-33 23.5-56.5T200-800h40v-80h80v80h320v-80h80v80h40q33 0 56.5 23.5T840-720v560q0 33-23.5 56.5T760-80H200Zm0-80h560v-400H200v400Zm0-480h560v-80H200v80Zm0 0v-80 80Z\"/>\n </svg>`;\n }\n\n protected override renderAfterContent() {\n return html`\n <u-menu\n positioning=${this.menuPositioning}\n autoclose=\"outside\"\n anchor-corner=\"end-start\"\n direction=\"down-start\"\n allow-overflow\n manualFocus\n @click=${this.#stopPropagation}>\n <u-calendar\n .value=${this._value}\n .locale=${this.locale}\n @input=${this.#handleCalendarInput}></u-calendar>\n </u-menu>\n `;\n }\n\n override connectedCallback(): void {\n super.connectedCallback();\n void this.#attach();\n }\n\n override disconnectedCallback(): void {\n super.disconnectedCallback();\n this._trailingSlot?.removeEventListener('click', this.#toggleMenu);\n }\n\n protected override _handleInput(): void {\n super._handleInput();\n\n if (ISO_DATE.test(this._value)) {\n this._calendar.value = this._value;\n }\n\n this.dispatchEvent(new InputEvent('input', { bubbles: true, composed: true }));\n }\n\n #handleKeyDown = (e: KeyboardEvent): void => {\n if (e.key === 'ArrowDown' && !this._menu.open) {\n e.preventDefault();\n this._menu.show();\n return;\n }\n\n if (e.key === 'Escape' && this._menu.open) {\n e.preventDefault();\n this._menu.close();\n return;\n }\n\n this._handleKeyDown(e);\n };\n\n #handleCalendarInput = (e: Event): void => {\n e.stopPropagation();\n const value = (e.target as UmCalendar).value;\n this.value = value;\n this.dispatchEvent(new InputEvent('input', { bubbles: true, composed: true }));\n this.dispatchEvent(new Event('change', { bubbles: true }));\n this._menu.close();\n };\n\n #stopPropagation = (e: Event): void => {\n e.stopPropagation();\n };\n\n #toggleMenu = (): void => {\n if (this.disabled) {\n return;\n }\n this._menu.toggle();\n };\n\n async #attach(): Promise<void> {\n await this.updateComplete;\n this._menu.anchorElement = this._container;\n this._trailingSlot.addEventListener('click', this.#toggleMenu);\n }\n}\n\ndeclare global {\n interface HTMLElementTagNameMap {\n 'u-datepicker': UmDatepicker;\n }\n}\n"]}
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
export type DatepickerFormat = 'short' | 'medium' | 'long' | 'full' | 'iso' | Intl.DateTimeFormatOptions;
|
|
2
|
+
/**
|
|
3
|
+
* Parses an ISO `YYYY-MM-DD` string into a `Date` at local midnight,
|
|
4
|
+
* sidestepping the UTC-vs-local parsing ambiguity of the `Date` constructor
|
|
5
|
+
* when given a string.
|
|
6
|
+
*/
|
|
7
|
+
export declare function parseIsoDate(iso: string): Date | null;
|
|
8
|
+
/**
|
|
9
|
+
* Formats an ISO date string (`YYYY-MM-DD`) for display, following the
|
|
10
|
+
* datepicker `format` property. Non-ISO inputs are passed through
|
|
11
|
+
* unchanged so partially-typed values aren't mangled.
|
|
12
|
+
*/
|
|
13
|
+
export declare function formatIsoDate(value: string, format: DatepickerFormat, locale: string | null): string;
|
|
14
|
+
/**
|
|
15
|
+
* Formats a range value (`YYYY-MM-DD - YYYY-MM-DD`) by formatting each end
|
|
16
|
+
* with `formatIsoDate` and rejoining them with the same separator.
|
|
17
|
+
*/
|
|
18
|
+
export declare function formatIsoDateRange(value: string, format: DatepickerFormat, locale: string | null): string;
|
|
19
|
+
//# sourceMappingURL=format.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"format.d.ts","sourceRoot":"","sources":["../../src/datepicker/format.ts"],"names":[],"mappings":"AAAA,MAAM,MAAM,gBAAgB,GACxB,OAAO,GACP,QAAQ,GACR,MAAM,GACN,MAAM,GACN,KAAK,GACL,IAAI,CAAC,qBAAqB,CAAC;AAI/B;;;;GAIG;AACH,wBAAgB,YAAY,CAAC,GAAG,EAAE,MAAM,GAAG,IAAI,GAAG,IAAI,CAOrD;AAED;;;;GAIG;AACH,wBAAgB,aAAa,CAC3B,KAAK,EAAE,MAAM,EACb,MAAM,EAAE,gBAAgB,EACxB,MAAM,EAAE,MAAM,GAAG,IAAI,GACpB,MAAM,CAgBR;AAED;;;GAGG;AACH,wBAAgB,kBAAkB,CAChC,KAAK,EAAE,MAAM,EACb,MAAM,EAAE,gBAAgB,EACxB,MAAM,EAAE,MAAM,GAAG,IAAI,GACpB,MAAM,CAYR"}
|
|
@@ -0,0 +1,47 @@
|
|
|
1
|
+
const ISO_DATE = /^\d{4}-\d{2}-\d{2}$/;
|
|
2
|
+
/**
|
|
3
|
+
* Parses an ISO `YYYY-MM-DD` string into a `Date` at local midnight,
|
|
4
|
+
* sidestepping the UTC-vs-local parsing ambiguity of the `Date` constructor
|
|
5
|
+
* when given a string.
|
|
6
|
+
*/
|
|
7
|
+
export function parseIsoDate(iso) {
|
|
8
|
+
if (!ISO_DATE.test(iso)) {
|
|
9
|
+
return null;
|
|
10
|
+
}
|
|
11
|
+
const [year, month, day] = iso.split('-').map(Number);
|
|
12
|
+
return new Date(year, month - 1, day);
|
|
13
|
+
}
|
|
14
|
+
/**
|
|
15
|
+
* Formats an ISO date string (`YYYY-MM-DD`) for display, following the
|
|
16
|
+
* datepicker `format` property. Non-ISO inputs are passed through
|
|
17
|
+
* unchanged so partially-typed values aren't mangled.
|
|
18
|
+
*/
|
|
19
|
+
export function formatIsoDate(value, format, locale) {
|
|
20
|
+
if (!value || format === 'iso') {
|
|
21
|
+
return value;
|
|
22
|
+
}
|
|
23
|
+
const date = parseIsoDate(value);
|
|
24
|
+
if (!date) {
|
|
25
|
+
return value;
|
|
26
|
+
}
|
|
27
|
+
const options = typeof format === 'string'
|
|
28
|
+
? { dateStyle: format }
|
|
29
|
+
: format;
|
|
30
|
+
return new Intl.DateTimeFormat(locale ?? undefined, options).format(date);
|
|
31
|
+
}
|
|
32
|
+
/**
|
|
33
|
+
* Formats a range value (`YYYY-MM-DD - YYYY-MM-DD`) by formatting each end
|
|
34
|
+
* with `formatIsoDate` and rejoining them with the same separator.
|
|
35
|
+
*/
|
|
36
|
+
export function formatIsoDateRange(value, format, locale) {
|
|
37
|
+
if (!value || format === 'iso') {
|
|
38
|
+
return value;
|
|
39
|
+
}
|
|
40
|
+
const parts = value.split(' - ');
|
|
41
|
+
if (parts.length !== 2) {
|
|
42
|
+
return value;
|
|
43
|
+
}
|
|
44
|
+
const [start, end] = parts;
|
|
45
|
+
return `${formatIsoDate(start, format, locale)} - ${formatIsoDate(end, format, locale)}`;
|
|
46
|
+
}
|
|
47
|
+
//# sourceMappingURL=format.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"format.js","sourceRoot":"","sources":["../../src/datepicker/format.ts"],"names":[],"mappings":"AAQA,MAAM,QAAQ,GAAG,qBAAqB,CAAC;AAEvC;;;;GAIG;AACH,MAAM,UAAU,YAAY,CAAC,GAAW;IACtC,IAAI,CAAC,QAAQ,CAAC,IAAI,CAAC,GAAG,CAAC,EAAE,CAAC;QACxB,OAAO,IAAI,CAAC;IACd,CAAC;IAED,MAAM,CAAC,IAAI,EAAE,KAAK,EAAE,GAAG,CAAC,GAAG,GAAG,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC,GAAG,CAAC,MAAM,CAAC,CAAC;IACtD,OAAO,IAAI,IAAI,CAAC,IAAI,EAAE,KAAK,GAAG,CAAC,EAAE,GAAG,CAAC,CAAC;AACxC,CAAC;AAED;;;;GAIG;AACH,MAAM,UAAU,aAAa,CAC3B,KAAa,EACb,MAAwB,EACxB,MAAqB;IAErB,IAAI,CAAC,KAAK,IAAI,MAAM,KAAK,KAAK,EAAE,CAAC;QAC/B,OAAO,KAAK,CAAC;IACf,CAAC;IAED,MAAM,IAAI,GAAG,YAAY,CAAC,KAAK,CAAC,CAAC;IACjC,IAAI,CAAC,IAAI,EAAE,CAAC;QACV,OAAO,KAAK,CAAC;IACf,CAAC;IAED,MAAM,OAAO,GACX,OAAO,MAAM,KAAK,QAAQ;QACxB,CAAC,CAAC,EAAE,SAAS,EAAE,MAAM,EAAE;QACvB,CAAC,CAAC,MAAM,CAAC;IAEb,OAAO,IAAI,IAAI,CAAC,cAAc,CAAC,MAAM,IAAI,SAAS,EAAE,OAAO,CAAC,CAAC,MAAM,CAAC,IAAI,CAAC,CAAC;AAC5E,CAAC;AAED;;;GAGG;AACH,MAAM,UAAU,kBAAkB,CAChC,KAAa,EACb,MAAwB,EACxB,MAAqB;IAErB,IAAI,CAAC,KAAK,IAAI,MAAM,KAAK,KAAK,EAAE,CAAC;QAC/B,OAAO,KAAK,CAAC;IACf,CAAC;IAED,MAAM,KAAK,GAAG,KAAK,CAAC,KAAK,CAAC,KAAK,CAAC,CAAC;IACjC,IAAI,KAAK,CAAC,MAAM,KAAK,CAAC,EAAE,CAAC;QACvB,OAAO,KAAK,CAAC;IACf,CAAC;IAED,MAAM,CAAC,KAAK,EAAE,GAAG,CAAC,GAAG,KAAK,CAAC;IAC3B,OAAO,GAAG,aAAa,CAAC,KAAK,EAAE,MAAM,EAAE,MAAM,CAAC,MAAM,aAAa,CAAC,GAAG,EAAE,MAAM,EAAE,MAAM,CAAC,EAAE,CAAC;AAC3F,CAAC","sourcesContent":["export type DatepickerFormat =\n | 'short'\n | 'medium'\n | 'long'\n | 'full'\n | 'iso'\n | Intl.DateTimeFormatOptions;\n\nconst ISO_DATE = /^\\d{4}-\\d{2}-\\d{2}$/;\n\n/**\n * Parses an ISO `YYYY-MM-DD` string into a `Date` at local midnight,\n * sidestepping the UTC-vs-local parsing ambiguity of the `Date` constructor\n * when given a string.\n */\nexport function parseIsoDate(iso: string): Date | null {\n if (!ISO_DATE.test(iso)) {\n return null;\n }\n\n const [year, month, day] = iso.split('-').map(Number);\n return new Date(year, month - 1, day);\n}\n\n/**\n * Formats an ISO date string (`YYYY-MM-DD`) for display, following the\n * datepicker `format` property. Non-ISO inputs are passed through\n * unchanged so partially-typed values aren't mangled.\n */\nexport function formatIsoDate(\n value: string,\n format: DatepickerFormat,\n locale: string | null,\n): string {\n if (!value || format === 'iso') {\n return value;\n }\n\n const date = parseIsoDate(value);\n if (!date) {\n return value;\n }\n\n const options: Intl.DateTimeFormatOptions =\n typeof format === 'string'\n ? { dateStyle: format }\n : format;\n\n return new Intl.DateTimeFormat(locale ?? undefined, options).format(date);\n}\n\n/**\n * Formats a range value (`YYYY-MM-DD - YYYY-MM-DD`) by formatting each end\n * with `formatIsoDate` and rejoining them with the same separator.\n */\nexport function formatIsoDateRange(\n value: string,\n format: DatepickerFormat,\n locale: string | null,\n): string {\n if (!value || format === 'iso') {\n return value;\n }\n\n const parts = value.split(' - ');\n if (parts.length !== 2) {\n return value;\n }\n\n const [start, end] = parts;\n return `${formatIsoDate(start, format, locale)} - ${formatIsoDate(end, format, locale)}`;\n}\n"]}
|
|
@@ -0,0 +1,56 @@
|
|
|
1
|
+
import { CSSResultGroup } from '@lit/reactive-element/css-tag';
|
|
2
|
+
import { HTMLTemplateResult } from 'lit';
|
|
3
|
+
import { UmNativeTextFieldWrapper } from '../shared/char-count-text-field/native-text-field-wrapper.js';
|
|
4
|
+
import { DatepickerFormat } from './format.js';
|
|
5
|
+
import '../calendar/range-calendar.js';
|
|
6
|
+
import '../menu/menu.js';
|
|
7
|
+
export declare class UmRangeDatepicker extends UmNativeTextFieldWrapper {
|
|
8
|
+
#private;
|
|
9
|
+
static styles: CSSResultGroup;
|
|
10
|
+
/**
|
|
11
|
+
* The BCP 47 locale tag forwarded to the underlying range calendar and used
|
|
12
|
+
* for non-editable display formatting.
|
|
13
|
+
* When `null`, the calendar falls back to the browser's `navigator.language`.
|
|
14
|
+
*/
|
|
15
|
+
locale: string | null;
|
|
16
|
+
/**
|
|
17
|
+
* Format used when displaying the value while the field is not editable.
|
|
18
|
+
* Accepts `'short'`, `'medium'`, `'long'`, `'full'`, `'iso'`, or an
|
|
19
|
+
* `Intl.DateTimeFormatOptions` object. Each end of the range is formatted
|
|
20
|
+
* independently and joined with ` - `.
|
|
21
|
+
*/
|
|
22
|
+
format: DatepickerFormat;
|
|
23
|
+
/**
|
|
24
|
+
* Whether the input accepts manually-typed ranges. When `false` (default),
|
|
25
|
+
* the field is read-only and clicking anywhere opens the calendar popover.
|
|
26
|
+
* When `true`, the input accepts text in the `YYYY-MM-DD - YYYY-MM-DD` format;
|
|
27
|
+
* the calendar popover is opened via the trailing icon.
|
|
28
|
+
*/
|
|
29
|
+
editable: boolean;
|
|
30
|
+
/**
|
|
31
|
+
* Whether the input is read-only. When set, manual typing is disabled even
|
|
32
|
+
* if `editable` is `true`; the calendar popover remains available.
|
|
33
|
+
*/
|
|
34
|
+
readOnly: boolean;
|
|
35
|
+
/**
|
|
36
|
+
* The positioning strategy used by the calendar popover. Use `'fixed'`
|
|
37
|
+
* when the datepicker is rendered inside a clipped/scrollable container.
|
|
38
|
+
*/
|
|
39
|
+
menuPositioning: 'relative' | 'fixed';
|
|
40
|
+
input: HTMLInputElement;
|
|
41
|
+
private _menu;
|
|
42
|
+
private _calendar;
|
|
43
|
+
private _trailingSlot;
|
|
44
|
+
protected renderControl(): HTMLTemplateResult;
|
|
45
|
+
protected renderDefaultTrailingIcon(): import("lit-html").TemplateResult<2>;
|
|
46
|
+
protected renderAfterContent(): import("lit-html").TemplateResult<1>;
|
|
47
|
+
connectedCallback(): void;
|
|
48
|
+
disconnectedCallback(): void;
|
|
49
|
+
protected _handleInput(): void;
|
|
50
|
+
}
|
|
51
|
+
declare global {
|
|
52
|
+
interface HTMLElementTagNameMap {
|
|
53
|
+
'u-range-datepicker': UmRangeDatepicker;
|
|
54
|
+
}
|
|
55
|
+
}
|
|
56
|
+
//# sourceMappingURL=range-datepicker.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"range-datepicker.d.ts","sourceRoot":"","sources":["../../src/datepicker/range-datepicker.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,cAAc,EAAE,MAAM,+BAA+B,CAAC;AAE/D,OAAO,EAAQ,kBAAkB,EAAgB,MAAM,KAAK,CAAC;AAM7D,OAAO,EAAE,wBAAwB,EAAE,MAAM,8DAA8D,CAAC;AAKxG,OAAO,EAAE,gBAAgB,EAAsB,MAAM,aAAa,CAAC;AAEnE,OAAO,+BAA+B,CAAC;AACvC,OAAO,iBAAiB,CAAC;AAIzB,qBACa,iBAAkB,SAAQ,wBAAwB;;IAC7D,OAAgB,MAAM,EAAE,cAAc,CAAqD;IAE3F;;;;OAIG;IACS,MAAM,EAAE,MAAM,GAAG,IAAI,CAAQ;IAEzC;;;;;OAKG;IACS,MAAM,EAAE,gBAAgB,CAAW;IAE/C;;;;;OAKG;IACyC,QAAQ,UAAS;IAE7D;;;OAGG;IACyC,QAAQ,UAAS;IAE7D;;;OAGG;IACyD,eAAe,EAAE,UAAU,GAAG,OAAO,CAAc;IAE/F,KAAK,EAAG,gBAAgB,CAAC;IAClB,OAAO,CAAC,KAAK,CAAU;IACb,OAAO,CAAC,SAAS,CAAmB;IACtC,OAAO,CAAC,aAAa,CAAmB;cAEpD,aAAa,IAAI,kBAAkB;cAmCnC,yBAAyB;cAOzB,kBAAkB;IAmB5B,iBAAiB,IAAI,IAAI;IAKzB,oBAAoB,IAAI,IAAI;cAKlB,YAAY,IAAI,IAAI;CA4DxC;AAED,OAAO,CAAC,MAAM,CAAC;IACb,UAAU,qBAAqB;QAC7B,oBAAoB,EAAE,iBAAiB,CAAC;KACzC;CACF"}
|
|
@@ -0,0 +1,198 @@
|
|
|
1
|
+
import { __decorate } from "tslib";
|
|
2
|
+
import { html, nothing, svg } from 'lit';
|
|
3
|
+
import { customElement, property, query } from 'lit/decorators.js';
|
|
4
|
+
import { live } from 'lit/directives/live.js';
|
|
5
|
+
import { UmNativeTextFieldWrapper } from '../shared/char-count-text-field/native-text-field-wrapper.js';
|
|
6
|
+
import { UmTextFieldBase } from '../shared/text-field-base/text-field-base.js';
|
|
7
|
+
import { styles as textFieldStyles } from '../text-field/text-field.styles.js';
|
|
8
|
+
import { styles } from './datepicker.styles.js';
|
|
9
|
+
import { formatIsoDateRange } from './format.js';
|
|
10
|
+
import '../calendar/range-calendar.js';
|
|
11
|
+
import '../menu/menu.js';
|
|
12
|
+
const ISO_DATE_RANGE = /^\d{4}-\d{2}-\d{2} - \d{4}-\d{2}-\d{2}$/;
|
|
13
|
+
let UmRangeDatepicker = class UmRangeDatepicker extends UmNativeTextFieldWrapper {
|
|
14
|
+
constructor() {
|
|
15
|
+
super(...arguments);
|
|
16
|
+
/**
|
|
17
|
+
* The BCP 47 locale tag forwarded to the underlying range calendar and used
|
|
18
|
+
* for non-editable display formatting.
|
|
19
|
+
* When `null`, the calendar falls back to the browser's `navigator.language`.
|
|
20
|
+
*/
|
|
21
|
+
this.locale = null;
|
|
22
|
+
/**
|
|
23
|
+
* Format used when displaying the value while the field is not editable.
|
|
24
|
+
* Accepts `'short'`, `'medium'`, `'long'`, `'full'`, `'iso'`, or an
|
|
25
|
+
* `Intl.DateTimeFormatOptions` object. Each end of the range is formatted
|
|
26
|
+
* independently and joined with ` - `.
|
|
27
|
+
*/
|
|
28
|
+
this.format = 'short';
|
|
29
|
+
/**
|
|
30
|
+
* Whether the input accepts manually-typed ranges. When `false` (default),
|
|
31
|
+
* the field is read-only and clicking anywhere opens the calendar popover.
|
|
32
|
+
* When `true`, the input accepts text in the `YYYY-MM-DD - YYYY-MM-DD` format;
|
|
33
|
+
* the calendar popover is opened via the trailing icon.
|
|
34
|
+
*/
|
|
35
|
+
this.editable = false;
|
|
36
|
+
/**
|
|
37
|
+
* Whether the input is read-only. When set, manual typing is disabled even
|
|
38
|
+
* if `editable` is `true`; the calendar popover remains available.
|
|
39
|
+
*/
|
|
40
|
+
this.readOnly = false;
|
|
41
|
+
/**
|
|
42
|
+
* The positioning strategy used by the calendar popover. Use `'fixed'`
|
|
43
|
+
* when the datepicker is rendered inside a clipped/scrollable container.
|
|
44
|
+
*/
|
|
45
|
+
this.menuPositioning = 'relative';
|
|
46
|
+
this.#handleKeyDown = (e) => {
|
|
47
|
+
if (e.key === 'ArrowDown' && !this._menu.open) {
|
|
48
|
+
e.preventDefault();
|
|
49
|
+
this._menu.show();
|
|
50
|
+
return;
|
|
51
|
+
}
|
|
52
|
+
if (e.key === 'Escape' && this._menu.open) {
|
|
53
|
+
e.preventDefault();
|
|
54
|
+
this._menu.close();
|
|
55
|
+
return;
|
|
56
|
+
}
|
|
57
|
+
this._handleKeyDown(e);
|
|
58
|
+
};
|
|
59
|
+
this.#handleCalendarInput = (e) => {
|
|
60
|
+
e.stopPropagation();
|
|
61
|
+
const value = e.target.value ?? '';
|
|
62
|
+
this.value = value;
|
|
63
|
+
this.dispatchEvent(new InputEvent('input', { bubbles: true, composed: true }));
|
|
64
|
+
};
|
|
65
|
+
this.#handleCalendarChange = (e) => {
|
|
66
|
+
e.stopPropagation();
|
|
67
|
+
if (!ISO_DATE_RANGE.test(this._value)) {
|
|
68
|
+
return;
|
|
69
|
+
}
|
|
70
|
+
this.dispatchEvent(new Event('change', { bubbles: true }));
|
|
71
|
+
this._menu.close();
|
|
72
|
+
};
|
|
73
|
+
this.#stopPropagation = (e) => {
|
|
74
|
+
e.stopPropagation();
|
|
75
|
+
};
|
|
76
|
+
this.#toggleMenu = () => {
|
|
77
|
+
if (this.disabled) {
|
|
78
|
+
return;
|
|
79
|
+
}
|
|
80
|
+
this._menu.toggle();
|
|
81
|
+
};
|
|
82
|
+
}
|
|
83
|
+
static { this.styles = [UmTextFieldBase.styles, textFieldStyles, styles]; }
|
|
84
|
+
renderControl() {
|
|
85
|
+
const displayValue = this.editable
|
|
86
|
+
? this._value
|
|
87
|
+
: formatIsoDateRange(this._value, this.format, this.locale);
|
|
88
|
+
return html `
|
|
89
|
+
${this.editable
|
|
90
|
+
? nothing
|
|
91
|
+
: html `
|
|
92
|
+
<button
|
|
93
|
+
class="trigger"
|
|
94
|
+
type="button"
|
|
95
|
+
aria-haspopup="dialog"
|
|
96
|
+
?disabled=${this.disabled}
|
|
97
|
+
@click=${this.#toggleMenu}></button>
|
|
98
|
+
`}
|
|
99
|
+
<div class="input">
|
|
100
|
+
<input
|
|
101
|
+
type="text"
|
|
102
|
+
part="input"
|
|
103
|
+
id=${this.id || nothing}
|
|
104
|
+
aria-labelledby="label"
|
|
105
|
+
aria-describedby="supporting-text"
|
|
106
|
+
aria-haspopup="dialog"
|
|
107
|
+
tabindex=${this.editable ? nothing : -1}
|
|
108
|
+
?readonly=${this.readOnly || !this.editable}
|
|
109
|
+
?disabled=${this.disabled}
|
|
110
|
+
placeholder=${this.placeholder ?? nothing}
|
|
111
|
+
.value=${live(displayValue)}
|
|
112
|
+
@input=${this._handleInput}
|
|
113
|
+
@keydown=${this.#handleKeyDown} />
|
|
114
|
+
</div>
|
|
115
|
+
`;
|
|
116
|
+
}
|
|
117
|
+
renderDefaultTrailingIcon() {
|
|
118
|
+
return svg `
|
|
119
|
+
<svg xmlns="http://www.w3.org/2000/svg" height="1.25em" viewBox="0 -960 960 960" width="1.25em" fill="currentColor">
|
|
120
|
+
<path d="M200-80q-33 0-56.5-23.5T120-160v-560q0-33 23.5-56.5T200-800h40v-80h80v80h320v-80h80v80h40q33 0 56.5 23.5T840-720v560q0 33-23.5 56.5T760-80H200Zm0-80h560v-400H200v400Zm0-480h560v-80H200v80Zm0 0v-80 80Z"/>
|
|
121
|
+
</svg>`;
|
|
122
|
+
}
|
|
123
|
+
renderAfterContent() {
|
|
124
|
+
return html `
|
|
125
|
+
<u-menu
|
|
126
|
+
positioning=${this.menuPositioning}
|
|
127
|
+
autoclose="outside"
|
|
128
|
+
anchor-corner="end-start"
|
|
129
|
+
direction="down-start"
|
|
130
|
+
allow-overflow
|
|
131
|
+
manualFocus
|
|
132
|
+
@click=${this.#stopPropagation}>
|
|
133
|
+
<u-range-calendar
|
|
134
|
+
.value=${this._value}
|
|
135
|
+
.locale=${this.locale}
|
|
136
|
+
@input=${this.#handleCalendarInput}
|
|
137
|
+
@change=${this.#handleCalendarChange}></u-range-calendar>
|
|
138
|
+
</u-menu>
|
|
139
|
+
`;
|
|
140
|
+
}
|
|
141
|
+
connectedCallback() {
|
|
142
|
+
super.connectedCallback();
|
|
143
|
+
void this.#attach();
|
|
144
|
+
}
|
|
145
|
+
disconnectedCallback() {
|
|
146
|
+
super.disconnectedCallback();
|
|
147
|
+
this._trailingSlot?.removeEventListener('click', this.#toggleMenu);
|
|
148
|
+
}
|
|
149
|
+
_handleInput() {
|
|
150
|
+
super._handleInput();
|
|
151
|
+
if (ISO_DATE_RANGE.test(this._value)) {
|
|
152
|
+
this._calendar.value = this._value;
|
|
153
|
+
}
|
|
154
|
+
this.dispatchEvent(new InputEvent('input', { bubbles: true, composed: true }));
|
|
155
|
+
}
|
|
156
|
+
#handleKeyDown;
|
|
157
|
+
#handleCalendarInput;
|
|
158
|
+
#handleCalendarChange;
|
|
159
|
+
#stopPropagation;
|
|
160
|
+
#toggleMenu;
|
|
161
|
+
async #attach() {
|
|
162
|
+
await this.updateComplete;
|
|
163
|
+
this._menu.anchorElement = this._container;
|
|
164
|
+
this._trailingSlot.addEventListener('click', this.#toggleMenu);
|
|
165
|
+
}
|
|
166
|
+
};
|
|
167
|
+
__decorate([
|
|
168
|
+
property()
|
|
169
|
+
], UmRangeDatepicker.prototype, "locale", void 0);
|
|
170
|
+
__decorate([
|
|
171
|
+
property()
|
|
172
|
+
], UmRangeDatepicker.prototype, "format", void 0);
|
|
173
|
+
__decorate([
|
|
174
|
+
property({ type: Boolean, reflect: true })
|
|
175
|
+
], UmRangeDatepicker.prototype, "editable", void 0);
|
|
176
|
+
__decorate([
|
|
177
|
+
property({ type: Boolean, reflect: true })
|
|
178
|
+
], UmRangeDatepicker.prototype, "readOnly", void 0);
|
|
179
|
+
__decorate([
|
|
180
|
+
property({ reflect: true, attribute: 'menu-positioning' })
|
|
181
|
+
], UmRangeDatepicker.prototype, "menuPositioning", void 0);
|
|
182
|
+
__decorate([
|
|
183
|
+
query('input')
|
|
184
|
+
], UmRangeDatepicker.prototype, "input", void 0);
|
|
185
|
+
__decorate([
|
|
186
|
+
query('u-menu', true)
|
|
187
|
+
], UmRangeDatepicker.prototype, "_menu", void 0);
|
|
188
|
+
__decorate([
|
|
189
|
+
query('u-range-calendar', true)
|
|
190
|
+
], UmRangeDatepicker.prototype, "_calendar", void 0);
|
|
191
|
+
__decorate([
|
|
192
|
+
query('.trailing-icon', true)
|
|
193
|
+
], UmRangeDatepicker.prototype, "_trailingSlot", void 0);
|
|
194
|
+
UmRangeDatepicker = __decorate([
|
|
195
|
+
customElement('u-range-datepicker')
|
|
196
|
+
], UmRangeDatepicker);
|
|
197
|
+
export { UmRangeDatepicker };
|
|
198
|
+
//# sourceMappingURL=range-datepicker.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"range-datepicker.js","sourceRoot":"","sources":["../../src/datepicker/range-datepicker.ts"],"names":[],"mappings":"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","sourcesContent":["import { CSSResultGroup } from '@lit/reactive-element/css-tag';\n\nimport { html, HTMLTemplateResult, nothing, svg } from 'lit';\nimport { customElement, property, query } from 'lit/decorators.js';\nimport { live } from 'lit/directives/live.js';\n\nimport { UmRangeCalendar } from '../calendar/range-calendar.js';\nimport { UmMenu } from '../menu/menu.js';\nimport { UmNativeTextFieldWrapper } from '../shared/char-count-text-field/native-text-field-wrapper.js';\nimport { UmTextFieldBase } from '../shared/text-field-base/text-field-base.js';\n\nimport { styles as textFieldStyles } from '../text-field/text-field.styles.js';\nimport { styles } from './datepicker.styles.js';\nimport { DatepickerFormat, formatIsoDateRange } from './format.js';\n\nimport '../calendar/range-calendar.js';\nimport '../menu/menu.js';\n\nconst ISO_DATE_RANGE = /^\\d{4}-\\d{2}-\\d{2} - \\d{4}-\\d{2}-\\d{2}$/;\n\n@customElement('u-range-datepicker')\nexport class UmRangeDatepicker extends UmNativeTextFieldWrapper {\n static override styles: CSSResultGroup = [UmTextFieldBase.styles, textFieldStyles, styles];\n\n /**\n * The BCP 47 locale tag forwarded to the underlying range calendar and used\n * for non-editable display formatting.\n * When `null`, the calendar falls back to the browser's `navigator.language`.\n */\n @property() locale: string | null = null;\n\n /**\n * Format used when displaying the value while the field is not editable.\n * Accepts `'short'`, `'medium'`, `'long'`, `'full'`, `'iso'`, or an\n * `Intl.DateTimeFormatOptions` object. Each end of the range is formatted\n * independently and joined with ` - `.\n */\n @property() format: DatepickerFormat = 'short';\n\n /**\n * Whether the input accepts manually-typed ranges. When `false` (default),\n * the field is read-only and clicking anywhere opens the calendar popover.\n * When `true`, the input accepts text in the `YYYY-MM-DD - YYYY-MM-DD` format;\n * the calendar popover is opened via the trailing icon.\n */\n @property({ type: Boolean, reflect: true }) editable = false;\n\n /**\n * Whether the input is read-only. When set, manual typing is disabled even\n * if `editable` is `true`; the calendar popover remains available.\n */\n @property({ type: Boolean, reflect: true }) readOnly = false;\n\n /**\n * The positioning strategy used by the calendar popover. Use `'fixed'`\n * when the datepicker is rendered inside a clipped/scrollable container.\n */\n @property({ reflect: true, attribute: 'menu-positioning' }) menuPositioning: 'relative' | 'fixed' = 'relative';\n\n @query('input') input!: HTMLInputElement;\n @query('u-menu', true) private _menu!: UmMenu;\n @query('u-range-calendar', true) private _calendar!: UmRangeCalendar;\n @query('.trailing-icon', true) private _trailingSlot!: HTMLSlotElement;\n\n protected override renderControl(): HTMLTemplateResult {\n const displayValue = this.editable\n ? this._value\n : formatIsoDateRange(this._value, this.format, this.locale);\n\n return html`\n ${this.editable\n ? nothing\n : html`\n <button\n class=\"trigger\"\n type=\"button\"\n aria-haspopup=\"dialog\"\n ?disabled=${this.disabled}\n @click=${this.#toggleMenu}></button>\n `}\n <div class=\"input\">\n <input\n type=\"text\"\n part=\"input\"\n id=${this.id || nothing}\n aria-labelledby=\"label\"\n aria-describedby=\"supporting-text\"\n aria-haspopup=\"dialog\"\n tabindex=${this.editable ? nothing : -1}\n ?readonly=${this.readOnly || !this.editable}\n ?disabled=${this.disabled}\n placeholder=${this.placeholder ?? nothing}\n .value=${live(displayValue)}\n @input=${this._handleInput}\n @keydown=${this.#handleKeyDown} />\n </div>\n `;\n }\n\n protected override renderDefaultTrailingIcon() {\n return svg`\n <svg xmlns=\"http://www.w3.org/2000/svg\" height=\"1.25em\" viewBox=\"0 -960 960 960\" width=\"1.25em\" fill=\"currentColor\">\n <path d=\"M200-80q-33 0-56.5-23.5T120-160v-560q0-33 23.5-56.5T200-800h40v-80h80v80h320v-80h80v80h40q33 0 56.5 23.5T840-720v560q0 33-23.5 56.5T760-80H200Zm0-80h560v-400H200v400Zm0-480h560v-80H200v80Zm0 0v-80 80Z\"/>\n </svg>`;\n }\n\n protected override renderAfterContent() {\n return html`\n <u-menu\n positioning=${this.menuPositioning}\n autoclose=\"outside\"\n anchor-corner=\"end-start\"\n direction=\"down-start\"\n allow-overflow\n manualFocus\n @click=${this.#stopPropagation}>\n <u-range-calendar\n .value=${this._value}\n .locale=${this.locale}\n @input=${this.#handleCalendarInput}\n @change=${this.#handleCalendarChange}></u-range-calendar>\n </u-menu>\n `;\n }\n\n override connectedCallback(): void {\n super.connectedCallback();\n void this.#attach();\n }\n\n override disconnectedCallback(): void {\n super.disconnectedCallback();\n this._trailingSlot?.removeEventListener('click', this.#toggleMenu);\n }\n\n protected override _handleInput(): void {\n super._handleInput();\n\n if (ISO_DATE_RANGE.test(this._value)) {\n this._calendar.value = this._value;\n }\n\n this.dispatchEvent(new InputEvent('input', { bubbles: true, composed: true }));\n }\n\n #handleKeyDown = (e: KeyboardEvent): void => {\n if (e.key === 'ArrowDown' && !this._menu.open) {\n e.preventDefault();\n this._menu.show();\n return;\n }\n\n if (e.key === 'Escape' && this._menu.open) {\n e.preventDefault();\n this._menu.close();\n return;\n }\n\n this._handleKeyDown(e);\n };\n\n #handleCalendarInput = (e: Event): void => {\n e.stopPropagation();\n const value = (e.target as UmRangeCalendar).value ?? '';\n this.value = value;\n this.dispatchEvent(new InputEvent('input', { bubbles: true, composed: true }));\n };\n\n #handleCalendarChange = (e: Event): void => {\n e.stopPropagation();\n\n if (!ISO_DATE_RANGE.test(this._value)) {\n return;\n }\n\n this.dispatchEvent(new Event('change', { bubbles: true }));\n this._menu.close();\n };\n\n #stopPropagation = (e: Event): void => {\n e.stopPropagation();\n };\n\n #toggleMenu = (): void => {\n if (this.disabled) {\n return;\n }\n this._menu.toggle();\n };\n\n async #attach(): Promise<void> {\n await this.updateComplete;\n this._menu.anchorElement = this._container;\n this._trailingSlot.addEventListener('click', this.#toggleMenu);\n }\n}\n\ndeclare global {\n interface HTMLElementTagNameMap {\n 'u-range-datepicker': UmRangeDatepicker;\n }\n}\n"]}
|