@redvars/peacock 3.3.2 → 3.4.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/IndividualComponent-DUINtMGK.js +67 -0
- package/dist/IndividualComponent-DUINtMGK.js.map +1 -0
- package/dist/assets/images/empty-state/no-document.svg +11 -12
- package/dist/assets/images/empty-state/page.svg +15 -9
- package/dist/bottom-sheet.js +238 -0
- package/dist/bottom-sheet.js.map +1 -0
- package/dist/{button-ClzS8JLq.js → button-COYCtuA8.js} +306 -149
- package/dist/button-COYCtuA8.js.map +1 -0
- package/dist/button-group-DsXquZQn.js +440 -0
- package/dist/button-group-DsXquZQn.js.map +1 -0
- package/dist/button-group.js +6 -4
- package/dist/button-group.js.map +1 -1
- package/dist/button.js +5 -3
- package/dist/button.js.map +1 -1
- package/dist/card-content.js +29 -0
- package/dist/card-content.js.map +1 -0
- package/dist/card.js +418 -44
- package/dist/card.js.map +1 -1
- package/dist/{chart-bar-DbnXQgvS.js → chart-bar-cn6rrna-.js} +2 -2
- package/dist/{chart-bar-DbnXQgvS.js.map → chart-bar-cn6rrna-.js.map} +1 -1
- package/dist/chart-bar.js +4 -3
- package/dist/chart-bar.js.map +1 -1
- package/dist/chart-doughnut.js +2 -1
- package/dist/chart-doughnut.js.map +1 -1
- package/dist/chart-pie.js +2 -1
- package/dist/chart-pie.js.map +1 -1
- package/dist/chart-stacked-bar.js +4 -3
- package/dist/chart-stacked-bar.js.map +1 -1
- package/dist/{class-map-59YGWLnx.js → class-map-3TAnCMAX.js} +3 -9
- package/dist/class-map-3TAnCMAX.js.map +1 -0
- package/dist/clock.js +2 -1
- package/dist/clock.js.map +1 -1
- package/dist/code-editor.js +6 -4
- package/dist/code-editor.js.map +1 -1
- package/dist/code-highlighter.js +5 -3
- package/dist/code-highlighter.js.map +1 -1
- package/dist/custom-elements-jsdocs.json +2458 -2753
- package/dist/custom-elements.json +3185 -777
- package/dist/dispatch-event-utils-B4odODQf.js.map +1 -1
- package/dist/index.js +14 -10
- package/dist/index.js.map +1 -1
- package/dist/number-counter.js +3 -2
- package/dist/number-counter.js.map +1 -1
- package/dist/{observe-theme-change-pALI5fmV.js → observe-theme-change-DKAIv5BB.js} +3 -2
- package/dist/observe-theme-change-DKAIv5BB.js.map +1 -0
- package/dist/peacock-loader.js +37 -8
- package/dist/peacock-loader.js.map +1 -1
- package/dist/property-1psGvXOq.js +10 -0
- package/dist/property-1psGvXOq.js.map +1 -0
- package/dist/{snackbar-74YCdMPL.js → select-C3XAzenC.js} +2158 -191
- package/dist/select-C3XAzenC.js.map +1 -0
- package/dist/side-sheet.js +186 -0
- package/dist/side-sheet.js.map +1 -0
- package/dist/src/bottom-sheet/bottom-sheet.d.ts +42 -0
- package/dist/src/bottom-sheet/index.d.ts +1 -0
- package/dist/src/button/BaseButton.d.ts +4 -3
- package/dist/src/button/button/button.d.ts +4 -0
- package/dist/src/button/button-group/button-group.d.ts +32 -3
- package/dist/src/button/icon-button/icon-button.d.ts +4 -0
- package/dist/src/card/card-content.d.ts +15 -0
- package/dist/src/card/card.d.ts +37 -3
- package/dist/src/card/index.d.ts +1 -0
- package/dist/src/container/container.d.ts +1 -1
- package/dist/src/empty-state/empty-state.d.ts +1 -1
- package/dist/src/focus-ring/focus-ring.d.ts +4 -1
- package/dist/src/index.d.ts +7 -1
- package/dist/src/menu/menu/menu.d.ts +1 -0
- package/dist/src/menu/menu-item/menu-item.d.ts +0 -1
- package/dist/src/radio/index.d.ts +1 -0
- package/dist/src/radio/radio.d.ts +73 -0
- package/dist/src/ripple/ripple.d.ts +19 -3
- package/dist/src/segmented-button/index.d.ts +2 -0
- package/dist/src/segmented-button/segmented-button-group.d.ts +46 -0
- package/dist/src/segmented-button/segmented-button.d.ts +65 -0
- package/dist/src/select/index.d.ts +3 -0
- package/dist/src/select/option.d.ts +55 -0
- package/dist/src/select/select.d.ts +116 -0
- package/dist/src/side-sheet/index.d.ts +1 -0
- package/dist/src/side-sheet/side-sheet.d.ts +41 -0
- package/dist/src/tabs/tab-group.d.ts +0 -1
- package/dist/src/tabs/tab.d.ts +8 -2
- package/dist/src/tabs/tabs.d.ts +13 -1
- package/dist/state-DwbEjqVk.js +10 -0
- package/dist/state-DwbEjqVk.js.map +1 -0
- package/dist/{style-map-DcB52w-l.js → style-map-CRFEoCEg.js} +2 -2
- package/dist/{style-map-DcB52w-l.js.map → style-map-CRFEoCEg.js.map} +1 -1
- package/dist/tsconfig.tsbuildinfo +1 -1
- package/dist/{unsafe-html-C2r3PyzF.js → unsafe-html-D3GHRaGQ.js} +2 -2
- package/dist/{unsafe-html-C2r3PyzF.js.map → unsafe-html-D3GHRaGQ.js.map} +1 -1
- package/package.json +1 -1
- package/readme.md +2 -2
- package/src/bottom-sheet/bottom-sheet.scss +88 -0
- package/src/bottom-sheet/bottom-sheet.ts +135 -0
- package/src/bottom-sheet/index.ts +1 -0
- package/src/button/BaseButton.ts +16 -7
- package/src/button/button/button-colors.scss +76 -5
- package/src/button/button/button-sizes.scss +39 -19
- package/src/button/button/button.scss +117 -116
- package/src/button/button/button.ts +23 -1
- package/src/button/button-group/button-group.scss +25 -22
- package/src/button/button-group/button-group.ts +121 -4
- package/src/button/icon-button/icon-button-sizes.scss +35 -15
- package/src/button/icon-button/icon-button.ts +21 -1
- package/src/card/card-colors.scss +10 -0
- package/src/card/card-content.ts +26 -0
- package/src/card/card.scss +221 -41
- package/src/card/card.ts +240 -7
- package/src/card/index.ts +1 -0
- package/src/code-editor/code-editor.ts +1 -1
- package/src/container/container.ts +1 -1
- package/src/empty-state/empty-state.scss +8 -0
- package/src/empty-state/empty-state.ts +2 -2
- package/src/focus-ring/focus-ring.ts +37 -19
- package/src/index.ts +8 -1
- package/src/menu/menu/menu.scss +24 -3
- package/src/menu/menu/menu.ts +23 -2
- package/src/menu/menu-item/menu-item.scss +1 -0
- package/src/menu/menu-item/menu-item.ts +1 -9
- package/src/peacock-loader.ts +32 -0
- package/src/radio/index.ts +1 -0
- package/src/radio/radio.scss +181 -0
- package/src/radio/radio.ts +362 -0
- package/src/ripple/ripple.ts +19 -3
- package/src/segmented-button/index.ts +2 -0
- package/src/segmented-button/segmented-button-group.scss +21 -0
- package/src/segmented-button/segmented-button-group.ts +110 -0
- package/src/segmented-button/segmented-button.scss +115 -0
- package/src/segmented-button/segmented-button.ts +175 -0
- package/src/select/index.ts +3 -0
- package/src/select/option.ts +109 -0
- package/src/select/select.scss +120 -0
- package/src/select/select.ts +486 -0
- package/src/side-sheet/index.ts +1 -0
- package/src/side-sheet/side-sheet.scss +79 -0
- package/src/side-sheet/side-sheet.ts +100 -0
- package/src/slider/slider.scss +0 -1
- package/src/tabs/demo/index.html +90 -0
- package/src/tabs/tab-group.ts +0 -3
- package/src/tabs/tab.scss +237 -25
- package/src/tabs/tab.ts +86 -12
- package/src/tabs/tabs.scss +37 -3
- package/src/tabs/tabs.ts +118 -2
- package/src/utils/dispatch-event-utils.ts +1 -0
- package/dist/IndividualComponent-Dt5xirYG.js +0 -73
- package/dist/IndividualComponent-Dt5xirYG.js.map +0 -1
- package/dist/button-ClzS8JLq.js.map +0 -1
- package/dist/button-group-BMS5WvaF.js +0 -292
- package/dist/button-group-BMS5WvaF.js.map +0 -1
- package/dist/chart-donut.js +0 -309
- package/dist/chart-donut.js.map +0 -1
- package/dist/class-map-59YGWLnx.js.map +0 -1
- package/dist/observe-theme-change-pALI5fmV.js.map +0 -1
- package/dist/snackbar-74YCdMPL.js.map +0 -1
- package/dist/src/chart-donut/chart-donut.d.ts +0 -53
- package/dist/src/chart-donut/index.d.ts +0 -1
- package/dist/test/card.test.d.ts +0 -1
- package/src/chart-donut/chart-donut.scss +0 -37
- package/src/chart-donut/chart-donut.ts +0 -287
- package/src/chart-donut/demo/index.html +0 -51
- package/src/chart-donut/index.ts +0 -1
package/src/card/card.ts
CHANGED
|
@@ -1,10 +1,14 @@
|
|
|
1
|
-
import { LitElement, html } from 'lit';
|
|
2
|
-
import { property } from 'lit/decorators.js';
|
|
1
|
+
import { LitElement, html, nothing, PropertyValues } from 'lit';
|
|
2
|
+
import { property, query, state } from 'lit/decorators.js';
|
|
3
|
+
import { classMap } from 'lit/directives/class-map.js';
|
|
4
|
+
import { dispatchActivationClick, isActivationClick } from '../utils/dispatch-event-utils.js';
|
|
5
|
+
import { observerSlotChangesWithCallback, throttle } from '../utils.js';
|
|
3
6
|
import IndividualComponent from '../IndividualComponent.js';
|
|
4
7
|
import styles from './card.scss';
|
|
8
|
+
import colorStyles from './card-colors.scss';
|
|
5
9
|
|
|
6
10
|
type CardVariant = 'elevated' | 'filled' | 'outlined';
|
|
7
|
-
|
|
11
|
+
|
|
8
12
|
/**
|
|
9
13
|
* @label Card
|
|
10
14
|
* @tag wc-card
|
|
@@ -24,15 +28,244 @@ type CardElevation = 0 | 1 | 2 | 3 | 4 | 5;
|
|
|
24
28
|
*/
|
|
25
29
|
@IndividualComponent
|
|
26
30
|
export class Card extends LitElement {
|
|
27
|
-
static styles = [styles];
|
|
31
|
+
static styles = [styles, colorStyles];
|
|
28
32
|
|
|
33
|
+
#id = crypto.randomUUID();
|
|
34
|
+
|
|
29
35
|
@property({ type: String, reflect: true })
|
|
30
36
|
variant: CardVariant = 'elevated';
|
|
31
37
|
|
|
32
|
-
@property({
|
|
33
|
-
|
|
38
|
+
@property({type: Boolean, reflect: true})
|
|
39
|
+
disabled: boolean = false;
|
|
40
|
+
|
|
41
|
+
@property({ type: Boolean, reflect: true })
|
|
42
|
+
actionable: boolean = false;
|
|
43
|
+
|
|
44
|
+
/**
|
|
45
|
+
* If button is disabled, the reason why it is disabled.
|
|
46
|
+
*/
|
|
47
|
+
@property({ attribute: 'disabled-reason' })
|
|
48
|
+
disabledReason: string = '';
|
|
49
|
+
|
|
50
|
+
/**
|
|
51
|
+
* Hyperlink to navigate to on click.
|
|
52
|
+
*/
|
|
53
|
+
@property({ reflect: true }) href?: string;
|
|
54
|
+
|
|
55
|
+
/**
|
|
56
|
+
* Sets or retrieves the window or frame at which to target content.
|
|
57
|
+
*/
|
|
58
|
+
@property() target: string = '_self';
|
|
59
|
+
|
|
60
|
+
|
|
61
|
+
/**
|
|
62
|
+
* Sets the delay for throttle in milliseconds. Defaults to 200 milliseconds.
|
|
63
|
+
*/
|
|
64
|
+
@property() throttleDelay = 200;
|
|
65
|
+
|
|
66
|
+
/**
|
|
67
|
+
* States
|
|
68
|
+
*/
|
|
69
|
+
@state()
|
|
70
|
+
isPressed = false;
|
|
71
|
+
|
|
72
|
+
@state()
|
|
73
|
+
private slotHasContent = false;
|
|
74
|
+
|
|
75
|
+
|
|
76
|
+
@query('.card') readonly cardElement!: HTMLElement | null;
|
|
77
|
+
|
|
78
|
+
@query('slot') readonly contentSlot!: HTMLSlotElement | null;
|
|
79
|
+
|
|
80
|
+
#tabindex?: number = 0;
|
|
81
|
+
|
|
82
|
+
#slottedTabIndexMap = new WeakMap<HTMLElement, string | null>();
|
|
83
|
+
|
|
84
|
+
override firstUpdated() {
|
|
85
|
+
this.__dispatchClickWithThrottle = throttle(
|
|
86
|
+
this.__dispatchClick,
|
|
87
|
+
this.throttleDelay,
|
|
88
|
+
);
|
|
89
|
+
observerSlotChangesWithCallback(
|
|
90
|
+
this.renderRoot.querySelector('slot'),
|
|
91
|
+
hasContent => {
|
|
92
|
+
this.slotHasContent = hasContent;
|
|
93
|
+
this.__syncSlottedChildrenTabIndex();
|
|
94
|
+
this.requestUpdate();
|
|
95
|
+
},
|
|
96
|
+
);
|
|
97
|
+
this.__syncSlottedChildrenTabIndex();
|
|
98
|
+
}
|
|
99
|
+
|
|
100
|
+
override updated(changedProperties: PropertyValues<this>) {
|
|
101
|
+
if (changedProperties.has('actionable') || changedProperties.has('href')) {
|
|
102
|
+
this.__syncSlottedChildrenTabIndex();
|
|
103
|
+
}
|
|
104
|
+
}
|
|
105
|
+
|
|
106
|
+
__syncSlottedChildrenTabIndex() {
|
|
107
|
+
if (!this.contentSlot) return;
|
|
108
|
+
|
|
109
|
+
const shouldDisableTabbing = this.actionable || this.__isLink();
|
|
110
|
+
const assignedChildren = this.contentSlot.assignedElements({ flatten: true });
|
|
111
|
+
|
|
112
|
+
assignedChildren.forEach(node => {
|
|
113
|
+
if (!(node instanceof HTMLElement)) return;
|
|
114
|
+
|
|
115
|
+
if (shouldDisableTabbing) {
|
|
116
|
+
if (!this.#slottedTabIndexMap.has(node)) {
|
|
117
|
+
this.#slottedTabIndexMap.set(node, node.getAttribute('tabindex'));
|
|
118
|
+
}
|
|
119
|
+
|
|
120
|
+
if (node.getAttribute('tabindex') !== '-1') {
|
|
121
|
+
node.setAttribute('tabindex', '-1');
|
|
122
|
+
}
|
|
123
|
+
return;
|
|
124
|
+
}
|
|
125
|
+
|
|
126
|
+
const originalTabIndex = this.#slottedTabIndexMap.get(node);
|
|
127
|
+
if (originalTabIndex === null) {
|
|
128
|
+
if (node.hasAttribute('tabindex')) {
|
|
129
|
+
node.removeAttribute('tabindex');
|
|
130
|
+
}
|
|
131
|
+
} else if (originalTabIndex !== undefined) {
|
|
132
|
+
if (node.getAttribute('tabindex') !== originalTabIndex) {
|
|
133
|
+
node.setAttribute('tabindex', originalTabIndex);
|
|
134
|
+
}
|
|
135
|
+
}
|
|
136
|
+
|
|
137
|
+
this.#slottedTabIndexMap.delete(node);
|
|
138
|
+
});
|
|
139
|
+
}
|
|
140
|
+
|
|
141
|
+
__dispatchClickWithThrottle: (event: MouseEvent | KeyboardEvent) => void =
|
|
142
|
+
event => {
|
|
143
|
+
this.__dispatchClick(event);
|
|
144
|
+
};
|
|
145
|
+
|
|
146
|
+
__dispatchClick = (event: MouseEvent | KeyboardEvent) => {
|
|
147
|
+
// If the button is soft-disabled or a disabled link, we need to explicitly
|
|
148
|
+
// prevent the click from propagating to other event listeners as well as
|
|
149
|
+
// prevent the default action.
|
|
150
|
+
if (this.disabled && this.href) {
|
|
151
|
+
event.stopImmediatePropagation();
|
|
152
|
+
event.preventDefault();
|
|
153
|
+
return;
|
|
154
|
+
}
|
|
155
|
+
|
|
156
|
+
if (!isActivationClick(event) || !this.cardElement) {
|
|
157
|
+
return;
|
|
158
|
+
}
|
|
159
|
+
|
|
160
|
+
this.focus();
|
|
161
|
+
dispatchActivationClick(this.cardElement);
|
|
162
|
+
};
|
|
163
|
+
|
|
164
|
+
__isLink() {
|
|
165
|
+
return !!this.href;
|
|
166
|
+
}
|
|
167
|
+
|
|
168
|
+
__getDisabledReasonID() {
|
|
169
|
+
return this.disabled && this.disabledReason
|
|
170
|
+
? `disabled-reason-${this.#id}`
|
|
171
|
+
: nothing;
|
|
172
|
+
}
|
|
173
|
+
|
|
174
|
+
__renderDisabledReason() {
|
|
175
|
+
const disabledReasonID = this.__getDisabledReasonID();
|
|
176
|
+
if (disabledReasonID)
|
|
177
|
+
return html`<div
|
|
178
|
+
id="disabled-reason-${this.#id}"
|
|
179
|
+
role="tooltip"
|
|
180
|
+
aria-label=${this.disabledReason}
|
|
181
|
+
class="screen-reader-only"
|
|
182
|
+
>
|
|
183
|
+
${this.disabledReason}
|
|
184
|
+
</div>`;
|
|
185
|
+
return nothing;
|
|
186
|
+
}
|
|
187
|
+
|
|
188
|
+
__handlePress = (event: KeyboardEvent | MouseEvent) => {
|
|
189
|
+
if (this.disabled) return;
|
|
190
|
+
if (
|
|
191
|
+
event instanceof KeyboardEvent &&
|
|
192
|
+
event.type === 'keydown' &&
|
|
193
|
+
(event.key === 'Enter' || event.key === ' ')
|
|
194
|
+
) {
|
|
195
|
+
this.isPressed = true;
|
|
196
|
+
} else if (event.type === 'mousedown') {
|
|
197
|
+
this.isPressed = true;
|
|
198
|
+
} else {
|
|
199
|
+
this.isPressed = false;
|
|
200
|
+
}
|
|
201
|
+
};
|
|
202
|
+
|
|
203
|
+
|
|
204
|
+
|
|
34
205
|
|
|
35
206
|
render() {
|
|
36
|
-
|
|
207
|
+
|
|
208
|
+
const isLink = this.__isLink();
|
|
209
|
+
|
|
210
|
+
const cssClasses = {
|
|
211
|
+
card: true,
|
|
212
|
+
'card-element': true,
|
|
213
|
+
[`variant-${this.variant}`]: true,
|
|
214
|
+
actionable: (this.actionable && !this.disabled) || isLink,
|
|
215
|
+
disabled: this.disabled,
|
|
216
|
+
pressed: this.isPressed,
|
|
217
|
+
'has-content': this.slotHasContent,
|
|
218
|
+
};
|
|
219
|
+
|
|
220
|
+
if (!isLink) {
|
|
221
|
+
return html`<button
|
|
222
|
+
class=${classMap(cssClasses)}
|
|
223
|
+
id="button"
|
|
224
|
+
tabindex=${this.#tabindex}
|
|
225
|
+
@click=${this.__dispatchClickWithThrottle}
|
|
226
|
+
@mousedown=${this.__handlePress}
|
|
227
|
+
@keydown=${this.__handlePress}
|
|
228
|
+
@keyup=${this.__handlePress}
|
|
229
|
+
?aria-describedby=${this.__getDisabledReasonID()}
|
|
230
|
+
aria-disabled=${`${this.disabled}`}
|
|
231
|
+
?disabled=${this.disabled}
|
|
232
|
+
>
|
|
233
|
+
${this.renderCardContent()}
|
|
234
|
+
</button>`;
|
|
235
|
+
}
|
|
236
|
+
return html`<a
|
|
237
|
+
class=${classMap(cssClasses)}
|
|
238
|
+
id="button"
|
|
239
|
+
tabindex=${this.#tabindex}
|
|
240
|
+
href=${this.href}
|
|
241
|
+
target=${this.target}
|
|
242
|
+
@click=${this.__dispatchClickWithThrottle}
|
|
243
|
+
@mousedown=${this.__handlePress}
|
|
244
|
+
@keydown=${this.__handlePress}
|
|
245
|
+
@keyup=${this.__handlePress}
|
|
246
|
+
role="button"
|
|
247
|
+
?aria-describedby=${this.__getDisabledReasonID()}
|
|
248
|
+
aria-disabled=${`${this.disabled}`}
|
|
249
|
+
>
|
|
250
|
+
${this.renderCardContent()}
|
|
251
|
+
</a>`;
|
|
252
|
+
}
|
|
253
|
+
|
|
254
|
+
renderCardContent() {
|
|
255
|
+
return html`
|
|
256
|
+
<wc-focus-ring class="focus-ring" .control=${this} .forElement=${this.cardElement}></wc-focus-ring>
|
|
257
|
+
<wc-elevation class="elevation"></wc-elevation>
|
|
258
|
+
<div class="background"></div>
|
|
259
|
+
<div class="outline"></div>
|
|
260
|
+
<wc-ripple class="ripple"></wc-ripple>
|
|
261
|
+
|
|
262
|
+
<div class="card-content">
|
|
263
|
+
|
|
264
|
+
<div class="slot-container">
|
|
265
|
+
<slot @slotchange=${this.__syncSlottedChildrenTabIndex}></slot>
|
|
266
|
+
</div>
|
|
267
|
+
|
|
268
|
+
</div>
|
|
269
|
+
`;
|
|
37
270
|
}
|
|
38
271
|
}
|
package/src/card/index.ts
CHANGED
|
@@ -21,7 +21,7 @@ import styles from './code-editor.scss';
|
|
|
21
21
|
*
|
|
22
22
|
* @example
|
|
23
23
|
* ```html
|
|
24
|
-
* <wc-code-editor language="javascript"></wc-code-editor>
|
|
24
|
+
* <wc-code-editor language="javascript" style="width: 80%;--code-editor-height: 9rem;height: 9rem;" ></wc-code-editor>
|
|
25
25
|
* ```
|
|
26
26
|
*/
|
|
27
27
|
|
|
@@ -16,7 +16,7 @@ type ContainerSize = 'max' | 'xl' | 'lg' | 'md' | 'sm' | 'full';
|
|
|
16
16
|
*
|
|
17
17
|
* @example
|
|
18
18
|
* ```html
|
|
19
|
-
* <wc-container size="
|
|
19
|
+
* <wc-container style="width: 80%; border: 1px dotted black;" size="md">Content</wc-container>
|
|
20
20
|
* ```
|
|
21
21
|
*/
|
|
22
22
|
export class Container extends LitElement {
|
|
@@ -64,6 +64,10 @@
|
|
|
64
64
|
.content {
|
|
65
65
|
width: 50%;
|
|
66
66
|
}
|
|
67
|
+
|
|
68
|
+
.headline {
|
|
69
|
+
@include mixin.get-typography(title-medium);
|
|
70
|
+
}
|
|
67
71
|
}
|
|
68
72
|
}
|
|
69
73
|
|
|
@@ -79,6 +83,10 @@
|
|
|
79
83
|
justify-content: center;
|
|
80
84
|
}
|
|
81
85
|
}
|
|
86
|
+
|
|
87
|
+
.headline {
|
|
88
|
+
@include mixin.get-typography(title-small);
|
|
89
|
+
}
|
|
82
90
|
}
|
|
83
91
|
}
|
|
84
92
|
|
|
@@ -12,7 +12,7 @@ import styles from './empty-state.scss';
|
|
|
12
12
|
*
|
|
13
13
|
* @example
|
|
14
14
|
* ```html
|
|
15
|
-
* <wc-empty-state headline="No items found"></wc-empty-state>
|
|
15
|
+
* <wc-empty-state width="80%" headline="No items found"></wc-empty-state>
|
|
16
16
|
* ```
|
|
17
17
|
*/
|
|
18
18
|
export class EmptyState extends LitElement {
|
|
@@ -52,7 +52,7 @@ export class EmptyState extends LitElement {
|
|
|
52
52
|
|
|
53
53
|
__renderTitle() {
|
|
54
54
|
if (!this.headline) return nothing;
|
|
55
|
-
return html`<div class="
|
|
55
|
+
return html`<div class="headline">${this.headline}</div>`;
|
|
56
56
|
}
|
|
57
57
|
|
|
58
58
|
__renderDescription() {
|
|
@@ -18,7 +18,7 @@ export class FocusRing extends LitElement {
|
|
|
18
18
|
|
|
19
19
|
@property({ type: Boolean, reflect: true }) visible: boolean = false;
|
|
20
20
|
|
|
21
|
-
@property({ type: String})
|
|
21
|
+
@property({ type: String }) for = '';
|
|
22
22
|
|
|
23
23
|
|
|
24
24
|
render() {
|
|
@@ -27,6 +27,8 @@ export class FocusRing extends LitElement {
|
|
|
27
27
|
|
|
28
28
|
_control?: HTMLElement;
|
|
29
29
|
|
|
30
|
+
_focusTarget?: HTMLElement;
|
|
31
|
+
|
|
30
32
|
get control() {
|
|
31
33
|
return this._control || null;
|
|
32
34
|
}
|
|
@@ -39,6 +41,15 @@ export class FocusRing extends LitElement {
|
|
|
39
41
|
}
|
|
40
42
|
}
|
|
41
43
|
|
|
44
|
+
set forElement(value: HTMLElement | null) {
|
|
45
|
+
if (value) {
|
|
46
|
+
this._focusTarget = value;
|
|
47
|
+
this.attach();
|
|
48
|
+
} else {
|
|
49
|
+
this.detach();
|
|
50
|
+
}
|
|
51
|
+
}
|
|
52
|
+
|
|
42
53
|
connectedCallback() {
|
|
43
54
|
super.connectedCallback();
|
|
44
55
|
this.attach();
|
|
@@ -50,8 +61,8 @@ export class FocusRing extends LitElement {
|
|
|
50
61
|
}
|
|
51
62
|
|
|
52
63
|
__focusin() {
|
|
53
|
-
|
|
54
|
-
this.visible =
|
|
64
|
+
const focusTarget = this.__getFocusTarget();
|
|
65
|
+
this.visible = focusTarget?.matches(':focus-visible') ?? false;
|
|
55
66
|
}
|
|
56
67
|
|
|
57
68
|
__focusout() {
|
|
@@ -62,27 +73,34 @@ export class FocusRing extends LitElement {
|
|
|
62
73
|
this.visible = false;
|
|
63
74
|
}
|
|
64
75
|
|
|
76
|
+
__getFocusTarget(): HTMLElement | undefined {
|
|
77
|
+
|
|
78
|
+
if (this._focusTarget) {
|
|
79
|
+
return this._focusTarget;
|
|
80
|
+
}
|
|
81
|
+
|
|
82
|
+
const focusTarget = document.getElementById(this.for);
|
|
83
|
+
if (focusTarget) {
|
|
84
|
+
return focusTarget
|
|
85
|
+
}
|
|
86
|
+
return undefined;
|
|
87
|
+
}
|
|
88
|
+
|
|
65
89
|
attach() {
|
|
66
|
-
|
|
67
|
-
if (
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
this._control[this.element].addEventListener('focusout', this.__focusin.bind(this));
|
|
72
|
-
// @ts-ignore
|
|
73
|
-
this._control[this.element].addEventListener('pointerdown', this.__focusin.bind(this));
|
|
90
|
+
const focusTarget = this.__getFocusTarget();
|
|
91
|
+
if (focusTarget) {
|
|
92
|
+
focusTarget.addEventListener('focusin', this.__focusin.bind(this));
|
|
93
|
+
focusTarget.addEventListener('focusout', this.__focusout.bind(this));
|
|
94
|
+
focusTarget.addEventListener('pointerdown', this.__pointerdown.bind(this));
|
|
74
95
|
}
|
|
75
96
|
}
|
|
76
97
|
|
|
77
98
|
detach() {
|
|
78
|
-
|
|
79
|
-
if (
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
this._control[this.element].removeEventListener('focusout', this.__focusout);
|
|
84
|
-
// @ts-ignore
|
|
85
|
-
this._control[this.element].removeEventListener('pointerdown', this.__pointerdown);
|
|
99
|
+
const focusTarget = this.__getFocusTarget();
|
|
100
|
+
if (focusTarget) {
|
|
101
|
+
focusTarget.removeEventListener('focusin', this.__focusin.bind(this));
|
|
102
|
+
focusTarget.removeEventListener('focusout', this.__focusout.bind(this));
|
|
103
|
+
focusTarget.removeEventListener('pointerdown', this.__pointerdown.bind(this));
|
|
86
104
|
}
|
|
87
105
|
this._control = undefined;
|
|
88
106
|
}
|
package/src/index.ts
CHANGED
|
@@ -5,6 +5,7 @@ export { Divider } from './divider/index.js';
|
|
|
5
5
|
export { Clock } from './clock/index.js';
|
|
6
6
|
export { Elevation } from './elevation/index.js';
|
|
7
7
|
export { Button, ButtonGroup, IconButton } from './button/index.js';
|
|
8
|
+
export { SegmentedButton, SegmentedButtonGroup } from './segmented-button/index.js';
|
|
8
9
|
|
|
9
10
|
export { FocusRing } from './focus-ring/index.js';
|
|
10
11
|
export { Ripple } from './ripple/index.js';
|
|
@@ -37,7 +38,6 @@ export { CodeEditor } from './code-editor/index.js';
|
|
|
37
38
|
export { Image } from './image/index.js';
|
|
38
39
|
export { Tab, TabGroup, TabPanel, Tabs } from './tabs/index.js';
|
|
39
40
|
export { Slider } from './slider/index.js';
|
|
40
|
-
export { ChartDonut } from './chart-donut/index.js';
|
|
41
41
|
export { ChartDoughnut } from './chart-doughnut/index.js';
|
|
42
42
|
export { ChartPie } from './chart-pie/index.js';
|
|
43
43
|
export { ChartBar, ChartStackedBar } from './chart-bar/index.js';
|
|
@@ -46,3 +46,10 @@ export { Pagination } from './pagination/index.js';
|
|
|
46
46
|
export { TreeView, TreeNode } from './tree-view/index.js';
|
|
47
47
|
export { Card } from './card/index.js';
|
|
48
48
|
export { Snackbar } from './snackbar/index.js';
|
|
49
|
+
export { Radio } from './radio/index.js';
|
|
50
|
+
export { BottomSheet } from './bottom-sheet/index.js';
|
|
51
|
+
export { SideSheet } from './side-sheet/index.js';
|
|
52
|
+
export { Select } from './select/index.js';
|
|
53
|
+
export type { SelectOption } from './select/index.js';
|
|
54
|
+
export { SelectOptionElement } from './select/index.js';
|
|
55
|
+
|
package/src/menu/menu/menu.scss
CHANGED
|
@@ -4,23 +4,37 @@
|
|
|
4
4
|
|
|
5
5
|
.menu {
|
|
6
6
|
display: flex;
|
|
7
|
-
position:
|
|
7
|
+
position: fixed;
|
|
8
8
|
z-index: var(--menu-z-index, 1000);
|
|
9
9
|
min-width: 112px;
|
|
10
10
|
padding-block: var(--spacing-050);
|
|
11
|
+
transform-origin: top center;
|
|
12
|
+
|
|
13
|
+
--_menu-enter-duration: var(--duration-medium1, 250ms);
|
|
14
|
+
--_menu-exit-duration: var(--duration-short4, 200ms);
|
|
15
|
+
--_menu-enter-easing: cubic-bezier(0.05, 0.7, 0.1, 1);
|
|
16
|
+
--_menu-exit-easing: cubic-bezier(0.3, 0, 0.8, 0.15);
|
|
17
|
+
|
|
18
|
+
transition-property: opacity, transform, visibility;
|
|
19
|
+
transition-duration: var(--_menu-exit-duration), var(--_menu-exit-duration), 0ms;
|
|
20
|
+
transition-delay: 0ms, 0ms, var(--_menu-exit-duration);
|
|
21
|
+
transition-timing-function: var(--_menu-exit-easing), var(--_menu-exit-easing), linear;
|
|
11
22
|
|
|
12
23
|
&.closed {
|
|
13
|
-
display: none;
|
|
14
24
|
opacity: 0;
|
|
15
25
|
visibility: hidden;
|
|
16
26
|
pointer-events: none;
|
|
27
|
+
transform: translateY(-4px) scale(0.97);
|
|
17
28
|
}
|
|
18
29
|
|
|
19
30
|
&.open {
|
|
20
|
-
display: flex;
|
|
21
31
|
opacity: 1;
|
|
22
32
|
visibility: visible;
|
|
23
33
|
pointer-events: auto;
|
|
34
|
+
transform: translateY(0) scale(1);
|
|
35
|
+
transition-duration: var(--_menu-enter-duration), var(--_menu-enter-duration), 0ms;
|
|
36
|
+
transition-delay: 0ms, 0ms, 0ms;
|
|
37
|
+
transition-timing-function: var(--_menu-enter-easing), var(--_menu-enter-easing), linear;
|
|
24
38
|
}
|
|
25
39
|
|
|
26
40
|
.menu-content {
|
|
@@ -73,6 +87,13 @@
|
|
|
73
87
|
}
|
|
74
88
|
}
|
|
75
89
|
|
|
90
|
+
@media (prefers-reduced-motion: reduce) {
|
|
91
|
+
.menu {
|
|
92
|
+
transition: none;
|
|
93
|
+
transform: none;
|
|
94
|
+
}
|
|
95
|
+
}
|
|
96
|
+
|
|
76
97
|
.menu {
|
|
77
98
|
--_container-shape-start-start: var(--shape-corner-large);
|
|
78
99
|
--_container-shape-start-end: var(--shape-corner-large);
|
package/src/menu/menu/menu.ts
CHANGED
|
@@ -181,7 +181,6 @@ export class Menu extends LitElement {
|
|
|
181
181
|
for (let index = 0; index < enabledItems.length; index += 1) {
|
|
182
182
|
const currentItem = enabledItems[index];
|
|
183
183
|
currentItem.tabIndex = index === this.activeIndex ? 0 : -1;
|
|
184
|
-
currentItem.selected = index === this.activeIndex;
|
|
185
184
|
}
|
|
186
185
|
}
|
|
187
186
|
|
|
@@ -226,10 +225,23 @@ export class Menu extends LitElement {
|
|
|
226
225
|
return this._enabledItems()[0] ?? null;
|
|
227
226
|
}
|
|
228
227
|
|
|
228
|
+
private _ownsKeyboardEvent(event: KeyboardEvent) {
|
|
229
|
+
const path = event.composedPath();
|
|
230
|
+
const ownedItems = this.items;
|
|
231
|
+
|
|
232
|
+
return path.some(target => target instanceof MenuItem && ownedItems.includes(target));
|
|
233
|
+
}
|
|
234
|
+
|
|
229
235
|
private _onItemActivate = (event: Event) => {
|
|
230
236
|
const customEvent = event as CustomEvent<{ item: MenuItem }>;
|
|
237
|
+
const { item } = customEvent.detail;
|
|
238
|
+
const ownedItems = this.items;
|
|
239
|
+
if (!ownedItems.includes(item)) {
|
|
240
|
+
return;
|
|
241
|
+
}
|
|
242
|
+
|
|
231
243
|
const enabledItems = this._enabledItems();
|
|
232
|
-
const nextIndex = enabledItems.indexOf(
|
|
244
|
+
const nextIndex = enabledItems.indexOf(item);
|
|
233
245
|
if (nextIndex >= 0) {
|
|
234
246
|
this.activeIndex = nextIndex;
|
|
235
247
|
this._syncRovingTabIndex();
|
|
@@ -238,10 +250,15 @@ export class Menu extends LitElement {
|
|
|
238
250
|
|
|
239
251
|
private _onItemRequestClose = (event: Event) => {
|
|
240
252
|
const customEvent = event as CustomEvent<{
|
|
253
|
+
item: MenuItem;
|
|
241
254
|
reason: 'click-selection' | 'keydown';
|
|
242
255
|
key?: string;
|
|
243
256
|
}>;
|
|
244
257
|
|
|
258
|
+
if (!this.items.includes(customEvent.detail.item)) {
|
|
259
|
+
return;
|
|
260
|
+
}
|
|
261
|
+
|
|
245
262
|
if (customEvent.defaultPrevented) {
|
|
246
263
|
return;
|
|
247
264
|
}
|
|
@@ -259,6 +276,10 @@ export class Menu extends LitElement {
|
|
|
259
276
|
return;
|
|
260
277
|
}
|
|
261
278
|
|
|
279
|
+
if (!this._ownsKeyboardEvent(event)) {
|
|
280
|
+
return;
|
|
281
|
+
}
|
|
282
|
+
|
|
262
283
|
switch (event.key) {
|
|
263
284
|
case 'ArrowDown':
|
|
264
285
|
event.preventDefault();
|
|
@@ -138,10 +138,6 @@ export class MenuItem extends LitElement {
|
|
|
138
138
|
return !!this.href;
|
|
139
139
|
}
|
|
140
140
|
|
|
141
|
-
get focusTarget() {
|
|
142
|
-
return this;
|
|
143
|
-
}
|
|
144
|
-
|
|
145
141
|
render() {
|
|
146
142
|
const isLink = this.__isLink();
|
|
147
143
|
|
|
@@ -180,11 +176,7 @@ export class MenuItem extends LitElement {
|
|
|
180
176
|
|
|
181
177
|
renderContent() {
|
|
182
178
|
return html`
|
|
183
|
-
<wc-focus-ring
|
|
184
|
-
class="focus-ring"
|
|
185
|
-
.control=${this}
|
|
186
|
-
element="focusTarget"
|
|
187
|
-
></wc-focus-ring>
|
|
179
|
+
<wc-focus-ring class="focus-ring" .control=${this} .forElement=${this}></wc-focus-ring>
|
|
188
180
|
<div class="background"></div>
|
|
189
181
|
<wc-ripple class="ripple"></wc-ripple>
|
|
190
182
|
|
package/src/peacock-loader.ts
CHANGED
|
@@ -11,6 +11,8 @@ import { Divider } from './divider/divider.js';
|
|
|
11
11
|
import { Button } from './button/button/button.js';
|
|
12
12
|
import { ButtonGroup } from './button/button-group/button-group.js';
|
|
13
13
|
import { IconButton } from './button/icon-button/icon-button.js';
|
|
14
|
+
import { SegmentedButton } from './segmented-button/segmented-button.js';
|
|
15
|
+
import { SegmentedButtonGroup } from './segmented-button/segmented-button-group.js';
|
|
14
16
|
import { Input } from './input/input.js';
|
|
15
17
|
import { Field } from './field/field.js';
|
|
16
18
|
import { NumberField } from './number-field/number-field.js';
|
|
@@ -19,6 +21,7 @@ import { TimePicker } from './time-picker/time-picker.js';
|
|
|
19
21
|
import { Textarea } from './textarea/textarea.js';
|
|
20
22
|
import { Switch } from './switch/switch.js';
|
|
21
23
|
import { Checkbox } from './checkbox/checkbox.js';
|
|
24
|
+
import { Radio } from './radio/radio.js';
|
|
22
25
|
|
|
23
26
|
import { Menu } from './menu/menu/menu.js';
|
|
24
27
|
import { MenuItem } from './menu/menu-item/menu-item.js';
|
|
@@ -52,7 +55,12 @@ import { Table } from './table/table.js';
|
|
|
52
55
|
import { Pagination } from './pagination/pagination.js';
|
|
53
56
|
import { TreeView } from './tree-view/tree-view.js';
|
|
54
57
|
import { Card } from './card/card.js';
|
|
58
|
+
import { CardContent } from './card/card-content.js';
|
|
55
59
|
import { Snackbar } from './snackbar/snackbar.js';
|
|
60
|
+
import { BottomSheet } from './bottom-sheet/bottom-sheet.js';
|
|
61
|
+
import { SideSheet } from './side-sheet/side-sheet.js';
|
|
62
|
+
import { Select } from './select/select.js';
|
|
63
|
+
import { SelectOptionElement } from './select/option.js';
|
|
56
64
|
|
|
57
65
|
const distDirectory = `${import.meta.url}/..`;
|
|
58
66
|
await loadCSS(`${distDirectory}/assets/styles.css`);
|
|
@@ -101,6 +109,12 @@ const loaderConfig: LoaderConfig = {
|
|
|
101
109
|
'wc-button-group': {
|
|
102
110
|
CustomElementClass: ButtonGroup,
|
|
103
111
|
},
|
|
112
|
+
'wc-segmented-button': {
|
|
113
|
+
CustomElementClass: SegmentedButton,
|
|
114
|
+
},
|
|
115
|
+
'wc-segmented-button-group': {
|
|
116
|
+
CustomElementClass: SegmentedButtonGroup,
|
|
117
|
+
},
|
|
104
118
|
'wc-divider': {
|
|
105
119
|
CustomElementClass: Divider,
|
|
106
120
|
},
|
|
@@ -140,6 +154,9 @@ const loaderConfig: LoaderConfig = {
|
|
|
140
154
|
'wc-card': {
|
|
141
155
|
CustomElementClass: Card,
|
|
142
156
|
},
|
|
157
|
+
'wc-card-content': {
|
|
158
|
+
CustomElementClass: CardContent,
|
|
159
|
+
},
|
|
143
160
|
'wc-tag': {
|
|
144
161
|
CustomElementClass: Tag,
|
|
145
162
|
},
|
|
@@ -195,6 +212,9 @@ const loaderConfig: LoaderConfig = {
|
|
|
195
212
|
'wc-checkbox': {
|
|
196
213
|
CustomElementClass: Checkbox,
|
|
197
214
|
},
|
|
215
|
+
'wc-radio': {
|
|
216
|
+
CustomElementClass: Radio,
|
|
217
|
+
},
|
|
198
218
|
'wc-spinner': {
|
|
199
219
|
CustomElementClass: Spinner,
|
|
200
220
|
},
|
|
@@ -234,6 +254,18 @@ const loaderConfig: LoaderConfig = {
|
|
|
234
254
|
'wc-snackbar': {
|
|
235
255
|
CustomElementClass: Snackbar,
|
|
236
256
|
},
|
|
257
|
+
'wc-bottom-sheet': {
|
|
258
|
+
CustomElementClass: BottomSheet,
|
|
259
|
+
},
|
|
260
|
+
'wc-side-sheet': {
|
|
261
|
+
CustomElementClass: SideSheet,
|
|
262
|
+
},
|
|
263
|
+
'wc-select': {
|
|
264
|
+
CustomElementClass: Select,
|
|
265
|
+
},
|
|
266
|
+
'wc-option': {
|
|
267
|
+
CustomElementClass: SelectOptionElement,
|
|
268
|
+
},
|
|
237
269
|
'wc-chart-doughnut': {
|
|
238
270
|
importPath: `${distDirectory}/chart-doughnut.js`,
|
|
239
271
|
},
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export { Radio } from './radio.js';
|