@sekiui/elements 0.0.88 → 0.1.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/dist/cdn/p-CQQRfw1L.js +18 -0
- package/dist/cdn/seki-date-picker.js +71 -36
- package/dist/cdn/seki-drawer.js +76 -32
- package/dist/cdn/seki-hover-card.js +58 -3
- package/dist/cdn/seki-select-content.js +21 -13
- package/dist/cdn/seki-select-group.js +3 -4
- package/dist/cdn/seki-select-option.js +33 -15
- package/dist/cdn/seki-select-trigger.js +6 -4
- package/dist/cdn/seki-sheet.js +71 -30
- package/dist/cdn/seki-tooltip.js +47 -2
- package/dist/cjs/loader.cjs.js +1 -1
- package/dist/cjs/option-id-wIa73qWK.js +20 -0
- package/dist/cjs/seki-date-picker.cjs.entry.js +64 -32
- package/dist/cjs/seki-drawer.cjs.entry.js +67 -27
- package/dist/cjs/seki-hover-card.cjs.entry.js +52 -2
- package/dist/cjs/seki-select-content.cjs.entry.js +20 -11
- package/dist/cjs/seki-select-group.cjs.entry.js +2 -2
- package/dist/cjs/seki-select-option.cjs.entry.js +32 -13
- package/dist/cjs/seki-select-trigger.cjs.entry.js +5 -2
- package/dist/cjs/seki-sheet.cjs.entry.js +62 -25
- package/dist/cjs/seki-tooltip.cjs.entry.js +43 -2
- package/dist/cjs/sekiui.cjs.js +1 -1
- package/dist/collection/components/date-picker/seki-date-picker.js +124 -36
- package/dist/collection/components/drawer/seki-drawer.js +132 -31
- package/dist/collection/components/hover-card/seki-hover-card.js +138 -2
- package/dist/collection/components/select-content/seki-select-content.css +8 -0
- package/dist/collection/components/select-content/seki-select-content.js +20 -11
- package/dist/collection/components/select-group/seki-select-group.js +2 -2
- package/dist/collection/components/select-option/seki-select-option.js +32 -13
- package/dist/collection/components/select-trigger/seki-select-trigger.js +5 -2
- package/dist/collection/components/sheet/seki-sheet.js +127 -29
- package/dist/collection/components/tooltip/seki-tooltip.js +92 -2
- package/dist/collection/utils/select/index.js +1 -0
- package/dist/collection/utils/select/option-id.js +16 -0
- package/dist/components/p-CQQRfw1L.js +18 -0
- package/dist/components/seki-date-picker.js +71 -36
- package/dist/components/seki-drawer.js +76 -32
- package/dist/components/seki-hover-card.js +58 -3
- package/dist/components/seki-select-content.js +21 -13
- package/dist/components/seki-select-group.js +3 -4
- package/dist/components/seki-select-option.js +33 -15
- package/dist/components/seki-select-trigger.js +6 -4
- package/dist/components/seki-sheet.js +71 -30
- package/dist/components/seki-tooltip.js +47 -2
- package/dist/esm/loader.js +1 -1
- package/dist/esm/option-id-CQQRfw1L.js +18 -0
- package/dist/esm/seki-date-picker.entry.js +64 -32
- package/dist/esm/seki-drawer.entry.js +67 -27
- package/dist/esm/seki-hover-card.entry.js +52 -2
- package/dist/esm/seki-select-content.entry.js +20 -11
- package/dist/esm/seki-select-group.entry.js +2 -2
- package/dist/esm/seki-select-option.entry.js +32 -13
- package/dist/esm/seki-select-trigger.entry.js +5 -2
- package/dist/esm/seki-sheet.entry.js +62 -25
- package/dist/esm/seki-tooltip.entry.js +43 -2
- package/dist/esm/sekiui.js +1 -1
- package/dist/sekiui/p-05b33a61.entry.js +1 -0
- package/dist/sekiui/p-1cd6b3e6.entry.js +1 -0
- package/dist/sekiui/p-3de5878b.entry.js +1 -0
- package/dist/sekiui/p-649dbdf0.entry.js +1 -0
- package/dist/sekiui/p-CQQRfw1L.js +1 -0
- package/dist/sekiui/p-a2ae6d1b.entry.js +1 -0
- package/dist/sekiui/p-b82c2267.entry.js +1 -0
- package/dist/sekiui/p-c0f21b6a.entry.js +1 -0
- package/dist/sekiui/p-c3ef507f.entry.js +1 -0
- package/dist/sekiui/p-fe3e661d.entry.js +1 -0
- package/dist/sekiui/sekiui.esm.js +1 -1
- package/dist/types/components/date-picker/seki-date-picker.d.ts +21 -5
- package/dist/types/components/drawer/seki-drawer.d.ts +22 -6
- package/dist/types/components/hover-card/seki-hover-card.d.ts +21 -0
- package/dist/types/components/select-content/seki-select-content.d.ts +8 -5
- package/dist/types/components/select-option/seki-select-option.d.ts +6 -4
- package/dist/types/components/sheet/seki-sheet.d.ts +22 -6
- package/dist/types/components/tooltip/seki-tooltip.d.ts +13 -0
- package/dist/types/components.d.ts +132 -9
- package/dist/types/utils/select/index.d.ts +1 -0
- package/dist/types/utils/select/option-id.d.ts +14 -0
- package/package.json +1 -1
- package/dist/sekiui/p-1866201e.entry.js +0 -1
- package/dist/sekiui/p-2e18933c.entry.js +0 -1
- package/dist/sekiui/p-779764c0.entry.js +0 -1
- package/dist/sekiui/p-786c153b.entry.js +0 -1
- package/dist/sekiui/p-87bcbb66.entry.js +0 -1
- package/dist/sekiui/p-9abfa3a5.entry.js +0 -1
- package/dist/sekiui/p-ac7bd611.entry.js +0 -1
- package/dist/sekiui/p-c62c4ad7.entry.js +0 -1
- package/dist/sekiui/p-e45e6992.entry.js +0 -1
|
@@ -20,66 +20,99 @@ import { syncTheme } from "../../utils/theme-sync";
|
|
|
20
20
|
*/
|
|
21
21
|
export class SekiSheet {
|
|
22
22
|
constructor() {
|
|
23
|
+
/**
|
|
24
|
+
* Controlled open state. Also readable/writable as the `open` attribute, so
|
|
25
|
+
* `<seki-sheet open>` renders open with no script involved.
|
|
26
|
+
*/
|
|
27
|
+
this.open = false;
|
|
28
|
+
/**
|
|
29
|
+
* Initial open state for uncontrolled usage
|
|
30
|
+
*/
|
|
31
|
+
this.defaultOpen = false;
|
|
23
32
|
/**
|
|
24
33
|
* Internal state for sheet open/closed
|
|
25
34
|
*/
|
|
26
|
-
this.
|
|
35
|
+
this._isOpen = false;
|
|
36
|
+
}
|
|
37
|
+
componentWillLoad() {
|
|
38
|
+
this._isOpen = this.open || this.defaultOpen;
|
|
39
|
+
this.open = this._isOpen;
|
|
40
|
+
}
|
|
41
|
+
componentDidLoad() {
|
|
42
|
+
this.updateContext();
|
|
43
|
+
}
|
|
44
|
+
handleOpenPropChange(newValue) {
|
|
45
|
+
// An outside assignment (`sheet.open = true`) has to win after first render;
|
|
46
|
+
// `open` is only read once in componentWillLoad otherwise.
|
|
47
|
+
if (newValue === this._isOpen)
|
|
48
|
+
return;
|
|
49
|
+
if (newValue) {
|
|
50
|
+
this.openSheet();
|
|
51
|
+
}
|
|
52
|
+
else {
|
|
53
|
+
this.closeSheet();
|
|
54
|
+
}
|
|
27
55
|
}
|
|
28
56
|
/**
|
|
29
57
|
* Opens the sheet
|
|
30
58
|
*/
|
|
31
|
-
async
|
|
32
|
-
this.
|
|
59
|
+
async openSheet() {
|
|
60
|
+
if (this._isOpen)
|
|
61
|
+
return;
|
|
62
|
+
this._isOpen = true;
|
|
63
|
+
this.open = true;
|
|
33
64
|
this.updateContext();
|
|
34
65
|
this.sheetOpen.emit();
|
|
66
|
+
this.sekiOpenChange.emit(true);
|
|
35
67
|
}
|
|
36
68
|
/**
|
|
37
69
|
* Closes the sheet
|
|
38
70
|
*/
|
|
39
|
-
async
|
|
40
|
-
this.
|
|
71
|
+
async closeSheet() {
|
|
72
|
+
if (!this._isOpen)
|
|
73
|
+
return;
|
|
74
|
+
this._isOpen = false;
|
|
75
|
+
this.open = false;
|
|
41
76
|
this.updateContext();
|
|
42
77
|
this.sheetClose.emit();
|
|
43
|
-
|
|
44
|
-
updateContext() {
|
|
45
|
-
// seki-sheet-content has no other way to know this sheet's open state — it
|
|
46
|
-
// reads this off the host element via closest('seki-sheet').
|
|
47
|
-
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
48
|
-
this.el._sheetContext = { isOpen: this.isOpen };
|
|
49
|
-
}
|
|
50
|
-
componentDidLoad() {
|
|
51
|
-
this.updateContext();
|
|
78
|
+
this.sekiOpenChange.emit(false);
|
|
52
79
|
}
|
|
53
80
|
/**
|
|
54
81
|
* Toggles the sheet
|
|
55
82
|
*/
|
|
56
|
-
async
|
|
57
|
-
if (this.
|
|
58
|
-
await this.
|
|
83
|
+
async toggleSheet() {
|
|
84
|
+
if (this._isOpen) {
|
|
85
|
+
await this.closeSheet();
|
|
59
86
|
}
|
|
60
87
|
else {
|
|
61
|
-
await this.
|
|
88
|
+
await this.openSheet();
|
|
62
89
|
}
|
|
63
90
|
}
|
|
91
|
+
updateContext() {
|
|
92
|
+
// seki-sheet-content has no other way to know this sheet's open state — it
|
|
93
|
+
// reads this off the host element via closest('seki-sheet').
|
|
94
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
95
|
+
this.el._sheetContext = { isOpen: this._isOpen };
|
|
96
|
+
}
|
|
64
97
|
handleTriggerClick() {
|
|
65
|
-
this.
|
|
98
|
+
this.toggleSheet();
|
|
66
99
|
}
|
|
67
100
|
handleCloseSheet() {
|
|
68
|
-
this.
|
|
101
|
+
this.closeSheet();
|
|
69
102
|
}
|
|
70
103
|
handleKeydown(ev) {
|
|
71
|
-
if (this.
|
|
72
|
-
this.
|
|
104
|
+
if (this._isOpen && ev.key === 'Escape') {
|
|
105
|
+
this.closeSheet();
|
|
73
106
|
}
|
|
74
107
|
}
|
|
75
108
|
connectedCallback() {
|
|
76
109
|
syncTheme(this.el);
|
|
77
110
|
}
|
|
78
111
|
render() {
|
|
79
|
-
return (h("div", { key: '
|
|
112
|
+
return (h("div", { key: '0d7f939728b7332e649e79b9189215f6ec2ee0ad', class: {
|
|
80
113
|
'seki-sheet': true,
|
|
81
|
-
'seki-sheet--open': this.
|
|
82
|
-
}, part: "sheet" }, h("slot", { key: '
|
|
114
|
+
'seki-sheet--open': this._isOpen,
|
|
115
|
+
}, part: "sheet" }, h("slot", { key: '2ab893341627204176329e2a40ac342f9d92f93c' }), this._isOpen && (h("div", { key: 'f7f131f3a2a287926d1547ad656f8125a00a1150', class: "seki-sheet-overlay", part: "overlay", onClick: () => this.closeSheet() }))));
|
|
83
116
|
}
|
|
84
117
|
static get is() { return "seki-sheet"; }
|
|
85
118
|
static get encapsulation() { return "shadow"; }
|
|
@@ -93,9 +126,53 @@ export class SekiSheet {
|
|
|
93
126
|
"$": ["seki-sheet.css"]
|
|
94
127
|
};
|
|
95
128
|
}
|
|
129
|
+
static get properties() {
|
|
130
|
+
return {
|
|
131
|
+
"open": {
|
|
132
|
+
"type": "boolean",
|
|
133
|
+
"mutable": true,
|
|
134
|
+
"complexType": {
|
|
135
|
+
"original": "boolean",
|
|
136
|
+
"resolved": "boolean",
|
|
137
|
+
"references": {}
|
|
138
|
+
},
|
|
139
|
+
"required": false,
|
|
140
|
+
"optional": false,
|
|
141
|
+
"docs": {
|
|
142
|
+
"tags": [],
|
|
143
|
+
"text": "Controlled open state. Also readable/writable as the `open` attribute, so\n`<seki-sheet open>` renders open with no script involved."
|
|
144
|
+
},
|
|
145
|
+
"getter": false,
|
|
146
|
+
"setter": false,
|
|
147
|
+
"reflect": true,
|
|
148
|
+
"attribute": "open",
|
|
149
|
+
"defaultValue": "false"
|
|
150
|
+
},
|
|
151
|
+
"defaultOpen": {
|
|
152
|
+
"type": "boolean",
|
|
153
|
+
"mutable": false,
|
|
154
|
+
"complexType": {
|
|
155
|
+
"original": "boolean",
|
|
156
|
+
"resolved": "boolean",
|
|
157
|
+
"references": {}
|
|
158
|
+
},
|
|
159
|
+
"required": false,
|
|
160
|
+
"optional": false,
|
|
161
|
+
"docs": {
|
|
162
|
+
"tags": [],
|
|
163
|
+
"text": "Initial open state for uncontrolled usage"
|
|
164
|
+
},
|
|
165
|
+
"getter": false,
|
|
166
|
+
"setter": false,
|
|
167
|
+
"reflect": false,
|
|
168
|
+
"attribute": "default-open",
|
|
169
|
+
"defaultValue": "false"
|
|
170
|
+
}
|
|
171
|
+
};
|
|
172
|
+
}
|
|
96
173
|
static get states() {
|
|
97
174
|
return {
|
|
98
|
-
"
|
|
175
|
+
"_isOpen": {}
|
|
99
176
|
};
|
|
100
177
|
}
|
|
101
178
|
static get events() {
|
|
@@ -129,11 +206,26 @@ export class SekiSheet {
|
|
|
129
206
|
"resolved": "void",
|
|
130
207
|
"references": {}
|
|
131
208
|
}
|
|
209
|
+
}, {
|
|
210
|
+
"method": "sekiOpenChange",
|
|
211
|
+
"name": "sekiOpenChange",
|
|
212
|
+
"bubbles": true,
|
|
213
|
+
"cancelable": true,
|
|
214
|
+
"composed": true,
|
|
215
|
+
"docs": {
|
|
216
|
+
"tags": [],
|
|
217
|
+
"text": "Emitted whenever the open state changes. Matches the dialog/popover/collapsible\nevent shape so a consumer can listen to one event name across every overlay."
|
|
218
|
+
},
|
|
219
|
+
"complexType": {
|
|
220
|
+
"original": "boolean",
|
|
221
|
+
"resolved": "boolean",
|
|
222
|
+
"references": {}
|
|
223
|
+
}
|
|
132
224
|
}];
|
|
133
225
|
}
|
|
134
226
|
static get methods() {
|
|
135
227
|
return {
|
|
136
|
-
"
|
|
228
|
+
"openSheet": {
|
|
137
229
|
"complexType": {
|
|
138
230
|
"signature": "() => Promise<void>",
|
|
139
231
|
"parameters": [],
|
|
@@ -150,7 +242,7 @@ export class SekiSheet {
|
|
|
150
242
|
"tags": []
|
|
151
243
|
}
|
|
152
244
|
},
|
|
153
|
-
"
|
|
245
|
+
"closeSheet": {
|
|
154
246
|
"complexType": {
|
|
155
247
|
"signature": "() => Promise<void>",
|
|
156
248
|
"parameters": [],
|
|
@@ -167,7 +259,7 @@ export class SekiSheet {
|
|
|
167
259
|
"tags": []
|
|
168
260
|
}
|
|
169
261
|
},
|
|
170
|
-
"
|
|
262
|
+
"toggleSheet": {
|
|
171
263
|
"complexType": {
|
|
172
264
|
"signature": "() => Promise<void>",
|
|
173
265
|
"parameters": [],
|
|
@@ -187,6 +279,12 @@ export class SekiSheet {
|
|
|
187
279
|
};
|
|
188
280
|
}
|
|
189
281
|
static get elementRef() { return "el"; }
|
|
282
|
+
static get watchers() {
|
|
283
|
+
return [{
|
|
284
|
+
"propName": "open",
|
|
285
|
+
"methodName": "handleOpenPropChange"
|
|
286
|
+
}];
|
|
287
|
+
}
|
|
190
288
|
static get listeners() {
|
|
191
289
|
return [{
|
|
192
290
|
"name": "triggerClick",
|
|
@@ -41,6 +41,17 @@ export class SekiTooltip {
|
|
|
41
41
|
* @min 0
|
|
42
42
|
*/
|
|
43
43
|
this.offset = 8;
|
|
44
|
+
/**
|
|
45
|
+
* Controlled open state. Reflects to the `open` attribute, so
|
|
46
|
+
* `<seki-tooltip open>` renders visible with no script involved.
|
|
47
|
+
* @default false
|
|
48
|
+
*/
|
|
49
|
+
this.open = false;
|
|
50
|
+
/**
|
|
51
|
+
* Initial open state for uncontrolled usage
|
|
52
|
+
* @default false
|
|
53
|
+
*/
|
|
54
|
+
this.defaultOpen = false;
|
|
44
55
|
/**
|
|
45
56
|
* Internal state: whether tooltip is currently visible
|
|
46
57
|
*/
|
|
@@ -181,8 +192,11 @@ export class SekiTooltip {
|
|
|
181
192
|
* @returns Promise resolves when tooltip is visible
|
|
182
193
|
*/
|
|
183
194
|
async show() {
|
|
184
|
-
if (this.disabled)
|
|
195
|
+
if (this.disabled) {
|
|
196
|
+
// Keep the reflected prop honest when a show request is refused.
|
|
197
|
+
this.open = false;
|
|
185
198
|
return;
|
|
199
|
+
}
|
|
186
200
|
// Clear any pending hide timer
|
|
187
201
|
if (this.hideTimer) {
|
|
188
202
|
clearTimeout(this.hideTimer);
|
|
@@ -190,6 +204,7 @@ export class SekiTooltip {
|
|
|
190
204
|
}
|
|
191
205
|
// Set visible state
|
|
192
206
|
this.isVisible = true;
|
|
207
|
+
this.open = true;
|
|
193
208
|
// Calculate position
|
|
194
209
|
this.calculatePosition();
|
|
195
210
|
// Emit show event
|
|
@@ -207,6 +222,7 @@ export class SekiTooltip {
|
|
|
207
222
|
}
|
|
208
223
|
// Set hidden state
|
|
209
224
|
this.isVisible = false;
|
|
225
|
+
this.open = false;
|
|
210
226
|
// Emit hide event
|
|
211
227
|
this.hideTooltip.emit({ reason: 'blur' });
|
|
212
228
|
}
|
|
@@ -338,9 +354,31 @@ export class SekiTooltip {
|
|
|
338
354
|
// here so it does not leak (and keep firing) after the tooltip is detached.
|
|
339
355
|
document.removeEventListener('keydown', this.onEscapeKey);
|
|
340
356
|
}
|
|
357
|
+
componentWillLoad() {
|
|
358
|
+
// `disabled` wins over a requested initial open state.
|
|
359
|
+
this.isVisible = (this.open || this.defaultOpen) && !this.disabled;
|
|
360
|
+
this.open = this.isVisible;
|
|
361
|
+
}
|
|
341
362
|
componentDidLoad() {
|
|
342
363
|
this.hasLoaded = true;
|
|
343
364
|
this.attachTriggerListeners();
|
|
365
|
+
if (this.isVisible) {
|
|
366
|
+
// Children are only in place now, so the initial position can finally be
|
|
367
|
+
// measured against the trigger.
|
|
368
|
+
this.calculatePosition();
|
|
369
|
+
}
|
|
370
|
+
}
|
|
371
|
+
openChanged(newValue) {
|
|
372
|
+
// An outside assignment (`tooltip.open = true`) has to win after first render;
|
|
373
|
+
// `open` is only read once in componentWillLoad otherwise.
|
|
374
|
+
if (newValue === this.isVisible)
|
|
375
|
+
return;
|
|
376
|
+
if (newValue) {
|
|
377
|
+
this.show();
|
|
378
|
+
}
|
|
379
|
+
else {
|
|
380
|
+
this.hide();
|
|
381
|
+
}
|
|
344
382
|
}
|
|
345
383
|
connectedCallback() {
|
|
346
384
|
syncTheme(this.el);
|
|
@@ -363,7 +401,7 @@ export class SekiTooltip {
|
|
|
363
401
|
clearTimeout(this.longPressTimer);
|
|
364
402
|
}
|
|
365
403
|
render() {
|
|
366
|
-
return (h("div", { key: '
|
|
404
|
+
return (h("div", { key: 'd934fb59ac9e6b47e208113f430dbdf151e4b9d8', class: `tooltip ${this.isVisible ? 'tooltip--visible' : ''}`, role: "tooltip" }, h("slot", { key: '0fe73a7b7b0bcd405dec9a77ddcf0c4a7e2b4b09', name: "content" }), h("div", { key: '9917e3661c8740b69bdaca4e8e7aa168b0c7c47c', class: "tooltip-arrow" })));
|
|
367
405
|
}
|
|
368
406
|
static get is() { return "seki-tooltip"; }
|
|
369
407
|
static get encapsulation() { return "shadow"; }
|
|
@@ -485,6 +523,52 @@ export class SekiTooltip {
|
|
|
485
523
|
"reflect": false,
|
|
486
524
|
"attribute": "offset",
|
|
487
525
|
"defaultValue": "8"
|
|
526
|
+
},
|
|
527
|
+
"open": {
|
|
528
|
+
"type": "boolean",
|
|
529
|
+
"mutable": true,
|
|
530
|
+
"complexType": {
|
|
531
|
+
"original": "boolean",
|
|
532
|
+
"resolved": "boolean",
|
|
533
|
+
"references": {}
|
|
534
|
+
},
|
|
535
|
+
"required": false,
|
|
536
|
+
"optional": false,
|
|
537
|
+
"docs": {
|
|
538
|
+
"tags": [{
|
|
539
|
+
"name": "default",
|
|
540
|
+
"text": "false"
|
|
541
|
+
}],
|
|
542
|
+
"text": "Controlled open state. Reflects to the `open` attribute, so\n`<seki-tooltip open>` renders visible with no script involved."
|
|
543
|
+
},
|
|
544
|
+
"getter": false,
|
|
545
|
+
"setter": false,
|
|
546
|
+
"reflect": true,
|
|
547
|
+
"attribute": "open",
|
|
548
|
+
"defaultValue": "false"
|
|
549
|
+
},
|
|
550
|
+
"defaultOpen": {
|
|
551
|
+
"type": "boolean",
|
|
552
|
+
"mutable": false,
|
|
553
|
+
"complexType": {
|
|
554
|
+
"original": "boolean",
|
|
555
|
+
"resolved": "boolean",
|
|
556
|
+
"references": {}
|
|
557
|
+
},
|
|
558
|
+
"required": false,
|
|
559
|
+
"optional": false,
|
|
560
|
+
"docs": {
|
|
561
|
+
"tags": [{
|
|
562
|
+
"name": "default",
|
|
563
|
+
"text": "false"
|
|
564
|
+
}],
|
|
565
|
+
"text": "Initial open state for uncontrolled usage"
|
|
566
|
+
},
|
|
567
|
+
"getter": false,
|
|
568
|
+
"setter": false,
|
|
569
|
+
"reflect": false,
|
|
570
|
+
"attribute": "default-open",
|
|
571
|
+
"defaultValue": "false"
|
|
488
572
|
}
|
|
489
573
|
};
|
|
490
574
|
}
|
|
@@ -622,4 +706,10 @@ export class SekiTooltip {
|
|
|
622
706
|
};
|
|
623
707
|
}
|
|
624
708
|
static get elementRef() { return "el"; }
|
|
709
|
+
static get watchers() {
|
|
710
|
+
return [{
|
|
711
|
+
"propName": "open",
|
|
712
|
+
"methodName": "openChanged"
|
|
713
|
+
}];
|
|
714
|
+
}
|
|
625
715
|
}
|
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Deterministic, per-select-instance option id.
|
|
3
|
+
*
|
|
4
|
+
* seki-select's `contentId` (see `SelectContext.contentId` in
|
|
5
|
+
* `src/utils/select/types.ts`) is randomized once per `<seki-select>`
|
|
6
|
+
* instance. Prefixing the option id with it keeps ids collision-free across
|
|
7
|
+
* multiple `<seki-select>` instances on the same page that happen to share
|
|
8
|
+
* an option `value` — this only matters now that seki-select-option renders
|
|
9
|
+
* in scoped (non-shadow) mode and its `id` is a real, page-scoped DOM id
|
|
10
|
+
* assistive tech can actually resolve (see #300). Exported so both
|
|
11
|
+
* seki-select-option (which sets the id) and seki-select-trigger (which
|
|
12
|
+
* references it via aria-activedescendant) compute the exact same string.
|
|
13
|
+
*/
|
|
14
|
+
export function buildOptionId(contentId, value) {
|
|
15
|
+
return `${contentId}-option-${value}`;
|
|
16
|
+
}
|
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Deterministic, per-select-instance option id.
|
|
3
|
+
*
|
|
4
|
+
* seki-select's `contentId` (see `SelectContext.contentId` in
|
|
5
|
+
* `src/utils/select/types.ts`) is randomized once per `<seki-select>`
|
|
6
|
+
* instance. Prefixing the option id with it keeps ids collision-free across
|
|
7
|
+
* multiple `<seki-select>` instances on the same page that happen to share
|
|
8
|
+
* an option `value` — this only matters now that seki-select-option renders
|
|
9
|
+
* in scoped (non-shadow) mode and its `id` is a real, page-scoped DOM id
|
|
10
|
+
* assistive tech can actually resolve (see #300). Exported so both
|
|
11
|
+
* seki-select-option (which sets the id) and seki-select-trigger (which
|
|
12
|
+
* references it via aria-activedescendant) compute the exact same string.
|
|
13
|
+
*/
|
|
14
|
+
function buildOptionId(contentId, value) {
|
|
15
|
+
return `${contentId}-option-${value}`;
|
|
16
|
+
}
|
|
17
|
+
|
|
18
|
+
export { buildOptionId as b };
|
|
@@ -13,6 +13,7 @@ const SekiDatePicker$1 = /*@__PURE__*/ proxyCustomElement(class SekiDatePicker e
|
|
|
13
13
|
this.sekiChange = createEvent(this, "sekiChange");
|
|
14
14
|
this.sekiOpen = createEvent(this, "sekiOpen");
|
|
15
15
|
this.sekiClose = createEvent(this, "sekiClose");
|
|
16
|
+
this.sekiOpenChange = createEvent(this, "sekiOpenChange");
|
|
16
17
|
/**
|
|
17
18
|
* Selection mode: single date or date range
|
|
18
19
|
* @default 'single'
|
|
@@ -36,27 +37,25 @@ const SekiDatePicker$1 = /*@__PURE__*/ proxyCustomElement(class SekiDatePicker e
|
|
|
36
37
|
*/
|
|
37
38
|
this.required = false;
|
|
38
39
|
/**
|
|
39
|
-
*
|
|
40
|
+
* Controlled open state of the popover. Also readable/writable as the `open`
|
|
41
|
+
* attribute, so `<seki-date-picker open>` renders open with no script involved.
|
|
40
42
|
*/
|
|
41
|
-
this.
|
|
43
|
+
this.open = false;
|
|
44
|
+
/**
|
|
45
|
+
* Initial open state for uncontrolled usage
|
|
46
|
+
*/
|
|
47
|
+
this.defaultOpen = false;
|
|
48
|
+
/**
|
|
49
|
+
* Internal state for whether the popover is open
|
|
50
|
+
*/
|
|
51
|
+
this._isOpen = false;
|
|
42
52
|
this.handleTriggerClick = () => {
|
|
43
|
-
|
|
44
|
-
return;
|
|
45
|
-
this.isOpen = !this.isOpen;
|
|
46
|
-
if (this.isOpen) {
|
|
47
|
-
this.sekiOpen.emit();
|
|
48
|
-
requestAnimationFrame(() => {
|
|
49
|
-
this.positionPopover();
|
|
50
|
-
});
|
|
51
|
-
}
|
|
52
|
-
else {
|
|
53
|
-
this.sekiClose.emit();
|
|
54
|
-
}
|
|
53
|
+
this.toggleDatePicker();
|
|
55
54
|
};
|
|
56
55
|
this.handleDateSelect = (e) => {
|
|
57
56
|
this.value = e.detail;
|
|
58
57
|
this.sekiChange.emit(e.detail);
|
|
59
|
-
this.
|
|
58
|
+
this.closeDatePicker();
|
|
60
59
|
};
|
|
61
60
|
this.handleRangeSelect = (e) => {
|
|
62
61
|
var _a, _b;
|
|
@@ -64,16 +63,37 @@ const SekiDatePicker$1 = /*@__PURE__*/ proxyCustomElement(class SekiDatePicker e
|
|
|
64
63
|
this.rangeTo = (_b = e.detail.to) !== null && _b !== void 0 ? _b : undefined;
|
|
65
64
|
if (e.detail.from && e.detail.to) {
|
|
66
65
|
this.sekiChange.emit(e.detail);
|
|
67
|
-
this.
|
|
66
|
+
this.closeDatePicker();
|
|
68
67
|
}
|
|
69
68
|
};
|
|
70
69
|
}
|
|
71
70
|
componentWillLoad() {
|
|
71
|
+
this._isOpen = (this.open || this.defaultOpen) && !this.disabled;
|
|
72
|
+
this.open = this._isOpen;
|
|
72
73
|
if ('attachInternals' in H.prototype) {
|
|
73
74
|
this.internals = this.el.attachInternals();
|
|
74
75
|
}
|
|
75
76
|
this.updateFormValue();
|
|
76
77
|
}
|
|
78
|
+
componentDidLoad() {
|
|
79
|
+
if (this._isOpen) {
|
|
80
|
+
requestAnimationFrame(() => {
|
|
81
|
+
this.positionPopover();
|
|
82
|
+
});
|
|
83
|
+
}
|
|
84
|
+
}
|
|
85
|
+
handleOpenPropChange(newValue) {
|
|
86
|
+
// An outside assignment (`picker.open = true`) has to win after first render;
|
|
87
|
+
// `open` is only read once in componentWillLoad otherwise.
|
|
88
|
+
if (newValue === this._isOpen)
|
|
89
|
+
return;
|
|
90
|
+
if (newValue) {
|
|
91
|
+
this.openDatePicker();
|
|
92
|
+
}
|
|
93
|
+
else {
|
|
94
|
+
this.closeDatePicker();
|
|
95
|
+
}
|
|
96
|
+
}
|
|
77
97
|
updateFormValue() {
|
|
78
98
|
if (this.internals && typeof this.internals.setFormValue === 'function') {
|
|
79
99
|
const value = this.parseDate(this.value);
|
|
@@ -138,28 +158,35 @@ const SekiDatePicker$1 = /*@__PURE__*/ proxyCustomElement(class SekiDatePicker e
|
|
|
138
158
|
}
|
|
139
159
|
handleKeyDown(event) {
|
|
140
160
|
var _a;
|
|
141
|
-
if (event.key === 'Escape' && this.
|
|
161
|
+
if (event.key === 'Escape' && this._isOpen) {
|
|
142
162
|
event.preventDefault();
|
|
143
|
-
this.
|
|
163
|
+
this.closeDatePicker();
|
|
144
164
|
(_a = this.triggerRef) === null || _a === void 0 ? void 0 : _a.focus();
|
|
145
165
|
}
|
|
146
166
|
}
|
|
147
167
|
handleDocumentClick(event) {
|
|
148
|
-
if (!this.
|
|
168
|
+
if (!this._isOpen)
|
|
149
169
|
return;
|
|
150
170
|
const target = event.target;
|
|
151
171
|
if (!this.el.contains(target)) {
|
|
152
|
-
this.
|
|
172
|
+
this.closeDatePicker();
|
|
153
173
|
}
|
|
154
174
|
}
|
|
155
175
|
/**
|
|
156
176
|
* Open the date picker popover
|
|
157
177
|
*/
|
|
158
|
-
async
|
|
159
|
-
if (this.disabled)
|
|
178
|
+
async openDatePicker() {
|
|
179
|
+
if (this.disabled) {
|
|
180
|
+
// Keep the reflected prop honest when an open request is refused.
|
|
181
|
+
this.open = false;
|
|
182
|
+
return;
|
|
183
|
+
}
|
|
184
|
+
if (this._isOpen)
|
|
160
185
|
return;
|
|
161
|
-
this.
|
|
186
|
+
this._isOpen = true;
|
|
187
|
+
this.open = true;
|
|
162
188
|
this.sekiOpen.emit();
|
|
189
|
+
this.sekiOpenChange.emit(true);
|
|
163
190
|
requestAnimationFrame(() => {
|
|
164
191
|
this.positionPopover();
|
|
165
192
|
});
|
|
@@ -167,19 +194,23 @@ const SekiDatePicker$1 = /*@__PURE__*/ proxyCustomElement(class SekiDatePicker e
|
|
|
167
194
|
/**
|
|
168
195
|
* Close the date picker popover
|
|
169
196
|
*/
|
|
170
|
-
async
|
|
171
|
-
this.
|
|
197
|
+
async closeDatePicker() {
|
|
198
|
+
if (!this._isOpen)
|
|
199
|
+
return;
|
|
200
|
+
this._isOpen = false;
|
|
201
|
+
this.open = false;
|
|
172
202
|
this.sekiClose.emit();
|
|
203
|
+
this.sekiOpenChange.emit(false);
|
|
173
204
|
}
|
|
174
205
|
/**
|
|
175
206
|
* Toggle the date picker popover
|
|
176
207
|
*/
|
|
177
|
-
async
|
|
178
|
-
if (this.
|
|
179
|
-
await this.
|
|
208
|
+
async toggleDatePicker() {
|
|
209
|
+
if (this._isOpen) {
|
|
210
|
+
await this.closeDatePicker();
|
|
180
211
|
}
|
|
181
212
|
else {
|
|
182
|
-
await this.
|
|
213
|
+
await this.openDatePicker();
|
|
183
214
|
}
|
|
184
215
|
}
|
|
185
216
|
connectedCallback() {
|
|
@@ -191,16 +222,17 @@ const SekiDatePicker$1 = /*@__PURE__*/ proxyCustomElement(class SekiDatePicker e
|
|
|
191
222
|
const selectedDate = this.parseDate(this.value);
|
|
192
223
|
const rangeFrom = this.parseDate(this.rangeFrom);
|
|
193
224
|
const rangeTo = this.parseDate(this.rangeTo);
|
|
194
|
-
return (h("div", { key: '
|
|
225
|
+
return (h("div", { key: '79b9eec6c71d77d2af7f006ee03f6a836f5405df', class: "seki-date-picker" }, h("button", { key: '54460e6603c806d24eb0c36baa1b5dbdd7aeb90d', type: "button", ref: el => (this.triggerRef = el), class: {
|
|
195
226
|
'seki-date-picker__trigger': true,
|
|
196
|
-
'seki-date-picker__trigger--open': this.
|
|
227
|
+
'seki-date-picker__trigger--open': this._isOpen,
|
|
197
228
|
'seki-date-picker__trigger--disabled': this.disabled,
|
|
198
229
|
'seki-date-picker__trigger--has-value': hasValue,
|
|
199
|
-
}, disabled: this.disabled, "aria-haspopup": "dialog", "aria-expanded": this.
|
|
230
|
+
}, disabled: this.disabled, "aria-haspopup": "dialog", "aria-expanded": this._isOpen ? 'true' : 'false', "aria-label": this.ariaLabel || this.placeholder, onClick: this.handleTriggerClick }, h("svg", { key: 'b65b7e82e5ad5485f5f2dd5934fb00fe7a2df0e4', class: "seki-date-picker__icon", xmlns: "http://www.w3.org/2000/svg", width: "16", height: "16", viewBox: "0 0 24 24", fill: "none", stroke: "currentColor", "stroke-width": "2", "stroke-linecap": "round", "stroke-linejoin": "round" }, h("rect", { key: 'be93574c133eb04d61d765fa0d4d893dfd18de5b', x: "3", y: "4", width: "18", height: "18", rx: "2", ry: "2" }), h("line", { key: 'f60deabd7d2c3061b08b8245650935a85068937a', x1: "16", y1: "2", x2: "16", y2: "6" }), h("line", { key: 'e6dba2b6b7501a6e2de21a29edcafe1927f1ad4d', x1: "8", y1: "2", x2: "8", y2: "6" }), h("line", { key: '4ca41a9af0155298fcaf2f1273f3833ba1df379a', x1: "3", y1: "10", x2: "21", y2: "10" })), h("span", { key: 'f9ef3166165413282928920a7a1b726b1edc4d54', class: "seki-date-picker__value" }, hasValue ? displayValue : this.placeholder)), this._isOpen && (h("div", { key: '561b160f14e86b0a7c043a30ed6e315465d6160b', ref: el => (this.popoverRef = el), class: "seki-date-picker__popover", role: "dialog", "aria-modal": "true", "aria-label": "Choose date" }, h("seki-calendar", { key: '96688e161b3a3814ed27135905de95df437c8bbc', mode: this.mode, selected: selectedDate === null || selectedDate === void 0 ? void 0 : selectedDate.toISOString(), "range-from": rangeFrom === null || rangeFrom === void 0 ? void 0 : rangeFrom.toISOString(), "range-to": rangeTo === null || rangeTo === void 0 ? void 0 : rangeTo.toISOString(), "min-date": this.minDate, "max-date": this.maxDate, onSekiSelect: this.handleDateSelect, onSekiRangeSelect: this.handleRangeSelect })))));
|
|
200
231
|
}
|
|
201
232
|
static get formAssociated() { return true; }
|
|
202
233
|
get el() { return this; }
|
|
203
234
|
static get watchers() { return {
|
|
235
|
+
"open": ["handleOpenPropChange"],
|
|
204
236
|
"value": ["updateFormValue"],
|
|
205
237
|
"rangeFrom": ["updateFormValue"],
|
|
206
238
|
"rangeTo": ["updateFormValue"]
|
|
@@ -219,11 +251,14 @@ const SekiDatePicker$1 = /*@__PURE__*/ proxyCustomElement(class SekiDatePicker e
|
|
|
219
251
|
"name": [1],
|
|
220
252
|
"required": [4],
|
|
221
253
|
"ariaLabel": [1, "aria-label"],
|
|
222
|
-
"
|
|
223
|
-
"
|
|
224
|
-
"
|
|
225
|
-
"
|
|
254
|
+
"open": [1540],
|
|
255
|
+
"defaultOpen": [4, "default-open"],
|
|
256
|
+
"_isOpen": [32],
|
|
257
|
+
"openDatePicker": [64],
|
|
258
|
+
"closeDatePicker": [64],
|
|
259
|
+
"toggleDatePicker": [64]
|
|
226
260
|
}, [[0, "keydown", "handleKeyDown"], [4, "click", "handleDocumentClick"]], {
|
|
261
|
+
"open": ["handleOpenPropChange"],
|
|
227
262
|
"value": ["updateFormValue"],
|
|
228
263
|
"rangeFrom": ["updateFormValue"],
|
|
229
264
|
"rangeTo": ["updateFormValue"]
|