@geoffcox/sterling-svelte 0.0.26 → 0.0.28
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/Button.svelte +81 -25
- package/Button.svelte.d.ts +3 -0
- package/Checkbox.svelte +56 -26
- package/Checkbox.svelte.d.ts +2 -0
- package/ColorPicker.constants.d.ts +1 -0
- package/ColorPicker.constants.js +1 -0
- package/ColorPicker.svelte +257 -0
- package/ColorPicker.svelte.d.ts +49 -0
- package/ColorPicker.types.d.ts +4 -0
- package/Dialog.svelte +10 -10
- package/Dropdown.svelte +97 -58
- package/Dropdown.svelte.d.ts +4 -0
- package/HexColorSliders.svelte +171 -0
- package/HexColorSliders.svelte.d.ts +22 -0
- package/HslColorSliders.svelte +208 -0
- package/HslColorSliders.svelte.d.ts +22 -0
- package/Input.svelte +59 -25
- package/Input.svelte.d.ts +3 -2
- package/Label.constants.d.ts +1 -0
- package/Label.constants.js +1 -0
- package/Label.svelte +212 -14
- package/Label.svelte.d.ts +24 -4
- package/Label.types.d.ts +4 -0
- package/Label.types.js +1 -0
- package/Link.svelte +62 -16
- package/Link.svelte.d.ts +1 -0
- package/List.svelte +29 -16
- package/List.svelte.d.ts +1 -0
- package/List.types.d.ts +4 -3
- package/ListItem.svelte +30 -10
- package/ListItem.svelte.d.ts +1 -1
- package/Menu.svelte +7 -7
- package/MenuBar.svelte +1 -1
- package/MenuButton.svelte +3 -9
- package/MenuButton.svelte.d.ts +2 -4
- package/MenuItem.svelte +34 -12
- package/MenuItem.svelte.d.ts +2 -1
- package/MenuItemDisplay.svelte +8 -1
- package/MenuSeparator.svelte +3 -3
- package/Popover.svelte +66 -51
- package/Popover.svelte.d.ts +4 -2
- package/Progress.constants.d.ts +1 -1
- package/Progress.constants.js +1 -1
- package/Progress.svelte +34 -28
- package/Progress.svelte.d.ts +1 -1
- package/Progress.types.d.ts +3 -3
- package/Radio.svelte +54 -23
- package/Radio.svelte.d.ts +2 -0
- package/RgbColorSliders.svelte +182 -0
- package/RgbColorSliders.svelte.d.ts +22 -0
- package/Select.svelte +32 -25
- package/Select.svelte.d.ts +1 -1
- package/Slider.svelte +111 -123
- package/Slider.svelte.d.ts +1 -0
- package/Switch.svelte +112 -41
- package/Switch.svelte.d.ts +3 -2
- package/Tab.svelte +53 -29
- package/Tab.svelte.d.ts +7 -4
- package/TabList.svelte +21 -11
- package/TabList.svelte.d.ts +1 -0
- package/TabList.types.d.ts +1 -0
- package/TextArea.svelte +48 -22
- package/TextArea.svelte.d.ts +4 -3
- package/Tooltip.svelte +59 -16
- package/Tooltip.svelte.d.ts +34 -2
- package/Tree.svelte +35 -21
- package/Tree.svelte.d.ts +2 -0
- package/Tree.types.d.ts +6 -8
- package/TreeChevron.svelte +1 -1
- package/TreeItem.svelte +40 -9
- package/TreeItem.svelte.d.ts +2 -0
- package/TreeItem.types.d.ts +4 -4
- package/TreeItemDisplay.svelte +28 -9
- package/TreeItemDisplay.svelte.d.ts +3 -1
- package/actions/clickOutside.js +1 -1
- package/actions/trapKeyboardFocus.d.ts +3 -0
- package/actions/trapKeyboardFocus.js +52 -0
- package/floating-ui.types.d.ts +2 -0
- package/index.d.ts +14 -10
- package/index.js +11 -7
- package/package.json +12 -4
- package/theme/applyTheme.js +3 -2
- package/theme/colors.d.ts +1 -0
- package/theme/colors.js +28 -13
- package/theme/darkTheme.js +129 -87
- package/theme/lightTheme.js +109 -90
- package/Field.constants.d.ts +0 -1
- package/Field.constants.js +0 -1
- package/Field.svelte +0 -265
- package/Field.svelte.d.ts +0 -75
- package/Field.types.d.ts +0 -4
- /package/{Field.types.js → ColorPicker.types.js} +0 -0
package/Button.svelte
CHANGED
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
<script>export let disabled = false;
|
|
2
2
|
export let variant = "regular";
|
|
3
3
|
export let shape = "rounded";
|
|
4
|
+
export let colorful = false;
|
|
4
5
|
let buttonRef;
|
|
5
6
|
export const click = () => {
|
|
6
7
|
buttonRef?.click();
|
|
@@ -20,6 +21,7 @@ export const focus = (options) => {
|
|
|
20
21
|
<button
|
|
21
22
|
bind:this={buttonRef}
|
|
22
23
|
class="sterling-button"
|
|
24
|
+
class:colorful
|
|
23
25
|
class:square={shape === 'square'}
|
|
24
26
|
class:circular={shape === 'circular'}
|
|
25
27
|
class:outline={variant === 'outline'}
|
|
@@ -57,23 +59,23 @@ export const focus = (options) => {
|
|
|
57
59
|
on:pointerover
|
|
58
60
|
on:pointerout
|
|
59
61
|
on:pointerup
|
|
60
|
-
on:wheel
|
|
62
|
+
on:wheel|passive
|
|
61
63
|
{...$$restProps}
|
|
62
64
|
>
|
|
63
|
-
<slot {shape} {variant} />
|
|
65
|
+
<slot {disabled} {colorful} {shape} {variant} />
|
|
64
66
|
</button>
|
|
65
67
|
|
|
66
68
|
<style>
|
|
67
69
|
button {
|
|
68
70
|
align-content: center;
|
|
69
71
|
align-items: center;
|
|
70
|
-
background-color: var(--stsv-
|
|
71
|
-
border-color: var(--stsv-
|
|
72
|
-
border-radius: var(--stsv-
|
|
73
|
-
border-style: var(--stsv-
|
|
74
|
-
border-width: var(--stsv-
|
|
72
|
+
background-color: var(--stsv-button__background-color);
|
|
73
|
+
border-color: var(--stsv-button__border-color);
|
|
74
|
+
border-radius: var(--stsv-button__border-radius);
|
|
75
|
+
border-style: var(--stsv-button__border-style);
|
|
76
|
+
border-width: var(--stsv-button__border-width);
|
|
75
77
|
box-sizing: border-box;
|
|
76
|
-
color: var(--stsv-
|
|
78
|
+
color: var(--stsv-button__color);
|
|
77
79
|
cursor: pointer;
|
|
78
80
|
display: inline-flex;
|
|
79
81
|
flex-direction: row;
|
|
@@ -105,23 +107,40 @@ export const focus = (options) => {
|
|
|
105
107
|
}
|
|
106
108
|
|
|
107
109
|
button:hover {
|
|
108
|
-
background-color: var(--stsv-
|
|
109
|
-
border-color: var(--stsv-
|
|
110
|
-
color: var(--stsv-
|
|
110
|
+
background-color: var(--stsv-button__background-color--hover);
|
|
111
|
+
border-color: var(--stsv-button__border-color--hover);
|
|
112
|
+
color: var(--stsv-button__color--hover);
|
|
111
113
|
}
|
|
112
114
|
|
|
113
115
|
button:active {
|
|
114
|
-
background-color: var(--stsv-
|
|
115
|
-
border-color: var(--stsv-
|
|
116
|
-
color: var(--stsv-
|
|
116
|
+
background-color: var(--stsv-button__background-color--active);
|
|
117
|
+
border-color: var(--stsv-button__border-color--active);
|
|
118
|
+
color: var(--stsv-button__color--active);
|
|
117
119
|
}
|
|
118
120
|
|
|
119
121
|
button:focus-visible {
|
|
120
|
-
border-color: var(--stsv-
|
|
121
|
-
outline-color: var(--stsv-
|
|
122
|
-
outline-offset: var(--stsv-
|
|
123
|
-
outline-style: var(--stsv-
|
|
124
|
-
outline-width: var(--stsv-
|
|
122
|
+
border-color: var(--stsv-button__border-color--focus);
|
|
123
|
+
outline-color: var(--stsv-common__outline-color);
|
|
124
|
+
outline-offset: var(--stsv-common__outline-offset);
|
|
125
|
+
outline-style: var(--stsv-common__outline-style);
|
|
126
|
+
outline-width: var(--stsv-common__outline-width);
|
|
127
|
+
}
|
|
128
|
+
|
|
129
|
+
button.colorful {
|
|
130
|
+
background-color: var(--stsv-button--colorful__background-color);
|
|
131
|
+
border-color: var(--stsv-button--colorful__border-color);
|
|
132
|
+
color: var(--stsv-button--colorful__color);
|
|
133
|
+
}
|
|
134
|
+
button.colorful:hover {
|
|
135
|
+
background-color: var(--stsv-button--colorful__background-color--hover);
|
|
136
|
+
border-color: var(--stsv-button--colorful__border-color--hover);
|
|
137
|
+
color: var(--stsv-button--colorful__color--hover);
|
|
138
|
+
}
|
|
139
|
+
|
|
140
|
+
button.colorful:active {
|
|
141
|
+
background-color: var(--stsv-button--colorful__background-color--active);
|
|
142
|
+
border-color: var(--stsv-button--colorful__border-color--active);
|
|
143
|
+
color: var(--stsv-button--colorful__color--active);
|
|
125
144
|
}
|
|
126
145
|
|
|
127
146
|
button.outline {
|
|
@@ -129,11 +148,27 @@ export const focus = (options) => {
|
|
|
129
148
|
}
|
|
130
149
|
|
|
131
150
|
button.outline:hover {
|
|
132
|
-
background-color: var(--stsv-
|
|
151
|
+
background-color: var(--stsv-button__background-color--hover);
|
|
133
152
|
}
|
|
134
153
|
|
|
135
154
|
button.outline:active {
|
|
136
|
-
background-color: var(--stsv-
|
|
155
|
+
background-color: var(--stsv-button__background-color--active);
|
|
156
|
+
}
|
|
157
|
+
|
|
158
|
+
button.outline.colorful {
|
|
159
|
+
border-color: var(--stsv-button--colorful__border-color);
|
|
160
|
+
color: var(--stsv-button--colorful__border-color);
|
|
161
|
+
}
|
|
162
|
+
button.outline.colorful:hover {
|
|
163
|
+
background-color: var(--stsv-button--colorful__background-color--hover);
|
|
164
|
+
border-color: var(--stsv-button--colorful__border-color--hover);
|
|
165
|
+
color: var(--stsv-button--colorful__color--hover);
|
|
166
|
+
}
|
|
167
|
+
|
|
168
|
+
button.outline.colorful:active {
|
|
169
|
+
background-color: var(--stsv-button--colorful__background-color--active);
|
|
170
|
+
border-color: var(--stsv-button--colorful__border-color--active);
|
|
171
|
+
color: var(--stsv-button--colorful__color--active);
|
|
137
172
|
}
|
|
138
173
|
|
|
139
174
|
button.ghost {
|
|
@@ -142,17 +177,31 @@ export const focus = (options) => {
|
|
|
142
177
|
}
|
|
143
178
|
|
|
144
179
|
button.ghost:hover {
|
|
145
|
-
background-color: var(--stsv-
|
|
180
|
+
background-color: var(--stsv-button__background-color--hover);
|
|
146
181
|
border-color: transparent;
|
|
147
182
|
}
|
|
148
183
|
|
|
149
184
|
button.ghost:active {
|
|
150
|
-
background-color: var(--stsv-
|
|
185
|
+
background-color: var(--stsv-button__background-color--active);
|
|
151
186
|
border-color: transparent;
|
|
152
187
|
}
|
|
153
188
|
|
|
154
189
|
button.ghost:focus-visible {
|
|
155
|
-
border-color: var(--stsv-
|
|
190
|
+
border-color: var(--stsv-button__border-color--focus);
|
|
191
|
+
}
|
|
192
|
+
|
|
193
|
+
button.ghost.colorful {
|
|
194
|
+
color: var(--stsv-button--colorful__border-color);
|
|
195
|
+
}
|
|
196
|
+
|
|
197
|
+
button.ghost.colorful:hover {
|
|
198
|
+
background-color: var(--stsv-button--colorful__background-color--hover);
|
|
199
|
+
color: var(--stsv-button--colorful__color--hover);
|
|
200
|
+
}
|
|
201
|
+
|
|
202
|
+
button.ghost.colorful:active {
|
|
203
|
+
background-color: var(--stsv-button--colorful__background-color--active);
|
|
204
|
+
color: var(--stsv-button--colorful__color--active);
|
|
156
205
|
}
|
|
157
206
|
|
|
158
207
|
button:disabled {
|
|
@@ -167,7 +216,14 @@ export const focus = (options) => {
|
|
|
167
216
|
right: 0;
|
|
168
217
|
top: 0;
|
|
169
218
|
bottom: 0;
|
|
170
|
-
background:
|
|
219
|
+
background: repeating-linear-gradient(
|
|
220
|
+
var(--stsv-common--disabled__stripe-angle),
|
|
221
|
+
var(--stsv-common--disabled__stripe-color),
|
|
222
|
+
var(--stsv-common--disabled__stripe-color) var(--stsv-common--disabled__stripe-width),
|
|
223
|
+
var(--stsv-common--disabled__stripe-color--alt) var(--stsv-common--disabled__stripe-width),
|
|
224
|
+
var(--stsv-common--disabled__stripe-color--alt)
|
|
225
|
+
calc(2 * var(--stsv-common--disabled__stripe-width))
|
|
226
|
+
);
|
|
171
227
|
pointer-events: none;
|
|
172
228
|
}
|
|
173
229
|
|
package/Button.svelte.d.ts
CHANGED
|
@@ -5,6 +5,7 @@ declare const __propDef: {
|
|
|
5
5
|
disabled?: boolean | undefined;
|
|
6
6
|
variant?: "regular" | "outline" | "ghost" | undefined;
|
|
7
7
|
shape?: "circular" | "rounded" | "square" | undefined;
|
|
8
|
+
colorful?: boolean | undefined;
|
|
8
9
|
click?: (() => void) | undefined;
|
|
9
10
|
blur?: (() => void) | undefined;
|
|
10
11
|
focus?: ((options?: FocusOptions) => void) | undefined;
|
|
@@ -47,6 +48,8 @@ declare const __propDef: {
|
|
|
47
48
|
};
|
|
48
49
|
slots: {
|
|
49
50
|
default: {
|
|
51
|
+
disabled: boolean;
|
|
52
|
+
colorful: boolean;
|
|
50
53
|
shape: "circular" | "rounded" | "square";
|
|
51
54
|
variant: "regular" | "outline" | "ghost";
|
|
52
55
|
};
|
package/Checkbox.svelte
CHANGED
|
@@ -1,8 +1,8 @@
|
|
|
1
1
|
<script>import { idGenerator } from "./idGenerator";
|
|
2
|
-
import Label from "./Label.svelte";
|
|
3
2
|
export let checked = false;
|
|
4
3
|
export let disabled = false;
|
|
5
4
|
export let id = void 0;
|
|
5
|
+
export let colorful = false;
|
|
6
6
|
let inputRef;
|
|
7
7
|
$: {
|
|
8
8
|
if ($$slots.default && id === void 0) {
|
|
@@ -24,7 +24,7 @@ export const focus = (options) => {
|
|
|
24
24
|
@component
|
|
25
25
|
A styled HTML input type=checkbox element.
|
|
26
26
|
-->
|
|
27
|
-
<div class="sterling-checkbox" class:disabled>
|
|
27
|
+
<div class="sterling-checkbox" class:colorful class:disabled>
|
|
28
28
|
<div class="container">
|
|
29
29
|
<input
|
|
30
30
|
bind:this={inputRef}
|
|
@@ -56,17 +56,15 @@ export const focus = (options) => {
|
|
|
56
56
|
on:mouseover
|
|
57
57
|
on:mouseout
|
|
58
58
|
on:mouseup
|
|
59
|
-
on:wheel
|
|
59
|
+
on:wheel|passive
|
|
60
60
|
{...$$restProps}
|
|
61
61
|
/>
|
|
62
62
|
<div class="indicator" />
|
|
63
63
|
</div>
|
|
64
64
|
{#if $$slots.default}
|
|
65
|
-
<
|
|
66
|
-
<slot {checked} {disabled} inputId={id} value={$$restProps.value}
|
|
67
|
-
|
|
68
|
-
</slot>
|
|
69
|
-
</Label>
|
|
65
|
+
<label for={id}>
|
|
66
|
+
<slot {checked} {colorful} {disabled} inputId={id} value={$$restProps.value} />
|
|
67
|
+
</label>
|
|
70
68
|
{/if}
|
|
71
69
|
</div>
|
|
72
70
|
|
|
@@ -115,10 +113,10 @@ export const focus = (options) => {
|
|
|
115
113
|
and there is not a parent CSS selector.
|
|
116
114
|
*/
|
|
117
115
|
.indicator {
|
|
118
|
-
background-color: var(--stsv-
|
|
119
|
-
border-color: var(--stsv-
|
|
120
|
-
border-style: var(--stsv-
|
|
121
|
-
border-width: var(--stsv-
|
|
116
|
+
background-color: var(--stsv-input__background-color);
|
|
117
|
+
border-color: var(--stsv-input__border-color);
|
|
118
|
+
border-style: var(--stsv-input__border-style);
|
|
119
|
+
border-width: var(--stsv-input__border-width);
|
|
122
120
|
box-sizing: border-box;
|
|
123
121
|
display: inline-block;
|
|
124
122
|
height: 20px;
|
|
@@ -129,27 +127,27 @@ export const focus = (options) => {
|
|
|
129
127
|
}
|
|
130
128
|
|
|
131
129
|
input:checked + .indicator {
|
|
132
|
-
background-color: var(--stsv-
|
|
133
|
-
border-color: var(--stsv-
|
|
130
|
+
background-color: var(--stsv-input__background-color);
|
|
131
|
+
border-color: var(--stsv-input__border-color);
|
|
134
132
|
}
|
|
135
133
|
|
|
136
|
-
.sterling-checkbox:hover .indicator {
|
|
137
|
-
background-color: var(--stsv-
|
|
138
|
-
border-color: var(--stsv-
|
|
134
|
+
.sterling-checkbox:not(.disabled):hover .indicator {
|
|
135
|
+
background-color: var(--stsv-input__background-color--hover);
|
|
136
|
+
border-color: var(--stsv-input__border-color--hover);
|
|
139
137
|
}
|
|
140
138
|
|
|
141
139
|
input:focus-visible + .indicator {
|
|
142
|
-
outline-color: var(--stsv-
|
|
143
|
-
outline-offset: var(--stsv-
|
|
144
|
-
outline-style: var(--stsv-
|
|
145
|
-
outline-width: var(--stsv-
|
|
140
|
+
outline-color: var(--stsv-common__outline-color);
|
|
141
|
+
outline-offset: var(--stsv-common__outline-offset);
|
|
142
|
+
outline-style: var(--stsv-common__outline-style);
|
|
143
|
+
outline-width: var(--stsv-common__outline-width);
|
|
146
144
|
}
|
|
147
145
|
|
|
148
146
|
/*
|
|
149
147
|
The checkmark is a rotated L centered in the box.
|
|
150
148
|
*/
|
|
151
149
|
.indicator::after {
|
|
152
|
-
border-color: var(--stsv-
|
|
150
|
+
border-color: var(--stsv-input__color);
|
|
153
151
|
border-style: solid;
|
|
154
152
|
border-width: 0 3px 3px 0;
|
|
155
153
|
box-sizing: border-box;
|
|
@@ -169,8 +167,26 @@ export const focus = (options) => {
|
|
|
169
167
|
opacity: 1;
|
|
170
168
|
}
|
|
171
169
|
|
|
172
|
-
.sterling-checkbox:hover input:checked + .indicator::after {
|
|
173
|
-
border-color: var(--stsv-
|
|
170
|
+
.sterling-checkbox:not(.disabled):hover input:checked + .indicator::after {
|
|
171
|
+
border-color: var(--stsv-input__color--hover);
|
|
172
|
+
}
|
|
173
|
+
|
|
174
|
+
.sterling-checkbox.colorful .indicator {
|
|
175
|
+
background-color: var(--stsv-input--colorful__background-color);
|
|
176
|
+
border-color: var(--stsv-input--colorful__border-color);
|
|
177
|
+
}
|
|
178
|
+
|
|
179
|
+
.sterling-checkbox.colorful:not(.disabled):hover .indicator {
|
|
180
|
+
background-color: var(--stsv-input--colorful__background-color--hover);
|
|
181
|
+
border-color: var(--stsv-input--colorful__border-color--hover);
|
|
182
|
+
}
|
|
183
|
+
|
|
184
|
+
.sterling-checkbox.colorful .indicator::after {
|
|
185
|
+
border-color: var(--stsv-input--colorful__color);
|
|
186
|
+
}
|
|
187
|
+
|
|
188
|
+
.sterling-checkbox.colorful:not(.disabled):hover input:checked + .indicator::after {
|
|
189
|
+
border-color: var(--stsv-input--colorful__color--hover);
|
|
174
190
|
}
|
|
175
191
|
|
|
176
192
|
.sterling-checkbox.disabled,
|
|
@@ -179,7 +195,14 @@ export const focus = (options) => {
|
|
|
179
195
|
}
|
|
180
196
|
|
|
181
197
|
.container::after {
|
|
182
|
-
background:
|
|
198
|
+
background: repeating-linear-gradient(
|
|
199
|
+
var(--stsv-common--disabled__stripe-angle),
|
|
200
|
+
var(--stsv-common--disabled__stripe-color),
|
|
201
|
+
var(--stsv-common--disabled__stripe-color) var(--stsv-common--disabled__stripe-width),
|
|
202
|
+
var(--stsv-common--disabled__stripe-color--alt) var(--stsv-common--disabled__stripe-width),
|
|
203
|
+
var(--stsv-common--disabled__stripe-color--alt)
|
|
204
|
+
calc(2 * var(--stsv-common--disabled__stripe-width))
|
|
205
|
+
);
|
|
183
206
|
bottom: 0;
|
|
184
207
|
content: '';
|
|
185
208
|
left: 0;
|
|
@@ -191,6 +214,12 @@ export const focus = (options) => {
|
|
|
191
214
|
transition: opacity 250ms;
|
|
192
215
|
}
|
|
193
216
|
|
|
217
|
+
label {
|
|
218
|
+
color: var(--stsv-common__color);
|
|
219
|
+
transition: color 250ms;
|
|
220
|
+
font: inherit;
|
|
221
|
+
}
|
|
222
|
+
|
|
194
223
|
.sterling-checkbox.disabled .container::after {
|
|
195
224
|
opacity: 1;
|
|
196
225
|
}
|
|
@@ -198,7 +227,8 @@ export const focus = (options) => {
|
|
|
198
227
|
@media (prefers-reduced-motion) {
|
|
199
228
|
.indicator,
|
|
200
229
|
.indicator::after,
|
|
201
|
-
.container::after
|
|
230
|
+
.container::after,
|
|
231
|
+
label {
|
|
202
232
|
transition: none;
|
|
203
233
|
}
|
|
204
234
|
}
|
package/Checkbox.svelte.d.ts
CHANGED
|
@@ -5,6 +5,7 @@ declare const __propDef: {
|
|
|
5
5
|
checked?: boolean | undefined;
|
|
6
6
|
disabled?: boolean | undefined;
|
|
7
7
|
id?: string | undefined;
|
|
8
|
+
colorful?: boolean | undefined;
|
|
8
9
|
blur?: (() => void) | undefined;
|
|
9
10
|
click?: (() => void) | undefined;
|
|
10
11
|
focus?: ((options?: FocusOptions) => void) | undefined;
|
|
@@ -41,6 +42,7 @@ declare const __propDef: {
|
|
|
41
42
|
slots: {
|
|
42
43
|
default: {
|
|
43
44
|
checked: boolean;
|
|
45
|
+
colorful: boolean;
|
|
44
46
|
disabled: boolean;
|
|
45
47
|
inputId: string | undefined;
|
|
46
48
|
value: any;
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export declare const COLOR_FORMATS: readonly ["hex", "rgb", "hsl"];
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export const COLOR_FORMATS = ['hex', 'rgb', 'hsl'];
|
|
@@ -0,0 +1,257 @@
|
|
|
1
|
+
<script>import { tick } from "svelte";
|
|
2
|
+
import tinycolor from "@ctrl/tinycolor";
|
|
3
|
+
import Dropdown from "./Dropdown.svelte";
|
|
4
|
+
import Input from "./Input.svelte";
|
|
5
|
+
import Tab from "./Tab.svelte";
|
|
6
|
+
import TabList from "./TabList.svelte";
|
|
7
|
+
import RgbColorSliders from "./RgbColorSliders.svelte";
|
|
8
|
+
import HslColorSliders from "./HslColorSliders.svelte";
|
|
9
|
+
import HexColorSliders from "./HexColorSliders.svelte";
|
|
10
|
+
import { round } from "lodash-es";
|
|
11
|
+
import { trapKeyboardFocus } from "./actions/trapKeyboardFocus";
|
|
12
|
+
const defaultColorText = "#000000";
|
|
13
|
+
export let colorText = defaultColorText;
|
|
14
|
+
export let colorFormat = "hex";
|
|
15
|
+
export let colorful = false;
|
|
16
|
+
export let composed = false;
|
|
17
|
+
export let disabled = false;
|
|
18
|
+
export let open = false;
|
|
19
|
+
let hue = 0;
|
|
20
|
+
let saturation = 0;
|
|
21
|
+
let lightness = 0;
|
|
22
|
+
let red = 0;
|
|
23
|
+
let green = 0;
|
|
24
|
+
let blue = 0;
|
|
25
|
+
let alpha = 1;
|
|
26
|
+
let hexAlpha = 255;
|
|
27
|
+
let updating = false;
|
|
28
|
+
let tabListRef;
|
|
29
|
+
let tabsRef;
|
|
30
|
+
const updateFromRgb = async () => {
|
|
31
|
+
if (!updating && (colorFormat === "hex" || colorFormat === "rgb")) {
|
|
32
|
+
updating = true;
|
|
33
|
+
const newAlpha = colorFormat === "hex" ? hexAlpha / 255 : alpha;
|
|
34
|
+
const color = tinycolor({ r: red, g: green, b: blue, a: newAlpha });
|
|
35
|
+
const hsl = color.toHsl();
|
|
36
|
+
hue = Math.round(hsl.h);
|
|
37
|
+
saturation = Math.round(hsl.s * 100);
|
|
38
|
+
lightness = Math.round(hsl.l * 100);
|
|
39
|
+
switch (colorFormat) {
|
|
40
|
+
case "rgb":
|
|
41
|
+
colorText = color.toRgbString();
|
|
42
|
+
hexAlpha = Math.round(alpha * 255);
|
|
43
|
+
break;
|
|
44
|
+
case "hex":
|
|
45
|
+
colorText = alpha === 100 ? color.toHexString() : color.toHex8String();
|
|
46
|
+
alpha = round(hexAlpha / 255, 2);
|
|
47
|
+
break;
|
|
48
|
+
}
|
|
49
|
+
await tick();
|
|
50
|
+
updating = false;
|
|
51
|
+
}
|
|
52
|
+
};
|
|
53
|
+
const updateFromHsl = async () => {
|
|
54
|
+
if (!updating && colorFormat === "hsl") {
|
|
55
|
+
updating = true;
|
|
56
|
+
const color = tinycolor({ h: hue, s: saturation / 100, l: lightness / 100, a: alpha });
|
|
57
|
+
const rgb = color.toRgb();
|
|
58
|
+
red = rgb.r;
|
|
59
|
+
green = rgb.g;
|
|
60
|
+
blue = rgb.b;
|
|
61
|
+
colorText = color.toHslString();
|
|
62
|
+
hexAlpha = Math.round(alpha * 255);
|
|
63
|
+
await tick();
|
|
64
|
+
updating = false;
|
|
65
|
+
}
|
|
66
|
+
};
|
|
67
|
+
const updateColorsFromText = async () => {
|
|
68
|
+
const color = tinycolor(colorText);
|
|
69
|
+
if (color.isValid) {
|
|
70
|
+
if (!updating) {
|
|
71
|
+
updating = true;
|
|
72
|
+
switch (color.format) {
|
|
73
|
+
case "hsl":
|
|
74
|
+
colorFormat = "hsl";
|
|
75
|
+
break;
|
|
76
|
+
case "rgb":
|
|
77
|
+
colorFormat = "rgb";
|
|
78
|
+
break;
|
|
79
|
+
case "hex":
|
|
80
|
+
case "hex4":
|
|
81
|
+
case "hex8":
|
|
82
|
+
colorFormat = "hex";
|
|
83
|
+
break;
|
|
84
|
+
default:
|
|
85
|
+
break;
|
|
86
|
+
}
|
|
87
|
+
const hsl = color.toHsl();
|
|
88
|
+
hue = Math.round(hsl.h);
|
|
89
|
+
saturation = Math.round(hsl.s * 100);
|
|
90
|
+
lightness = Math.round(hsl.l * 100);
|
|
91
|
+
const rgb = color.toRgb();
|
|
92
|
+
red = rgb.r;
|
|
93
|
+
green = rgb.g;
|
|
94
|
+
blue = rgb.b;
|
|
95
|
+
if (rgb.a) {
|
|
96
|
+
alpha = hsl.a;
|
|
97
|
+
hexAlpha = Math.round(alpha * 255);
|
|
98
|
+
}
|
|
99
|
+
await tick();
|
|
100
|
+
updating = false;
|
|
101
|
+
}
|
|
102
|
+
}
|
|
103
|
+
};
|
|
104
|
+
$:
|
|
105
|
+
colorText, updateColorsFromText();
|
|
106
|
+
$:
|
|
107
|
+
colorFormat, hue, saturation, lightness, alpha, updateFromHsl();
|
|
108
|
+
$:
|
|
109
|
+
colorFormat, red, green, blue, alpha, hexAlpha, updateFromRgb();
|
|
110
|
+
const onInputBlur = async () => {
|
|
111
|
+
if (!updating) {
|
|
112
|
+
if (colorText.trim().length === 0) {
|
|
113
|
+
colorText = defaultColorText;
|
|
114
|
+
return;
|
|
115
|
+
}
|
|
116
|
+
const color = tinycolor(colorText);
|
|
117
|
+
if (color.isValid) {
|
|
118
|
+
updating = true;
|
|
119
|
+
switch (colorFormat) {
|
|
120
|
+
case "hsl":
|
|
121
|
+
colorText = color.toHslString();
|
|
122
|
+
break;
|
|
123
|
+
case "rgb":
|
|
124
|
+
colorText = color.toRgbString();
|
|
125
|
+
break;
|
|
126
|
+
case "hex":
|
|
127
|
+
colorText = alpha === 1 ? color.toHexString() : color.toHex8String();
|
|
128
|
+
break;
|
|
129
|
+
default:
|
|
130
|
+
break;
|
|
131
|
+
}
|
|
132
|
+
await tick();
|
|
133
|
+
updating = false;
|
|
134
|
+
}
|
|
135
|
+
}
|
|
136
|
+
};
|
|
137
|
+
const onInputClick = (event) => {
|
|
138
|
+
event.stopPropagation();
|
|
139
|
+
return false;
|
|
140
|
+
};
|
|
141
|
+
const onInputKeydown = (event) => {
|
|
142
|
+
switch (event.key) {
|
|
143
|
+
case "Tab":
|
|
144
|
+
if (open) {
|
|
145
|
+
setTimeout(() => {
|
|
146
|
+
tabListRef?.focus();
|
|
147
|
+
}, 0);
|
|
148
|
+
event.preventDefault();
|
|
149
|
+
event.stopPropagation();
|
|
150
|
+
return false;
|
|
151
|
+
}
|
|
152
|
+
break;
|
|
153
|
+
case "Escape":
|
|
154
|
+
if (open) {
|
|
155
|
+
open = false;
|
|
156
|
+
event.preventDefault();
|
|
157
|
+
event.stopPropagation();
|
|
158
|
+
return false;
|
|
159
|
+
}
|
|
160
|
+
break;
|
|
161
|
+
}
|
|
162
|
+
event.stopImmediatePropagation();
|
|
163
|
+
};
|
|
164
|
+
updateColorsFromText();
|
|
165
|
+
</script>
|
|
166
|
+
|
|
167
|
+
<Dropdown
|
|
168
|
+
bind:open
|
|
169
|
+
{colorful}
|
|
170
|
+
{composed}
|
|
171
|
+
{disabled}
|
|
172
|
+
on:blur
|
|
173
|
+
on:click
|
|
174
|
+
on:copy
|
|
175
|
+
on:cut
|
|
176
|
+
on:dblclick
|
|
177
|
+
on:dragend
|
|
178
|
+
on:dragenter
|
|
179
|
+
on:dragleave
|
|
180
|
+
on:dragover
|
|
181
|
+
on:dragstart
|
|
182
|
+
on:drop
|
|
183
|
+
on:focus
|
|
184
|
+
on:focusin
|
|
185
|
+
on:focusout
|
|
186
|
+
on:keydown
|
|
187
|
+
on:keypress
|
|
188
|
+
on:keyup
|
|
189
|
+
on:mousedown
|
|
190
|
+
on:mouseenter
|
|
191
|
+
on:mouseleave
|
|
192
|
+
on:mousemove
|
|
193
|
+
on:mouseover
|
|
194
|
+
on:mouseout
|
|
195
|
+
on:mouseup
|
|
196
|
+
on:wheel
|
|
197
|
+
on:paste
|
|
198
|
+
{...$$restProps}
|
|
199
|
+
>
|
|
200
|
+
<div class="value" slot="value">
|
|
201
|
+
<div class="color-box" style="background-color: {colorText}" />
|
|
202
|
+
<Input
|
|
203
|
+
bind:value={colorText}
|
|
204
|
+
{colorful}
|
|
205
|
+
{disabled}
|
|
206
|
+
composed
|
|
207
|
+
on:blur={onInputBlur}
|
|
208
|
+
on:click={onInputClick}
|
|
209
|
+
on:keydown={onInputKeydown}
|
|
210
|
+
spellcheck="false"
|
|
211
|
+
/>
|
|
212
|
+
</div>
|
|
213
|
+
<div class="popup" use:trapKeyboardFocus>
|
|
214
|
+
<div class="tabs" bind:this={tabsRef}>
|
|
215
|
+
<TabList bind:this={tabListRef} bind:selectedValue={colorFormat} {colorful}>
|
|
216
|
+
<Tab value="hex">hex</Tab>
|
|
217
|
+
<Tab value="rgb">rgb</Tab>
|
|
218
|
+
<Tab value="hsl">hsl</Tab>
|
|
219
|
+
</TabList>
|
|
220
|
+
</div>
|
|
221
|
+
<div class="sliders">
|
|
222
|
+
{#if colorFormat === 'rgb'}
|
|
223
|
+
<RgbColorSliders bind:red bind:green bind:blue bind:alpha {colorful} />
|
|
224
|
+
{:else if colorFormat === 'hex'}
|
|
225
|
+
<HexColorSliders bind:red bind:green bind:blue bind:alpha={hexAlpha} {colorful} />
|
|
226
|
+
{:else if colorFormat === 'hsl'}
|
|
227
|
+
<HslColorSliders bind:hue bind:saturation bind:lightness bind:alpha {colorful} />
|
|
228
|
+
{/if}
|
|
229
|
+
</div>
|
|
230
|
+
</div>
|
|
231
|
+
</Dropdown>
|
|
232
|
+
|
|
233
|
+
<style>
|
|
234
|
+
.value {
|
|
235
|
+
display: grid;
|
|
236
|
+
align-items: center;
|
|
237
|
+
justify-content: stretch;
|
|
238
|
+
justify-items: stretch;
|
|
239
|
+
grid-template-columns: auto 1fr;
|
|
240
|
+
padding-left: 0.5em;
|
|
241
|
+
width: 250px;
|
|
242
|
+
}
|
|
243
|
+
|
|
244
|
+
.color-box {
|
|
245
|
+
width: 1em;
|
|
246
|
+
height: 1em;
|
|
247
|
+
border: 1px dashed var(--stsv-common__border-color);
|
|
248
|
+
}
|
|
249
|
+
|
|
250
|
+
.popup {
|
|
251
|
+
width: fit-content;
|
|
252
|
+
min-width: 500px;
|
|
253
|
+
display: grid;
|
|
254
|
+
align-items: center;
|
|
255
|
+
padding: 0.25em;
|
|
256
|
+
}
|
|
257
|
+
</style>
|
|
@@ -0,0 +1,49 @@
|
|
|
1
|
+
import { SvelteComponentTyped } from "svelte";
|
|
2
|
+
declare const __propDef: {
|
|
3
|
+
props: {
|
|
4
|
+
[x: string]: any;
|
|
5
|
+
colorText?: string | undefined;
|
|
6
|
+
colorFormat?: "hex" | "rgb" | "hsl" | undefined;
|
|
7
|
+
colorful?: boolean | undefined;
|
|
8
|
+
composed?: boolean | undefined;
|
|
9
|
+
disabled?: boolean | undefined;
|
|
10
|
+
open?: boolean | undefined;
|
|
11
|
+
};
|
|
12
|
+
events: {
|
|
13
|
+
blur: FocusEvent;
|
|
14
|
+
click: MouseEvent;
|
|
15
|
+
copy: ClipboardEvent;
|
|
16
|
+
cut: ClipboardEvent;
|
|
17
|
+
dblclick: MouseEvent;
|
|
18
|
+
dragend: DragEvent;
|
|
19
|
+
dragenter: DragEvent;
|
|
20
|
+
dragleave: DragEvent;
|
|
21
|
+
dragover: DragEvent;
|
|
22
|
+
dragstart: DragEvent;
|
|
23
|
+
drop: DragEvent;
|
|
24
|
+
focus: FocusEvent;
|
|
25
|
+
focusin: FocusEvent;
|
|
26
|
+
focusout: FocusEvent;
|
|
27
|
+
keydown: KeyboardEvent;
|
|
28
|
+
keypress: KeyboardEvent;
|
|
29
|
+
keyup: KeyboardEvent;
|
|
30
|
+
mousedown: MouseEvent;
|
|
31
|
+
mouseenter: MouseEvent;
|
|
32
|
+
mouseleave: MouseEvent;
|
|
33
|
+
mousemove: MouseEvent;
|
|
34
|
+
mouseover: MouseEvent;
|
|
35
|
+
mouseout: MouseEvent;
|
|
36
|
+
mouseup: MouseEvent;
|
|
37
|
+
wheel: WheelEvent;
|
|
38
|
+
paste: ClipboardEvent;
|
|
39
|
+
} & {
|
|
40
|
+
[evt: string]: CustomEvent<any>;
|
|
41
|
+
};
|
|
42
|
+
slots: {};
|
|
43
|
+
};
|
|
44
|
+
export type ColorPickerProps = typeof __propDef.props;
|
|
45
|
+
export type ColorPickerEvents = typeof __propDef.events;
|
|
46
|
+
export type ColorPickerSlots = typeof __propDef.slots;
|
|
47
|
+
export default class ColorPicker extends SvelteComponentTyped<ColorPickerProps, ColorPickerEvents, ColorPickerSlots> {
|
|
48
|
+
}
|
|
49
|
+
export {};
|