@nuvia-ui/components 4.0.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/package.json +27 -0
- package/src/ds-accordion/ds-accordion-item.js +288 -0
- package/src/ds-accordion/ds-accordion-item.stories.js +82 -0
- package/src/ds-accordion/ds-accordion.a11y.test.js +92 -0
- package/src/ds-accordion/ds-accordion.js +68 -0
- package/src/ds-accordion/ds-accordion.stories.js +118 -0
- package/src/ds-accordion/ds-accordion.test.js +146 -0
- package/src/ds-accordion/index.js +2 -0
- package/src/ds-action-bar/ds-action-bar.js +116 -0
- package/src/ds-action-bar/ds-action-bar.stories.js +86 -0
- package/src/ds-action-bar/ds-action-bar.test.js +64 -0
- package/src/ds-action-bar/index.js +1 -0
- package/src/ds-alert/ds-alert.a11y.test.js +151 -0
- package/src/ds-alert/ds-alert.js +223 -0
- package/src/ds-alert/ds-alert.mdx +142 -0
- package/src/ds-alert/ds-alert.stories.js +166 -0
- package/src/ds-alert/ds-alert.test.js +256 -0
- package/src/ds-alert/index.js +1 -0
- package/src/ds-avatar/ds-avatar.a11y.test.js +45 -0
- package/src/ds-avatar/ds-avatar.js +216 -0
- package/src/ds-avatar/ds-avatar.stories.js +120 -0
- package/src/ds-avatar/ds-avatar.test.js +83 -0
- package/src/ds-avatar/index.js +1 -0
- package/src/ds-avatar-extended/ds-avatar-extended.a11y.test.js +29 -0
- package/src/ds-avatar-extended/ds-avatar-extended.js +108 -0
- package/src/ds-avatar-extended/ds-avatar-extended.stories.js +93 -0
- package/src/ds-avatar-extended/ds-avatar-extended.test.js +66 -0
- package/src/ds-avatar-extended/index.js +1 -0
- package/src/ds-banner/ds-banner.a11y.test.js +51 -0
- package/src/ds-banner/ds-banner.js +233 -0
- package/src/ds-banner/ds-banner.stories.js +185 -0
- package/src/ds-banner/ds-banner.test.js +116 -0
- package/src/ds-banner/index.js +1 -0
- package/src/ds-breadcrumb-item/ds-breadcrumb-item.js +135 -0
- package/src/ds-breadcrumb-item/ds-breadcrumb-item.stories.js +49 -0
- package/src/ds-breadcrumb-item/ds-breadcrumb-item.test.js +55 -0
- package/src/ds-breadcrumbs/ds-breadcrumbs.js +194 -0
- package/src/ds-breadcrumbs/ds-breadcrumbs.stories.js +54 -0
- package/src/ds-breadcrumbs/ds-breadcrumbs.test.js +33 -0
- package/src/ds-button/ds-button.a11y.test.js +49 -0
- package/src/ds-button/ds-button.js +205 -0
- package/src/ds-button/ds-button.mdx +141 -0
- package/src/ds-button/ds-button.stories.js +152 -0
- package/src/ds-button/ds-button.test.js +62 -0
- package/src/ds-button/index.js +1 -0
- package/src/ds-button-group/ds-button-group.js +82 -0
- package/src/ds-button-group/ds-button-group.mdx +39 -0
- package/src/ds-button-group/ds-button-group.stories.js +47 -0
- package/src/ds-button-group/ds-button-group.test.js +47 -0
- package/src/ds-button-group/index.js +1 -0
- package/src/ds-checkbox/ds-checkbox.a11y.test.js +79 -0
- package/src/ds-checkbox/ds-checkbox.js +271 -0
- package/src/ds-checkbox/ds-checkbox.stories.js +77 -0
- package/src/ds-checkbox/ds-checkbox.test.js +191 -0
- package/src/ds-checkbox/index.js +1 -0
- package/src/ds-checkbox-group/ds-checkbox-group.a11y.test.js +146 -0
- package/src/ds-checkbox-group/ds-checkbox-group.js +235 -0
- package/src/ds-checkbox-group/ds-checkbox-group.stories.js +210 -0
- package/src/ds-checkbox-group/ds-checkbox-group.test.js +150 -0
- package/src/ds-checkbox-group/index.js +1 -0
- package/src/ds-dialog/ds-dialog.js +466 -0
- package/src/ds-dialog/ds-dialog.stories.js +274 -0
- package/src/ds-dialog/ds-dialog.test.js +441 -0
- package/src/ds-dialog/index.js +1 -0
- package/src/ds-dropdown/ds-dropdown.a11y.test.js +80 -0
- package/src/ds-dropdown/ds-dropdown.js +891 -0
- package/src/ds-dropdown/ds-dropdown.stories.js +259 -0
- package/src/ds-dropdown/ds-dropdown.test.js +268 -0
- package/src/ds-dropdown/index.js +1 -0
- package/src/ds-dropdown-group/ds-dropdown-group.js +55 -0
- package/src/ds-dropdown-panel/ds-dropdown-panel.js +34 -0
- package/src/ds-file-uploaded/ds-file-uploaded.a11y.test.js +40 -0
- package/src/ds-file-uploaded/ds-file-uploaded.js +135 -0
- package/src/ds-file-uploaded/ds-file-uploaded.mdx +33 -0
- package/src/ds-file-uploaded/ds-file-uploaded.stories.js +81 -0
- package/src/ds-file-uploaded/ds-file-uploaded.test.js +85 -0
- package/src/ds-file-uploader/ds-file-uploader.a11y.test.js +61 -0
- package/src/ds-file-uploader/ds-file-uploader.js +442 -0
- package/src/ds-file-uploader/ds-file-uploader.mdx +44 -0
- package/src/ds-file-uploader/ds-file-uploader.stories.js +76 -0
- package/src/ds-file-uploader/ds-file-uploader.test.js +142 -0
- package/src/ds-header/ds-header.a11y.test.js +38 -0
- package/src/ds-header/ds-header.js +149 -0
- package/src/ds-header/ds-header.stories.js +63 -0
- package/src/ds-header/ds-header.test.js +52 -0
- package/src/ds-header/index.js +1 -0
- package/src/ds-header-nav/ds-header-nav.a11y.test.js +69 -0
- package/src/ds-header-nav/ds-header-nav.js +114 -0
- package/src/ds-header-nav/ds-header-nav.stories.js +17 -0
- package/src/ds-header-nav/ds-header-nav.test.js +93 -0
- package/src/ds-header-nav-item/ds-header-nav-item.a11y.test.js +71 -0
- package/src/ds-header-nav-item/ds-header-nav-item.js +124 -0
- package/src/ds-header-nav-item/ds-header-nav-item.stories.js +43 -0
- package/src/ds-header-nav-item/ds-header-nav-item.test.js +61 -0
- package/src/ds-icon/ds-icon.a11y.test.js +49 -0
- package/src/ds-icon/ds-icon.js +75 -0
- package/src/ds-icon/ds-icon.mdx +36 -0
- package/src/ds-icon/ds-icon.stories.js +88 -0
- package/src/ds-icon/ds-icon.test.js +97 -0
- package/src/ds-icon/index.js +1 -0
- package/src/ds-icon-button/ds-icon-button.a11y.test.js +55 -0
- package/src/ds-icon-button/ds-icon-button.js +224 -0
- package/src/ds-icon-button/ds-icon-button.mdx +131 -0
- package/src/ds-icon-button/ds-icon-button.stories.js +128 -0
- package/src/ds-icon-button/ds-icon-button.test.js +90 -0
- package/src/ds-icon-button/index.js +1 -0
- package/src/ds-input/ds-input.a11y.test.js +145 -0
- package/src/ds-input/ds-input.js +645 -0
- package/src/ds-input/ds-input.mdx +251 -0
- package/src/ds-input/ds-input.stories.js +298 -0
- package/src/ds-input/ds-input.test.js +792 -0
- package/src/ds-input/index.js +1 -0
- package/src/ds-link/ds-link.js +111 -0
- package/src/ds-link/ds-link.stories.js +56 -0
- package/src/ds-link/ds-link.test.js +74 -0
- package/src/ds-list-item/ds-list-item.a11y.test.js +39 -0
- package/src/ds-list-item/ds-list-item.js +292 -0
- package/src/ds-list-item/ds-list-item.stories.js +101 -0
- package/src/ds-list-item/ds-list-item.test.js +63 -0
- package/src/ds-menu/ds-menu.js +30 -0
- package/src/ds-menu/ds-menu.stories.js +120 -0
- package/src/ds-menu/ds-menu.test.js +123 -0
- package/src/ds-menu-group/ds-menu-group.js +101 -0
- package/src/ds-menu-group/ds-menu-group.stories.js +99 -0
- package/src/ds-nav-item/ds-nav-item.a11y.test.js +91 -0
- package/src/ds-nav-item/ds-nav-item.js +307 -0
- package/src/ds-nav-item/ds-nav-item.stories.js +99 -0
- package/src/ds-nav-item/ds-nav-item.test.js +169 -0
- package/src/ds-nav-item/index.js +1 -0
- package/src/ds-nav-vertical/ds-nav-vertical.a11y.test.js +69 -0
- package/src/ds-nav-vertical/ds-nav-vertical.js +173 -0
- package/src/ds-nav-vertical/ds-nav-vertical.stories.js +124 -0
- package/src/ds-nav-vertical/ds-nav-vertical.test.js +176 -0
- package/src/ds-nav-vertical/index.js +1 -0
- package/src/ds-pagination/ds-pagination.a11y.test.js +50 -0
- package/src/ds-pagination/ds-pagination.js +232 -0
- package/src/ds-pagination/ds-pagination.stories.js +63 -0
- package/src/ds-pagination/ds-pagination.test.js +141 -0
- package/src/ds-pagination/index.js +1 -0
- package/src/ds-progress-bar/ds-progress-bar.a11y.test.js +25 -0
- package/src/ds-progress-bar/ds-progress-bar.js +81 -0
- package/src/ds-progress-bar/ds-progress-bar.stories.js +69 -0
- package/src/ds-progress-bar/ds-progress-bar.test.js +60 -0
- package/src/ds-radio/ds-radio.a11y.test.js +69 -0
- package/src/ds-radio/ds-radio.js +240 -0
- package/src/ds-radio/ds-radio.stories.js +102 -0
- package/src/ds-radio/ds-radio.test.js +114 -0
- package/src/ds-radio/index.js +1 -0
- package/src/ds-radio-group/ds-radio-group.a11y.test.js +164 -0
- package/src/ds-radio-group/ds-radio-group.js +257 -0
- package/src/ds-radio-group/ds-radio-group.stories.js +247 -0
- package/src/ds-radio-group/ds-radio-group.test.js +194 -0
- package/src/ds-radio-group/index.js +1 -0
- package/src/ds-rich-list/ds-rich-list.js +246 -0
- package/src/ds-rich-list/ds-rich-list.stories.js +368 -0
- package/src/ds-rich-list/ds-rich-list.test.js +293 -0
- package/src/ds-rich-list-item/ds-rich-list-item.js +579 -0
- package/src/ds-rich-list-item/ds-rich-list-item.stories.js +197 -0
- package/src/ds-rich-list-item/ds-rich-list-item.test.js +434 -0
- package/src/ds-slider/ds-slider.js +399 -0
- package/src/ds-slider/ds-slider.stories.js +107 -0
- package/src/ds-slider/ds-slider.test.js +308 -0
- package/src/ds-spinner/ds-spinner.js +173 -0
- package/src/ds-spinner/ds-spinner.stories.js +52 -0
- package/src/ds-spinner/ds-spinner.test.js +50 -0
- package/src/ds-status-border/ds-status-border.js +88 -0
- package/src/ds-status-border/ds-status-border.stories.js +242 -0
- package/src/ds-status-border/ds-status-border.test.js +168 -0
- package/src/ds-stepper/ds-stepper.a11y.test.js +198 -0
- package/src/ds-stepper/ds-stepper.js +207 -0
- package/src/ds-stepper/ds-stepper.stories.js +530 -0
- package/src/ds-stepper/ds-stepper.test.js +311 -0
- package/src/ds-stepper-item/ds-stepper-item.js +485 -0
- package/src/ds-stepper-item/ds-stepper-item.stories.js +288 -0
- package/src/ds-switch/ds-switch.js +348 -0
- package/src/ds-switch/ds-switch.stories.js +145 -0
- package/src/ds-switch/ds-switch.test.js +226 -0
- package/src/ds-switch/index.js +1 -0
- package/src/ds-tab-item/ds-tab-item.js +341 -0
- package/src/ds-tab-item/ds-tab-item.stories.js +69 -0
- package/src/ds-tabs/ds-tab-panel.js +48 -0
- package/src/ds-tabs/ds-tabs.a11y.test.js +56 -0
- package/src/ds-tabs/ds-tabs.js +180 -0
- package/src/ds-tabs/ds-tabs.stories.js +152 -0
- package/src/ds-tabs/ds-tabs.test.js +306 -0
- package/src/ds-tabs/index.js +3 -0
- package/src/ds-tag-action/ds-tag-action.a11y.test.js +32 -0
- package/src/ds-tag-action/ds-tag-action.js +185 -0
- package/src/ds-tag-action/ds-tag-action.stories.js +55 -0
- package/src/ds-tag-action/ds-tag-action.test.js +44 -0
- package/src/ds-tag-removable/ds-tag-removable.a11y.test.js +24 -0
- package/src/ds-tag-removable/ds-tag-removable.js +146 -0
- package/src/ds-tag-removable/ds-tag-removable.stories.js +52 -0
- package/src/ds-tag-removable/ds-tag-removable.test.js +46 -0
- package/src/ds-tag-status/ds-tag-status.a11y.test.js +93 -0
- package/src/ds-tag-status/ds-tag-status.js +164 -0
- package/src/ds-tag-status/ds-tag-status.stories.js +200 -0
- package/src/ds-tag-status/ds-tag-status.test.js +140 -0
- package/src/ds-tag-status/index.js +1 -0
- package/src/ds-textarea/ds-textarea-clearable.test.js +89 -0
- package/src/ds-textarea/ds-textarea.a11y.test.js +66 -0
- package/src/ds-textarea/ds-textarea.js +505 -0
- package/src/ds-textarea/ds-textarea.stories.js +335 -0
- package/src/ds-textarea/ds-textarea.test.js +218 -0
- package/src/ds-textarea/index.js +1 -0
- package/src/ds-thumbnail/ds-thumbnail.js +207 -0
- package/src/ds-thumbnail/ds-thumbnail.stories.js +217 -0
- package/src/ds-thumbnail/ds-thumbnail.test.js +220 -0
- package/src/ds-toast/ds-toast-provider.js +110 -0
- package/src/ds-toast/ds-toast.a11y.test.js +34 -0
- package/src/ds-toast/ds-toast.js +243 -0
- package/src/ds-toast/ds-toast.stories.js +143 -0
- package/src/ds-toast/ds-toast.test.js +93 -0
- package/src/ds-toast/index.js +2 -0
- package/src/ds-tooltip/ds-tooltip.a11y.test.js +110 -0
- package/src/ds-tooltip/ds-tooltip.js +217 -0
- package/src/ds-tooltip/ds-tooltip.mdx +75 -0
- package/src/ds-tooltip/ds-tooltip.stories.js +72 -0
- package/src/ds-tooltip/ds-tooltip.test.js +191 -0
- package/src/ds-tooltip/index.js +1 -0
- package/src/ds-tooltip/positioner.js +117 -0
- package/src/index.js +50 -0
- package/src/mixins/field-label.mixin.js +113 -0
- package/src/mixins/field-message.mixin.js +66 -0
- package/src/token-provider/index.js +1 -0
- package/src/token-provider/token-provider.a11y.test.js +44 -0
- package/src/token-provider/token-provider.js +85 -0
- package/src/token-provider/token-provider.stories.js +105 -0
- package/src/token-provider/token-provider.test.js +134 -0
- package/src/utils/number-input.utils.js +42 -0
|
@@ -0,0 +1,145 @@
|
|
|
1
|
+
import './ds-switch.js';
|
|
2
|
+
|
|
3
|
+
export default {
|
|
4
|
+
title: 'Components/Switch',
|
|
5
|
+
component: 'ds-switch',
|
|
6
|
+
tags: ['autodocs'],
|
|
7
|
+
argTypes: {
|
|
8
|
+
checked: { control: 'boolean' },
|
|
9
|
+
disabled: { control: 'boolean' },
|
|
10
|
+
label: { control: 'text', description: 'Block-level field label (above switch)' },
|
|
11
|
+
info: { control: 'text', description: 'Info tooltip text' },
|
|
12
|
+
statusLabel: { control: 'text', description: 'Inline state description next to track' },
|
|
13
|
+
helpText: { control: 'text', description: 'Helper text below switch' },
|
|
14
|
+
errorText: { control: 'text', description: 'Error text (shown when validationStatus="error")' },
|
|
15
|
+
standalone: { control: 'boolean' },
|
|
16
|
+
required: { control: 'boolean' },
|
|
17
|
+
validationStatus: {
|
|
18
|
+
control: 'select',
|
|
19
|
+
options: [undefined, 'error'],
|
|
20
|
+
description: 'Validation state of the switch'
|
|
21
|
+
},
|
|
22
|
+
labelPosition: {
|
|
23
|
+
control: 'select',
|
|
24
|
+
options: ['top', 'inline-start']
|
|
25
|
+
},
|
|
26
|
+
labelWidth: { control: 'text' }
|
|
27
|
+
}
|
|
28
|
+
};
|
|
29
|
+
|
|
30
|
+
const Template = (args) => {
|
|
31
|
+
const el = document.createElement('ds-switch');
|
|
32
|
+
Object.keys(args).forEach(key => {
|
|
33
|
+
// Convert camelCase to kebab-case for attributes
|
|
34
|
+
const attrName = key.replace(/([a-z0-9])([A-Z])/g, '$1-$2').toLowerCase();
|
|
35
|
+
|
|
36
|
+
if (args[key] !== undefined && args[key] !== null) {
|
|
37
|
+
if (typeof args[key] === 'boolean') {
|
|
38
|
+
if (args[key]) el.setAttribute(attrName, '');
|
|
39
|
+
else el.removeAttribute(attrName);
|
|
40
|
+
} else {
|
|
41
|
+
el.setAttribute(attrName, args[key]);
|
|
42
|
+
}
|
|
43
|
+
}
|
|
44
|
+
});
|
|
45
|
+
return el;
|
|
46
|
+
};
|
|
47
|
+
|
|
48
|
+
export const Default = Template.bind({});
|
|
49
|
+
Default.args = {
|
|
50
|
+
statusLabel: 'Toggle setting'
|
|
51
|
+
};
|
|
52
|
+
|
|
53
|
+
export const InlineLabel = Template.bind({});
|
|
54
|
+
InlineLabel.args = {
|
|
55
|
+
label: 'Setting',
|
|
56
|
+
labelPosition: 'inline-start',
|
|
57
|
+
labelWidth: '150px',
|
|
58
|
+
statusLabel: 'Enabled',
|
|
59
|
+
checked: true,
|
|
60
|
+
info: 'This label is positioned inline'
|
|
61
|
+
};
|
|
62
|
+
|
|
63
|
+
export const Checked = Template.bind({});
|
|
64
|
+
Checked.args = {
|
|
65
|
+
statusLabel: 'Active state',
|
|
66
|
+
checked: true
|
|
67
|
+
};
|
|
68
|
+
|
|
69
|
+
export const WithLabel = Template.bind({});
|
|
70
|
+
WithLabel.args = {
|
|
71
|
+
label: 'Notificações',
|
|
72
|
+
statusLabel: 'Ativado',
|
|
73
|
+
checked: true
|
|
74
|
+
};
|
|
75
|
+
|
|
76
|
+
export const WithLabelAndInfo = Template.bind({});
|
|
77
|
+
WithLabelAndInfo.args = {
|
|
78
|
+
label: 'Notificações por Email',
|
|
79
|
+
info: 'Recebe alertas e novidades na tua caixa de entrada',
|
|
80
|
+
statusLabel: 'Ativado',
|
|
81
|
+
checked: true
|
|
82
|
+
};
|
|
83
|
+
|
|
84
|
+
export const WithHelpText = Template.bind({});
|
|
85
|
+
WithHelpText.args = {
|
|
86
|
+
label: 'Marketing',
|
|
87
|
+
statusLabel: 'Ativado',
|
|
88
|
+
helpText: 'Recebe promoções e ofertas especiais',
|
|
89
|
+
checked: true
|
|
90
|
+
};
|
|
91
|
+
|
|
92
|
+
export const WithErrorText = Template.bind({});
|
|
93
|
+
WithErrorText.args = {
|
|
94
|
+
label: 'Termos e Condições',
|
|
95
|
+
statusLabel: 'Desativado',
|
|
96
|
+
errorText: 'Deves aceitar os termos para continuar',
|
|
97
|
+
validationStatus: 'error'
|
|
98
|
+
};
|
|
99
|
+
|
|
100
|
+
export const Disabled = Template.bind({});
|
|
101
|
+
Disabled.args = {
|
|
102
|
+
statusLabel: 'Disabled switch',
|
|
103
|
+
disabled: true
|
|
104
|
+
};
|
|
105
|
+
|
|
106
|
+
export const DisabledChecked = Template.bind({});
|
|
107
|
+
DisabledChecked.args = {
|
|
108
|
+
statusLabel: 'Disabled active switch',
|
|
109
|
+
disabled: true,
|
|
110
|
+
checked: true
|
|
111
|
+
};
|
|
112
|
+
|
|
113
|
+
export const Standalone = Template.bind({});
|
|
114
|
+
Standalone.args = {
|
|
115
|
+
standalone: true,
|
|
116
|
+
checked: true
|
|
117
|
+
};
|
|
118
|
+
|
|
119
|
+
export const LongLabel = Template.bind({});
|
|
120
|
+
LongLabel.args = {
|
|
121
|
+
statusLabel: 'This is a switch with a very long label that demonstrates how it aligns with the track in multiline scenarios'
|
|
122
|
+
};
|
|
123
|
+
LongLabel.decorators = [
|
|
124
|
+
(Story) => {
|
|
125
|
+
const div = document.createElement('div');
|
|
126
|
+
div.style.width = '200px';
|
|
127
|
+
div.appendChild(Story());
|
|
128
|
+
return div;
|
|
129
|
+
}
|
|
130
|
+
];
|
|
131
|
+
|
|
132
|
+
export const ErrorUnchecked = Template.bind({});
|
|
133
|
+
ErrorUnchecked.args = {
|
|
134
|
+
statusLabel: 'Error state (unchecked)',
|
|
135
|
+
validationStatus: 'error',
|
|
136
|
+
errorText: 'Este campo é obrigatório'
|
|
137
|
+
};
|
|
138
|
+
|
|
139
|
+
export const ErrorChecked = Template.bind({});
|
|
140
|
+
ErrorChecked.args = {
|
|
141
|
+
statusLabel: 'Error state (checked)',
|
|
142
|
+
validationStatus: 'error',
|
|
143
|
+
errorText: 'Valor inválido selecionado',
|
|
144
|
+
checked: true
|
|
145
|
+
};
|
|
@@ -0,0 +1,226 @@
|
|
|
1
|
+
import { describe, it, expect, beforeEach, afterEach } from 'vitest';
|
|
2
|
+
import './ds-switch.js';
|
|
3
|
+
|
|
4
|
+
describe('ds-switch', () => {
|
|
5
|
+
let container;
|
|
6
|
+
|
|
7
|
+
beforeEach(() => {
|
|
8
|
+
container = document.createElement('div');
|
|
9
|
+
document.body.appendChild(container);
|
|
10
|
+
});
|
|
11
|
+
|
|
12
|
+
afterEach(() => {
|
|
13
|
+
container.remove();
|
|
14
|
+
});
|
|
15
|
+
|
|
16
|
+
it('renders with default values', async () => {
|
|
17
|
+
container.innerHTML = '<ds-switch></ds-switch>';
|
|
18
|
+
const element = container.querySelector('ds-switch');
|
|
19
|
+
await new Promise(resolve => setTimeout(resolve, 0));
|
|
20
|
+
|
|
21
|
+
expect(element.checked).toBe(false);
|
|
22
|
+
expect(element.disabled).toBe(false);
|
|
23
|
+
|
|
24
|
+
const input = element.shadowRoot.querySelector('input');
|
|
25
|
+
expect(input.getAttribute('role')).toBe('switch');
|
|
26
|
+
});
|
|
27
|
+
|
|
28
|
+
it('renders statusLabel when provided', async () => {
|
|
29
|
+
container.innerHTML = '<ds-switch status-label="Test Label"></ds-switch>';
|
|
30
|
+
const element = container.querySelector('ds-switch');
|
|
31
|
+
await new Promise(resolve => setTimeout(resolve, 0));
|
|
32
|
+
|
|
33
|
+
const statusLabel = element.shadowRoot.querySelector('.status-label');
|
|
34
|
+
expect(statusLabel).toBeTruthy();
|
|
35
|
+
expect(statusLabel.textContent).toBe('Test Label');
|
|
36
|
+
});
|
|
37
|
+
|
|
38
|
+
it('renders block-level label when provided', async () => {
|
|
39
|
+
container.innerHTML = '<ds-switch label="Field Label"></ds-switch>';
|
|
40
|
+
const element = container.querySelector('ds-switch');
|
|
41
|
+
await new Promise(resolve => setTimeout(resolve, 0));
|
|
42
|
+
|
|
43
|
+
const labelRow = element.shadowRoot.querySelector('.label-row');
|
|
44
|
+
expect(labelRow).toBeTruthy();
|
|
45
|
+
const label = labelRow.querySelector('label');
|
|
46
|
+
expect(label.textContent).toBe('Field Label');
|
|
47
|
+
});
|
|
48
|
+
|
|
49
|
+
it('renders helpText when provided', async () => {
|
|
50
|
+
container.innerHTML = '<ds-switch help-text="Some help text"></ds-switch>';
|
|
51
|
+
const element = container.querySelector('ds-switch');
|
|
52
|
+
await new Promise(resolve => setTimeout(resolve, 0));
|
|
53
|
+
|
|
54
|
+
const message = element.shadowRoot.querySelector('.field-message');
|
|
55
|
+
expect(message).toBeTruthy();
|
|
56
|
+
expect(message.textContent).toContain('Some help text');
|
|
57
|
+
});
|
|
58
|
+
|
|
59
|
+
it('renders errorText only when validationStatus is error', async () => {
|
|
60
|
+
container.innerHTML = '<ds-switch error-text="Error msg" validation-status="error"></ds-switch>';
|
|
61
|
+
const element = container.querySelector('ds-switch');
|
|
62
|
+
await new Promise(resolve => setTimeout(resolve, 0));
|
|
63
|
+
|
|
64
|
+
const message = element.shadowRoot.querySelector('.field-message--error');
|
|
65
|
+
expect(message).toBeTruthy();
|
|
66
|
+
expect(message.textContent).toContain('Error msg');
|
|
67
|
+
});
|
|
68
|
+
|
|
69
|
+
it('does not render errorText when validationStatus is not error', async () => {
|
|
70
|
+
container.innerHTML = '<ds-switch error-text="Error msg"></ds-switch>';
|
|
71
|
+
const element = container.querySelector('ds-switch');
|
|
72
|
+
await new Promise(resolve => setTimeout(resolve, 0));
|
|
73
|
+
|
|
74
|
+
const errorMessage = element.shadowRoot.querySelector('.field-message--error');
|
|
75
|
+
expect(errorMessage).toBeFalsy();
|
|
76
|
+
});
|
|
77
|
+
|
|
78
|
+
it('reflects checked property to attribute and aria-checked', async () => {
|
|
79
|
+
container.innerHTML = '<ds-switch checked></ds-switch>';
|
|
80
|
+
const element = container.querySelector('ds-switch');
|
|
81
|
+
await new Promise(resolve => setTimeout(resolve, 0));
|
|
82
|
+
|
|
83
|
+
expect(element.hasAttribute('checked')).toBe(true);
|
|
84
|
+
const input = element.shadowRoot.querySelector('input');
|
|
85
|
+
expect(input.checked).toBe(true);
|
|
86
|
+
expect(input.getAttribute('aria-checked')).toBe('true');
|
|
87
|
+
});
|
|
88
|
+
|
|
89
|
+
it('handles click events to toggle state', async () => {
|
|
90
|
+
container.innerHTML = '<ds-switch></ds-switch>';
|
|
91
|
+
const element = container.querySelector('ds-switch');
|
|
92
|
+
await new Promise(resolve => setTimeout(resolve, 0));
|
|
93
|
+
|
|
94
|
+
const wrapper = element.shadowRoot.querySelector('.switch-row');
|
|
95
|
+
|
|
96
|
+
// Click to check
|
|
97
|
+
wrapper.click();
|
|
98
|
+
await new Promise(resolve => setTimeout(resolve, 0));
|
|
99
|
+
expect(element.checked).toBe(true);
|
|
100
|
+
|
|
101
|
+
// Click to uncheck
|
|
102
|
+
wrapper.click();
|
|
103
|
+
await new Promise(resolve => setTimeout(resolve, 0));
|
|
104
|
+
expect(element.checked).toBe(false);
|
|
105
|
+
});
|
|
106
|
+
|
|
107
|
+
it('dispatches change event on interaction', async () => {
|
|
108
|
+
container.innerHTML = '<ds-switch></ds-switch>';
|
|
109
|
+
const element = container.querySelector('ds-switch');
|
|
110
|
+
await new Promise(resolve => setTimeout(resolve, 0));
|
|
111
|
+
|
|
112
|
+
const wrapper = element.shadowRoot.querySelector('.switch-row');
|
|
113
|
+
|
|
114
|
+
let eventFired = false;
|
|
115
|
+
let eventDetail = null;
|
|
116
|
+
|
|
117
|
+
element.addEventListener('change', (e) => {
|
|
118
|
+
eventFired = true;
|
|
119
|
+
eventDetail = e.detail;
|
|
120
|
+
});
|
|
121
|
+
|
|
122
|
+
wrapper.click();
|
|
123
|
+
await new Promise(resolve => setTimeout(resolve, 0));
|
|
124
|
+
|
|
125
|
+
expect(eventFired).toBe(true);
|
|
126
|
+
expect(eventDetail.checked).toBe(true);
|
|
127
|
+
});
|
|
128
|
+
|
|
129
|
+
it('does not toggle when disabled', async () => {
|
|
130
|
+
container.innerHTML = '<ds-switch disabled></ds-switch>';
|
|
131
|
+
const element = container.querySelector('ds-switch');
|
|
132
|
+
await new Promise(resolve => setTimeout(resolve, 0));
|
|
133
|
+
|
|
134
|
+
const wrapper = element.shadowRoot.querySelector('.switch-row');
|
|
135
|
+
|
|
136
|
+
wrapper.click();
|
|
137
|
+
await new Promise(resolve => setTimeout(resolve, 0));
|
|
138
|
+
|
|
139
|
+
expect(element.checked).toBe(false);
|
|
140
|
+
});
|
|
141
|
+
|
|
142
|
+
it('sets name and value on internal input', async () => {
|
|
143
|
+
container.innerHTML = '<ds-switch name="test-switch" value="yes"></ds-switch>';
|
|
144
|
+
const element = container.querySelector('ds-switch');
|
|
145
|
+
await new Promise(resolve => setTimeout(resolve, 0));
|
|
146
|
+
|
|
147
|
+
const input = element.shadowRoot.querySelector('input');
|
|
148
|
+
expect(input.name).toBe('test-switch');
|
|
149
|
+
expect(input.value).toBe('yes');
|
|
150
|
+
});
|
|
151
|
+
|
|
152
|
+
it('uses aria-label from host if provided', async () => {
|
|
153
|
+
container.innerHTML = '<ds-switch aria-label="Toggle dark mode"></ds-switch>';
|
|
154
|
+
const element = container.querySelector('ds-switch');
|
|
155
|
+
await new Promise(resolve => setTimeout(resolve, 0));
|
|
156
|
+
|
|
157
|
+
const input = element.shadowRoot.querySelector('input');
|
|
158
|
+
expect(input.getAttribute('aria-label')).toBe('Toggle dark mode');
|
|
159
|
+
});
|
|
160
|
+
|
|
161
|
+
|
|
162
|
+
it('reflects validationStatus property to attribute', async () => {
|
|
163
|
+
container.innerHTML = '<ds-switch validation-status="error"></ds-switch>';
|
|
164
|
+
const element = container.querySelector('ds-switch');
|
|
165
|
+
await new Promise(resolve => setTimeout(resolve, 0));
|
|
166
|
+
|
|
167
|
+
expect(element.getAttribute('validation-status')).toBe('error');
|
|
168
|
+
expect(element.validationStatus).toBe('error');
|
|
169
|
+
});
|
|
170
|
+
|
|
171
|
+
it('toggle() method inverts checked state', async () => {
|
|
172
|
+
container.innerHTML = '<ds-switch></ds-switch>';
|
|
173
|
+
const element = container.querySelector('ds-switch');
|
|
174
|
+
await new Promise(resolve => setTimeout(resolve, 0));
|
|
175
|
+
|
|
176
|
+
expect(element.checked).toBe(false);
|
|
177
|
+
|
|
178
|
+
element.toggle();
|
|
179
|
+
await new Promise(resolve => setTimeout(resolve, 0));
|
|
180
|
+
expect(element.checked).toBe(true);
|
|
181
|
+
|
|
182
|
+
element.toggle();
|
|
183
|
+
await new Promise(resolve => setTimeout(resolve, 0));
|
|
184
|
+
expect(element.checked).toBe(false);
|
|
185
|
+
});
|
|
186
|
+
|
|
187
|
+
it('toggle() does not work when disabled', async () => {
|
|
188
|
+
container.innerHTML = '<ds-switch disabled></ds-switch>';
|
|
189
|
+
const element = container.querySelector('ds-switch');
|
|
190
|
+
await new Promise(resolve => setTimeout(resolve, 0));
|
|
191
|
+
|
|
192
|
+
element.toggle();
|
|
193
|
+
await new Promise(resolve => setTimeout(resolve, 0));
|
|
194
|
+
|
|
195
|
+
expect(element.checked).toBe(false);
|
|
196
|
+
});
|
|
197
|
+
|
|
198
|
+
it('toggle() dispatches change event', async () => {
|
|
199
|
+
container.innerHTML = '<ds-switch></ds-switch>';
|
|
200
|
+
const element = container.querySelector('ds-switch');
|
|
201
|
+
await new Promise(resolve => setTimeout(resolve, 0));
|
|
202
|
+
|
|
203
|
+
let eventFired = false;
|
|
204
|
+
element.addEventListener('change', () => {
|
|
205
|
+
eventFired = true;
|
|
206
|
+
});
|
|
207
|
+
|
|
208
|
+
element.toggle();
|
|
209
|
+
await new Promise(resolve => setTimeout(resolve, 0));
|
|
210
|
+
|
|
211
|
+
expect(eventFired).toBe(true);
|
|
212
|
+
});
|
|
213
|
+
|
|
214
|
+
it('focus() method focuses the input', async () => {
|
|
215
|
+
container.innerHTML = '<ds-switch></ds-switch>';
|
|
216
|
+
const element = container.querySelector('ds-switch');
|
|
217
|
+
await new Promise(resolve => setTimeout(resolve, 0));
|
|
218
|
+
|
|
219
|
+
element.focus();
|
|
220
|
+
await new Promise(resolve => setTimeout(resolve, 0));
|
|
221
|
+
|
|
222
|
+
const input = element.shadowRoot.querySelector('input');
|
|
223
|
+
expect(document.activeElement).toBe(element);
|
|
224
|
+
expect(element.shadowRoot.activeElement).toBe(input);
|
|
225
|
+
});
|
|
226
|
+
});
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export { DsSwitch } from './ds-switch.js';
|