@witchcraft/ui 0.1.0 → 0.1.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.
Files changed (138) hide show
  1. package/dist/module.json +2 -2
  2. package/dist/module.mjs +1 -1
  3. package/dist/runtime/components/Aria/Aria.vue +5 -9
  4. package/dist/runtime/components/Aria/Aria.vue.d.ts +5 -0
  5. package/dist/runtime/components/Icon/Icon.vue +10 -31
  6. package/dist/runtime/components/Icon/Icon.vue.d.ts +21 -0
  7. package/dist/runtime/components/LibButton/LibButton.vue +58 -77
  8. package/dist/runtime/components/LibButton/LibButton.vue.d.ts +36 -0
  9. package/dist/runtime/components/LibCheckbox/LibCheckbox.vue +48 -75
  10. package/dist/runtime/components/LibCheckbox/LibCheckbox.vue.d.ts +42 -0
  11. package/dist/runtime/components/LibColorInput/LibColorInput.vue +63 -108
  12. package/dist/runtime/components/LibColorInput/LibColorInput.vue.d.ts +63 -0
  13. package/dist/runtime/components/LibColorPicker/LibColorPicker.vue +271 -352
  14. package/dist/runtime/components/LibColorPicker/LibColorPicker.vue.d.ts +61 -0
  15. package/dist/runtime/components/LibDarkModeSwitcher/LibDarkModeSwitcher.vue +32 -57
  16. package/dist/runtime/components/LibDarkModeSwitcher/LibDarkModeSwitcher.vue.d.ts +22 -0
  17. package/dist/runtime/components/LibDatePicker/LibDatePicker.vue +17 -38
  18. package/dist/runtime/components/LibDatePicker/LibDatePicker.vue.d.ts +40 -0
  19. package/dist/runtime/components/LibDatePicker/LibRangeDatePicker.vue +53 -82
  20. package/dist/runtime/components/LibDatePicker/LibRangeDatePicker.vue.d.ts +34 -0
  21. package/dist/runtime/components/LibDatePicker/LibSingleDatePicker.vue +50 -67
  22. package/dist/runtime/components/LibDatePicker/LibSingleDatePicker.vue.d.ts +34 -0
  23. package/dist/runtime/components/LibDatePicker/LibTimeZonePicker.vue +7 -8
  24. package/dist/runtime/components/LibDatePicker/LibTimeZonePicker.vue.d.ts +22 -0
  25. package/dist/runtime/components/LibDebug/LibDebug.vue +42 -70
  26. package/dist/runtime/components/LibDebug/LibDebug.vue.d.ts +32 -0
  27. package/dist/runtime/components/LibDevOnly/LibDevOnly.vue +18 -31
  28. package/dist/runtime/components/LibDevOnly/LibDevOnly.vue.d.ts +22 -0
  29. package/dist/runtime/components/LibFileInput/LibFileInput.vue +113 -157
  30. package/dist/runtime/components/LibFileInput/LibFileInput.vue.d.ts +43 -0
  31. package/dist/runtime/components/LibInputDeprecated/LibInputDeprecated.vue +215 -242
  32. package/dist/runtime/components/LibInputDeprecated/LibInputDeprecated.vue.d.ts +165 -0
  33. package/dist/runtime/components/LibLabel/LibLabel.vue +30 -46
  34. package/dist/runtime/components/LibLabel/LibLabel.vue.d.ts +27 -0
  35. package/dist/runtime/components/LibMultiValues/LibMultiValues.vue +44 -59
  36. package/dist/runtime/components/LibMultiValues/LibMultiValues.vue.d.ts +29 -0
  37. package/dist/runtime/components/LibNotifications/LibNotification.vue +32 -49
  38. package/dist/runtime/components/LibNotifications/LibNotification.vue.d.ts +17 -0
  39. package/dist/runtime/components/LibNotifications/LibNotifications.vue +63 -84
  40. package/dist/runtime/components/LibNotifications/LibNotifications.vue.d.ts +13 -0
  41. package/dist/runtime/components/LibPagination/LibPagination.vue +67 -112
  42. package/dist/runtime/components/LibPagination/LibPagination.vue.d.ts +104 -0
  43. package/dist/runtime/components/LibPalette/LibPalette.vue +20 -23
  44. package/dist/runtime/components/LibPalette/LibPalette.vue.d.ts +14 -0
  45. package/dist/runtime/components/LibPopup/LibPopup.vue +314 -352
  46. package/dist/runtime/components/LibPopup/LibPopup.vue.d.ts +46 -0
  47. package/dist/runtime/components/LibProgressBar/LibProgressBar.vue +70 -92
  48. package/dist/runtime/components/LibProgressBar/LibProgressBar.vue.d.ts +41 -0
  49. package/dist/runtime/components/LibRecorder/LibRecorder.vue +133 -178
  50. package/dist/runtime/components/LibRecorder/LibRecorder.vue.d.ts +77 -0
  51. package/dist/runtime/components/LibRoot/LibRoot.vue +73 -100
  52. package/dist/runtime/components/LibRoot/LibRoot.vue.d.ts +41 -0
  53. package/dist/runtime/components/LibSimpleInput/LibSimpleInput.vue +49 -78
  54. package/dist/runtime/components/LibSimpleInput/LibSimpleInput.vue.d.ts +35 -0
  55. package/dist/runtime/components/LibSuggestions/LibSuggestions.vue +123 -157
  56. package/dist/runtime/components/LibSuggestions/LibSuggestions.vue.d.ts +94 -0
  57. package/dist/runtime/components/LibTable/LibTable.vue +63 -100
  58. package/dist/runtime/components/LibTable/LibTable.vue.d.ts +45 -0
  59. package/dist/runtime/components/Template/NAME.vue +15 -36
  60. package/dist/runtime/components/Template/NAME.vue.d.ts +17 -0
  61. package/dist/runtime/components/TestControls/TestControls.vue +6 -9
  62. package/dist/runtime/components/TestControls/TestControls.vue.d.ts +5 -0
  63. package/dist/runtime/directives/vResizableCols.js +89 -83
  64. package/dist/types.d.mts +2 -6
  65. package/package.json +11 -11
  66. package/src/runtime/components/Focus.stories.ts +3 -2
  67. package/src/runtime/components/Icon/Icon.vue +0 -1
  68. package/src/runtime/components/LibButton/LibButton.vue +0 -1
  69. package/src/runtime/components/LibCheckbox/LibCheckbox.vue +0 -1
  70. package/src/runtime/components/LibColorInput/LibColorInput.vue +0 -1
  71. package/src/runtime/components/LibColorPicker/utils/safeConvertToHsva.ts +0 -1
  72. package/src/runtime/components/LibDarkModeSwitcher/LibDarkModeSwitcher.vue +0 -1
  73. package/src/runtime/components/LibFileInput/LibFileInput.vue +0 -1
  74. package/src/runtime/components/LibInputDeprecated/LibInputDeprecated.vue +0 -1
  75. package/src/runtime/components/LibMultiValues/LibMultiValues.vue +0 -1
  76. package/src/runtime/components/LibNotifications/LibNotification.vue +0 -1
  77. package/src/runtime/components/LibNotifications/LibNotifications.vue +0 -1
  78. package/src/runtime/components/LibPagination/LibPagination.vue +0 -1
  79. package/src/runtime/components/LibPopup/LibPopup.vue +0 -1
  80. package/src/runtime/components/LibProgressBar/LibProgressBar.vue +0 -1
  81. package/src/runtime/components/LibRecorder/LibRecorder.vue +0 -1
  82. package/src/runtime/components/LibSimpleInput/LibSimpleInput.vue +0 -1
  83. package/src/runtime/components/LibSuggestions/LibSuggestions.vue +0 -1
  84. package/src/runtime/components/LibTable/LibTable.vue +0 -1
  85. package/src/runtime/directives/vResizableCols.ts +79 -73
  86. package/dist/module.cjs +0 -5
  87. package/dist/module.d.ts +0 -36
  88. package/dist/runtime/components/Focus.stories.d.ts +0 -11
  89. package/dist/runtime/components/Focus.stories.js +0 -53
  90. package/dist/runtime/components/LibButton/LibButton.stories.d.ts +0 -12
  91. package/dist/runtime/components/LibButton/LibButton.stories.js +0 -94
  92. package/dist/runtime/components/LibCheckbox/LibCheckbox.stories.d.ts +0 -14
  93. package/dist/runtime/components/LibCheckbox/LibCheckbox.stories.js +0 -29
  94. package/dist/runtime/components/LibColorInput/LibColorInput.stories.d.ts +0 -7
  95. package/dist/runtime/components/LibColorInput/LibColorInput.stories.js +0 -58
  96. package/dist/runtime/components/LibColorPicker/LibColorPicker.stories.d.ts +0 -9
  97. package/dist/runtime/components/LibColorPicker/LibColorPicker.stories.js +0 -68
  98. package/dist/runtime/components/LibDarkModeSwitcher/LibDarkModeSwitcher.stories.d.ts +0 -7
  99. package/dist/runtime/components/LibDarkModeSwitcher/LibDarkModeSwitcher.stories.js +0 -36
  100. package/dist/runtime/components/LibDatePicker/LibDatePicker.stories.d.ts +0 -11
  101. package/dist/runtime/components/LibDatePicker/LibDatePicker.stories.js +0 -98
  102. package/dist/runtime/components/LibDebug/LibDebug.stories.d.ts +0 -9
  103. package/dist/runtime/components/LibDebug/LibDebug.stories.js +0 -46
  104. package/dist/runtime/components/LibFileInput/LibFileInput.stories.d.ts +0 -10
  105. package/dist/runtime/components/LibFileInput/LibFileInput.stories.js +0 -63
  106. package/dist/runtime/components/LibInputDeprecated/LibInputDeprecated.stories.d.ts +0 -33
  107. package/dist/runtime/components/LibInputDeprecated/LibInputDeprecated.stories.js +0 -384
  108. package/dist/runtime/components/LibLabel/LibLabel.stories.d.ts +0 -6
  109. package/dist/runtime/components/LibLabel/LibLabel.stories.js +0 -25
  110. package/dist/runtime/components/LibMultiValues/LibMultiValues.stories.d.ts +0 -23
  111. package/dist/runtime/components/LibMultiValues/LibMultiValues.stories.js +0 -61
  112. package/dist/runtime/components/LibNotifications/LibNotification.stories.d.ts +0 -15
  113. package/dist/runtime/components/LibNotifications/LibNotification.stories.js +0 -126
  114. package/dist/runtime/components/LibNotifications/LibNotifications.stories.d.ts +0 -6
  115. package/dist/runtime/components/LibNotifications/LibNotifications.stories.js +0 -109
  116. package/dist/runtime/components/LibPagination/LibPagination.stories.d.ts +0 -6
  117. package/dist/runtime/components/LibPagination/LibPagination.stories.js +0 -40
  118. package/dist/runtime/components/LibPalette/LibPalette.stories.d.ts +0 -6
  119. package/dist/runtime/components/LibPalette/LibPalette.stories.js +0 -20
  120. package/dist/runtime/components/LibPopup/LibPopup.stories.d.ts +0 -14
  121. package/dist/runtime/components/LibPopup/LibPopup.stories.js +0 -147
  122. package/dist/runtime/components/LibProgressBar/LibProgressBar.stories.d.ts +0 -10
  123. package/dist/runtime/components/LibProgressBar/LibProgressBar.stories.js +0 -81
  124. package/dist/runtime/components/LibRecorder/LibRecorder.stories.d.ts +0 -19
  125. package/dist/runtime/components/LibRecorder/LibRecorder.stories.js +0 -63
  126. package/dist/runtime/components/LibSimpleInput/LibSimpleInput.stories.d.ts +0 -26
  127. package/dist/runtime/components/LibSimpleInput/LibSimpleInput.stories.js +0 -78
  128. package/dist/runtime/components/LibSuggestions/LibSuggestions.stories.d.ts +0 -27
  129. package/dist/runtime/components/LibSuggestions/LibSuggestions.stories.js +0 -112
  130. package/dist/runtime/components/LibTable/LibTable.stories.d.ts +0 -16
  131. package/dist/runtime/components/LibTable/LibTable.stories.js +0 -156
  132. package/dist/runtime/components/Reset.stories.d.ts +0 -5
  133. package/dist/runtime/components/Reset.stories.js +0 -19
  134. package/dist/runtime/components/Scrolling.stories.d.ts +0 -6
  135. package/dist/runtime/components/Scrolling.stories.js +0 -44
  136. package/dist/runtime/composables/useScrollNearContainerEdges.stories.d.ts +0 -7
  137. package/dist/runtime/composables/useScrollNearContainerEdges.stories.js +0 -85
  138. package/dist/types.d.ts +0 -7
@@ -2,7 +2,8 @@
2
2
  <div
3
3
  :id="id ?? fallbackId"
4
4
  :aria-label="t('color-picker.aria')"
5
- :class="twMerge(`color-picker
5
+ :class="twMerge(
6
+ `color-picker
6
7
  [--slider-size:calc(var(--spacing)_*_4)]
7
8
  [--contrast-dark:var(--color-neutral-100)]
8
9
  [--contrast-light:var(--color-neutral-800)]
@@ -15,15 +16,15 @@
15
16
  gap-3
16
17
  p-3
17
18
  `,
18
- invertColors && `
19
+ invertColors && `
19
20
  [--fg:rgb(var(--contrast-light))]
20
21
  [--bg:rgb(var(--contrast-dark))]
21
22
  `,
22
- border && `
23
+ border && `
23
24
  border rounded-sm border-neutral-600
24
25
  `,
25
- ($attrs as any)?.class
26
- )"
26
+ $attrs?.class
27
+ )"
27
28
  >
28
29
  <div
29
30
  :class="`color-picker--all-picker
@@ -168,37 +169,29 @@
168
169
  </div>
169
170
  </template>
170
171
 
171
- <script setup lang="ts">
172
- /* todo change to colorjsio for less dependencies */
173
- import { castType } from "@alanscodelog/utils/castType.js"
174
- import { clampNumber } from "@alanscodelog/utils/clampNumber.js"
175
- import { isArray } from "@alanscodelog/utils/isArray.js"
176
- import { unreachable } from "@alanscodelog/utils/unreachable.js"
177
- import Color from "colorjs.io"
178
- import { computed, onMounted, reactive, type Ref, ref, type UnwrapRef,useAttrs, watch } from "vue"
179
-
180
- import { safeConvertToHsva } from "./utils/safeConvertToHsva.js"
181
- import { safeConvertToRgba } from "./utils/safeConvertToRgba.js"
182
- import { toLowPrecisionRgbaString } from "./utils/toLowPrecisionRgbaString.js"
183
-
184
- import { useInjectedI18n } from "../../composables/useInjectedI18n.js"
185
- import { copy } from "../../helpers/copy.js"
186
- import type { HsvaColor, RgbaColor } from "../../types/index.js"
187
- import { twMerge } from "../../utils/twMerge.js"
188
- import aria from "../Aria/Aria.vue"
189
- import Icon from "../Icon/Icon.vue"
190
- import LibButton from "../LibButton/LibButton.vue"
191
- import LibSimpleInput from "../LibSimpleInput/LibSimpleInput.vue"
192
- import { getFallbackId, type LabelProps , type LinkableByIdProps } from "../shared/props.js"
193
-
172
+ <script setup>
173
+ import { castType } from "@alanscodelog/utils/castType.js";
174
+ import { clampNumber } from "@alanscodelog/utils/clampNumber.js";
175
+ import { isArray } from "@alanscodelog/utils/isArray.js";
176
+ import { unreachable } from "@alanscodelog/utils/unreachable.js";
177
+ import Color from "colorjs.io";
178
+ import { computed, onMounted, reactive, ref, useAttrs, watch } from "vue";
179
+ import { safeConvertToHsva } from "./utils/safeConvertToHsva.js";
180
+ import { safeConvertToRgba } from "./utils/safeConvertToRgba.js";
181
+ import { toLowPrecisionRgbaString } from "./utils/toLowPrecisionRgbaString.js";
182
+ import { useInjectedI18n } from "../../composables/useInjectedI18n.js";
183
+ import { copy } from "../../helpers/copy.js";
184
+ import { twMerge } from "../../utils/twMerge.js";
185
+ import aria from "../Aria/Aria.vue";
186
+ import Icon from "../Icon/Icon.vue";
187
+ import LibButton from "../LibButton/LibButton.vue";
188
+ import LibSimpleInput from "../LibSimpleInput/LibSimpleInput.vue";
189
+ import { getFallbackId } from "../shared/props.js";
194
190
  defineOptions({
195
- name: "lib-color-picker",
196
- })
197
-
198
- const $attrs = useAttrs()
199
-
200
- const t = useInjectedI18n()
201
-
191
+ name: "lib-color-picker"
192
+ });
193
+ const $attrs = useAttrs();
194
+ const t = useInjectedI18n();
202
195
  const sliderClasses = `
203
196
  slider
204
197
  no-touch-action
@@ -206,8 +199,7 @@ const sliderClasses = `
206
199
  w-full
207
200
  relative
208
201
  flex
209
- `
210
-
202
+ `;
211
203
  const handleClasses = `
212
204
  handle
213
205
  h-[var(--slider-size)]
@@ -222,338 +214,265 @@ const handleClasses = `
222
214
  focus:border-accent-500
223
215
  active:border-accent-500
224
216
  hover:border-accent-500
225
- `
226
- const emits = defineEmits<{
227
- (e: "save", val: RgbaColor): void
228
- (e: "cancel"): void
229
- }>()
230
-
231
- const props = withDefaults(defineProps<
232
- LabelProps
233
- & LinkableByIdProps
234
- & {
235
- allowAlpha?: boolean
236
- /**
237
- * The precision of the rgba string representation of the color. Defaults to 3. Extra trailing zeros are removed for a prettier number.
238
- *
239
- * Does not affect the number saved unless the user manually edits the color.
240
- *
241
- * Ignored if `customRepresentation` is set.
242
- */
243
- stringPrecision?: number
244
- /** Allows overriding the string representation of the color. Useful for using a different representation than rgba (e.g. hex). The fromStringToHsva part is rarely needed as the colorjs.io library can normally parse the color. Returning undefined signals an error. */
245
- customRepresentation?: {
246
- fromHsvaToString: (hsva: HsvaColor, includeAlpha: boolean) => string
247
- fromStringToHsva?: (string: string) => HsvaColor | undefined
248
- }
249
- border?: boolean
250
- /** Modify what the user copies to the clipboard. */
251
- copyTransform?: (val: HsvaColor, stringVal: string) => any
252
- valid?: boolean
253
- }>(), {
254
- allowAlpha: true,
255
- border: true,
256
- stringPrecision: 3,
257
- copyTransform: (_val: HsvaColor, stringVal: string) => stringVal,
258
- customRepresentation: undefined,
259
- valid: true,
260
- })
261
-
262
-
263
- const ariaDescription = t("color-picker.aria.description")
264
- const fallbackId = getFallbackId()
265
-
266
- const $value = defineModel<RgbaColor>({ required: false, default: () => ({ r: 0, g: 0, b: 0 }) })
267
- const $tempValue = defineModel<RgbaColor | undefined>("tempValue", { required: false, default: () => (undefined) })
268
-
269
- const pickerEl = ref<HTMLCanvasElement | null>(null)
270
- const hueSliderEl = ref<HTMLCanvasElement | null>(null)
271
- const alphaSliderEl = ref<HTMLCanvasElement | null>(null)
272
-
273
- type Config = Record<string, {
274
- el: Ref<HTMLCanvasElement>
275
- xKey?: keyof HsvaColor
276
- yKey?: keyof HsvaColor
277
- xSteps?: number
278
- ySteps?: number
279
- }>
280
-
281
- const config: Config = {
282
- hue: {
283
- el: hueSliderEl as Ref<HTMLCanvasElement>,
284
- xKey: "h",
285
- xSteps: 360,
286
- },
287
- alpha: {
288
- el: alphaSliderEl as Ref<HTMLCanvasElement>,
289
- xSteps: 1,
290
- xKey: "a",
291
- },
292
- all: {
293
- el: pickerEl as Ref<HTMLCanvasElement>,
294
- xSteps: 100,
295
- ySteps: 100,
296
- xKey: "s",
297
- yKey: "v",
298
- },
299
- }
300
-
301
- const localColor = reactive<Record<"percent" | "val", HsvaColor>>({
302
- percent: {
303
- h: 0, s: 0, v: 0, a: 0,
304
- },
305
- val: {
306
- h: 0, s: 0, v: 0, a: 0,
307
- },
308
- })
309
-
310
-
217
+ `;
218
+ const emits = defineEmits(["save", "cancel"]);
219
+ const props = defineProps({
220
+ label: { type: String, required: false },
221
+ id: { type: String, required: false },
222
+ allowAlpha: { type: Boolean, required: false, default: true },
223
+ stringPrecision: { type: Number, required: false, default: 3 },
224
+ customRepresentation: { type: Object, required: false, default: void 0 },
225
+ border: { type: Boolean, required: false, default: true },
226
+ copyTransform: { type: Function, required: false, default: (_val, stringVal) => stringVal },
227
+ valid: { type: Boolean, required: false, default: true }
228
+ });
229
+ const ariaDescription = t("color-picker.aria.description");
230
+ const fallbackId = getFallbackId();
231
+ const $value = defineModel({ type: Object, ...{ required: false, default: () => ({ r: 0, g: 0, b: 0 }) } });
232
+ const $tempValue = defineModel("tempValue", { type: null, ...{ required: false, default: () => void 0 } });
233
+ const pickerEl = ref(null);
234
+ const hueSliderEl = ref(null);
235
+ const alphaSliderEl = ref(null);
236
+ const config = {
237
+ hue: {
238
+ el: hueSliderEl,
239
+ xKey: "h",
240
+ xSteps: 360
241
+ },
242
+ alpha: {
243
+ el: alphaSliderEl,
244
+ xSteps: 1,
245
+ xKey: "a"
246
+ },
247
+ all: {
248
+ el: pickerEl,
249
+ xSteps: 100,
250
+ ySteps: 100,
251
+ xKey: "s",
252
+ yKey: "v"
253
+ }
254
+ };
255
+ const localColor = reactive({
256
+ percent: {
257
+ h: 0,
258
+ s: 0,
259
+ v: 0,
260
+ a: 0
261
+ },
262
+ val: {
263
+ h: 0,
264
+ s: 0,
265
+ v: 0,
266
+ a: 0
267
+ }
268
+ });
311
269
  const asRgba = computed(() => {
312
- const rgba = safeConvertToRgba(localColor.val, props.allowAlpha)
313
- if (!rgba) unreachable()
314
- return rgba
315
- })
270
+ const rgba = safeConvertToRgba(localColor.val, props.allowAlpha);
271
+ if (!rgba) unreachable();
272
+ return rgba;
273
+ });
316
274
  const asRgbaString = computed(() => {
317
- const rgba = asRgba.value
318
- if (!rgba) unreachable()
319
- return `rgba(${rgba.r}, ${rgba.g}, ${rgba.b}, ${rgba.a})`
320
- })
275
+ const rgba = asRgba.value;
276
+ if (!rgba) unreachable();
277
+ return `rgba(${rgba.r}, ${rgba.g}, ${rgba.b}, ${rgba.a})`;
278
+ });
321
279
  const localColorString = computed(() => {
322
- if (props.customRepresentation) {
323
- return props.customRepresentation.fromHsvaToString({ ...localColor.val }, props.allowAlpha)
324
- }
325
- return toLowPrecisionRgbaString(asRgba.value, props.allowAlpha, props.stringPrecision)
326
- })
327
-
328
- const localInputString = ref(localColorString.value)
329
- // fixes the localInputString not updating when the user inputs an invalid value
280
+ if (props.customRepresentation) {
281
+ return props.customRepresentation.fromHsvaToString({ ...localColor.val }, props.allowAlpha);
282
+ }
283
+ return toLowPrecisionRgbaString(asRgba.value, props.allowAlpha, props.stringPrecision);
284
+ });
285
+ const localInputString = ref(localColorString.value);
330
286
  function onBlurFixInvalidValue() {
331
- if (localInputString.value !== localColorString.value) {
332
- localInputString.value = localColorString.value
333
- }
287
+ if (localInputString.value !== localColorString.value) {
288
+ localInputString.value = localColorString.value;
289
+ }
334
290
  }
335
-
336
- function updatePicker(el: HTMLCanvasElement, hue: number): void {
337
- const ctx = el.getContext("2d")!
338
- const { height, width } = el
339
- ctx.clearRect(0, 0, width, height)
340
-
341
- const gradient = ctx.createLinearGradient(0, 0, 0, height)
342
- gradient.addColorStop(0, "white")
343
- gradient.addColorStop(1, "black")
344
- const gradientColor = ctx.createLinearGradient(0, 0, width, 0)
345
- gradientColor.addColorStop(0, `hsla(${hue} 100% 50% / 0)`)
346
- gradientColor.addColorStop(1, `hsla(${hue} 100% 50% /1)`)
347
-
348
-
349
- ctx.fillStyle = gradient
350
- ctx.fillRect(0, 0, width, height)
351
- ctx.fillStyle = gradientColor
352
- ctx.globalCompositeOperation = "multiply"
353
- ctx.fillRect(0, 0, width, height)
354
- ctx.globalCompositeOperation = "source-over"
291
+ function updatePicker(el, hue) {
292
+ const ctx = el.getContext("2d");
293
+ const { height, width } = el;
294
+ ctx.clearRect(0, 0, width, height);
295
+ const gradient = ctx.createLinearGradient(0, 0, 0, height);
296
+ gradient.addColorStop(0, "white");
297
+ gradient.addColorStop(1, "black");
298
+ const gradientColor = ctx.createLinearGradient(0, 0, width, 0);
299
+ gradientColor.addColorStop(0, `hsla(${hue} 100% 50% / 0)`);
300
+ gradientColor.addColorStop(1, `hsla(${hue} 100% 50% /1)`);
301
+ ctx.fillStyle = gradient;
302
+ ctx.fillRect(0, 0, width, height);
303
+ ctx.fillStyle = gradientColor;
304
+ ctx.globalCompositeOperation = "multiply";
305
+ ctx.fillRect(0, 0, width, height);
306
+ ctx.globalCompositeOperation = "source-over";
355
307
  }
356
-
357
- function updateSlider(el: HTMLCanvasElement, stops: ((i: number) => string) | string[], length: number = 360): void {
358
- const ctx = el.getContext("2d")!
359
- const { height, width } = el
360
- ctx.clearRect(0, 0, width, height)
361
-
362
- const end = isArray(stops) ? stops.length - 1 : length
363
-
364
- const gradient = ctx.createLinearGradient(0, 0, width, 0)
365
-
366
- for (let i = 0; i < end + 1; i++) {
367
- const stop = stops instanceof Function ? stops(i) : stops[i]
368
- if (stop === undefined) unreachable()
369
- gradient.addColorStop(i / end, stop)
370
- }
371
-
372
- ctx.fillStyle = gradient
373
- ctx.fillRect(0, 0, width, height)
308
+ function updateSlider(el, stops, length = 360) {
309
+ const ctx = el.getContext("2d");
310
+ const { height, width } = el;
311
+ ctx.clearRect(0, 0, width, height);
312
+ const end = isArray(stops) ? stops.length - 1 : length;
313
+ const gradient = ctx.createLinearGradient(0, 0, width, 0);
314
+ for (let i = 0; i < end + 1; i++) {
315
+ const stop = stops instanceof Function ? stops(i) : stops[i];
316
+ if (stop === void 0) unreachable();
317
+ gradient.addColorStop(i / end, stop);
318
+ }
319
+ ctx.fillStyle = gradient;
320
+ ctx.fillRect(0, 0, width, height);
374
321
  }
375
-
376
-
377
- function getVal(x: number, width: number, steps: number = 100, accuracy: number = 100, reverse = false): { val: number, percent: number } {
378
- const percent = (x / width)
379
- const unrounded = percent * steps
380
-
381
- const val = Math.round(unrounded * accuracy) / accuracy
382
- const percentVal = steps === accuracy ? val : Math.round(percent * 100 * accuracy) / accuracy
383
- const res = { val, percent: percentVal }
384
- if (reverse) res.val = steps - val
385
- return res
322
+ function getVal(x, width, steps = 100, accuracy = 100, reverse = false) {
323
+ const percent = x / width;
324
+ const unrounded = percent * steps;
325
+ const val = Math.round(unrounded * accuracy) / accuracy;
326
+ const percentVal = steps === accuracy ? val : Math.round(percent * 100 * accuracy) / accuracy;
327
+ const res = { val, percent: percentVal };
328
+ if (reverse) res.val = steps - val;
329
+ return res;
386
330
  }
387
-
388
- type Types = keyof UnwrapRef<Config>
389
- const elDragging = ref<Types | "">("")
390
- let dragging = false
391
-
392
- function moveHandle(e: { clientX: number, clientY: number }, type: string) {
393
- requestAnimationFrame(() => {
394
- if (type === "") return
395
- const el = config[type]?.el.value
396
- if (!el || !config[type]) return
397
- const { x, y, width, height } = el.getBoundingClientRect()
398
-
399
- const info = config[type]
400
- if (info.xKey !== undefined) {
401
- let newPosX = e.clientX - x
402
- newPosX = newPosX < 0 ? 0 : newPosX > width ? width : newPosX
403
- const newX = getVal(newPosX, width, info.xSteps ?? 100)
404
-
405
- localColor.percent[info.xKey] = newX.percent
406
- localColor.val[info.xKey] = newX.val
407
- }
408
-
409
- if (info.yKey !== undefined) {
410
- let newPosY = e.clientY - y
411
- newPosY = newPosY < 0 ? 0 : newPosY > height ? height : newPosY
412
- const newY = getVal(newPosY, height, info.ySteps ?? 100, 100, true)
413
-
414
- localColor.percent[info.yKey] = newY.percent
415
- localColor.val[info.yKey] = newY.val
416
- }
417
- })
331
+ const elDragging = ref("");
332
+ let dragging = false;
333
+ function moveHandle(e, type) {
334
+ requestAnimationFrame(() => {
335
+ if (type === "") return;
336
+ const el = config[type]?.el.value;
337
+ if (!el || !config[type]) return;
338
+ const { x, y, width, height } = el.getBoundingClientRect();
339
+ const info = config[type];
340
+ if (info.xKey !== void 0) {
341
+ let newPosX = e.clientX - x;
342
+ newPosX = newPosX < 0 ? 0 : newPosX > width ? width : newPosX;
343
+ const newX = getVal(newPosX, width, info.xSteps ?? 100);
344
+ localColor.percent[info.xKey] = newX.percent;
345
+ localColor.val[info.xKey] = newX.val;
346
+ }
347
+ if (info.yKey !== void 0) {
348
+ let newPosY = e.clientY - y;
349
+ newPosY = newPosY < 0 ? 0 : newPosY > height ? height : newPosY;
350
+ const newY = getVal(newPosY, height, info.ySteps ?? 100, 100, true);
351
+ localColor.percent[info.yKey] = newY.percent;
352
+ localColor.val[info.yKey] = newY.val;
353
+ }
354
+ });
418
355
  }
419
356
  const slider = {
420
- keydown: (e: KeyboardEvent, type: Types) => {
421
- castType<HTMLElement | undefined>(e.target)
422
- if (e.target?.getBoundingClientRect) {
423
- if (["ArrowRight", "ArrowLeft", "ArrowUp", "ArrowDown"].includes(e.key)) {
424
- e.preventDefault()
425
- const { x, y, width, height } = e.target.getBoundingClientRect()
426
- let xDiff = e.key === "ArrowRight" ? 1 : e.key === "ArrowLeft" ? -1 : 0
427
- let yDiff = e.key === "ArrowUp" ? -1 : e.key === "ArrowDown" ? 1 : 0
428
- if (e.shiftKey) {xDiff *= 10}
429
- if (e.shiftKey) {yDiff *= 10}
430
- moveHandle({ clientX: x + (width / 2) + xDiff, clientY: y + (height / 2) + yDiff }, type)
431
- }
432
- if (e.key === "Enter") {
433
- e.preventDefault()
434
- save()
435
- }
436
- }
437
- },
438
- pointerdown: (e: PointerEvent, type: Types) => {
439
- const focusTargetClass = `#${props.id ?? fallbackId} .color-picker--${type}-handle`
440
- const focusTarget = document.querySelector(focusTargetClass)
441
- // allows enter to work when the user drags any slider as the even will be captured by the keydown listener
442
- if (focusTarget instanceof HTMLElement) focusTarget.focus()
443
-
444
- if (dragging) return
445
- e.preventDefault()
446
- elDragging.value = type
447
- dragging = true
448
- document.addEventListener("pointermove", slider.pointermove)
449
- document.addEventListener("pointerup", slider.pointerup)
450
- moveHandle(e, elDragging.value)
451
- },
452
- pointerleave: (e: PointerEvent) => {
453
- if (dragging) {
454
- e.preventDefault()
455
- }
456
- },
457
- pointermove: (e: PointerEvent) => {
458
- e.preventDefault()
459
- moveHandle(e, elDragging.value)
460
- },
461
- pointerup: (e: PointerEvent) => {
462
- e.preventDefault()
463
- dragging = false
464
- elDragging.value = ""
465
- document.removeEventListener("pointermove", slider.pointermove)
466
- document.removeEventListener("pointerup", slider.pointerup)
467
- },
468
- }
469
- function updateSliders(_: HsvaColor): void {
470
- if (alphaSliderEl.value) {
471
- // https://colorjs.io/docs/output#get-a-displayable-css-color-value
472
- const color = new Color("hsv", [_.h, _.s, _.v], _.a).to("hsl")
473
- const hsl0 = color.clone()
474
- hsl0.alpha = 0
475
- const hsl1 = color.clone()
476
- hsl1.alpha = 1
477
- updateSlider(alphaSliderEl.value, [hsl0.toString(), hsl1.toString()])
478
- }
479
- updateSlider(hueSliderEl.value!, i => `hsl(${i} 100% 50%)`)
480
- updatePicker(pickerEl.value!, _.h)
357
+ keydown: (e, type) => {
358
+ castType(e.target);
359
+ if (e.target?.getBoundingClientRect) {
360
+ if (["ArrowRight", "ArrowLeft", "ArrowUp", "ArrowDown"].includes(e.key)) {
361
+ e.preventDefault();
362
+ const { x, y, width, height } = e.target.getBoundingClientRect();
363
+ let xDiff = e.key === "ArrowRight" ? 1 : e.key === "ArrowLeft" ? -1 : 0;
364
+ let yDiff = e.key === "ArrowUp" ? -1 : e.key === "ArrowDown" ? 1 : 0;
365
+ if (e.shiftKey) {
366
+ xDiff *= 10;
367
+ }
368
+ if (e.shiftKey) {
369
+ yDiff *= 10;
370
+ }
371
+ moveHandle({ clientX: x + width / 2 + xDiff, clientY: y + height / 2 + yDiff }, type);
372
+ }
373
+ if (e.key === "Enter") {
374
+ e.preventDefault();
375
+ save();
376
+ }
377
+ }
378
+ },
379
+ pointerdown: (e, type) => {
380
+ const focusTargetClass = `#${props.id ?? fallbackId} .color-picker--${type}-handle`;
381
+ const focusTarget = document.querySelector(focusTargetClass);
382
+ if (focusTarget instanceof HTMLElement) focusTarget.focus();
383
+ if (dragging) return;
384
+ e.preventDefault();
385
+ elDragging.value = type;
386
+ dragging = true;
387
+ document.addEventListener("pointermove", slider.pointermove);
388
+ document.addEventListener("pointerup", slider.pointerup);
389
+ moveHandle(e, elDragging.value);
390
+ },
391
+ pointerleave: (e) => {
392
+ if (dragging) {
393
+ e.preventDefault();
394
+ }
395
+ },
396
+ pointermove: (e) => {
397
+ e.preventDefault();
398
+ moveHandle(e, elDragging.value);
399
+ },
400
+ pointerup: (e) => {
401
+ e.preventDefault();
402
+ dragging = false;
403
+ elDragging.value = "";
404
+ document.removeEventListener("pointermove", slider.pointermove);
405
+ document.removeEventListener("pointerup", slider.pointerup);
406
+ }
407
+ };
408
+ function updateSliders(_) {
409
+ if (alphaSliderEl.value) {
410
+ const color = new Color("hsv", [_.h, _.s, _.v], _.a).to("hsl");
411
+ const hsl0 = color.clone();
412
+ hsl0.alpha = 0;
413
+ const hsl1 = color.clone();
414
+ hsl1.alpha = 1;
415
+ updateSlider(alphaSliderEl.value, [hsl0.toString(), hsl1.toString()]);
416
+ }
417
+ updateSlider(hueSliderEl.value, (i) => `hsl(${i} 100% 50%)`);
418
+ updatePicker(pickerEl.value, _.h);
481
419
  }
482
-
483
- function updateValueAndPosition(_: HsvaColor): void {
484
- localColor.percent.h = Math.round((_.h / 360) * 10000) / 100
485
- localColor.percent.s = _.s
486
- localColor.percent.v = 100 - _.v
487
- localColor.percent.a =
488
- props.allowAlpha
489
- ? _.a !== undefined
490
- ? _.a * 100
491
- : 1
492
- : 1
493
- localColor.val = { ..._, a: props.allowAlpha ? _.a : 1 }
420
+ function updateValueAndPosition(_) {
421
+ localColor.percent.h = Math.round(_.h / 360 * 1e4) / 100;
422
+ localColor.percent.s = _.s;
423
+ localColor.percent.v = 100 - _.v;
424
+ localColor.percent.a = props.allowAlpha ? _.a !== void 0 ? _.a * 100 : 1 : 1;
425
+ localColor.val = { ..._, a: props.allowAlpha ? _.a : 1 };
494
426
  }
495
-
496
- function convertAndUpdateAll(rgba: RgbaColor) {
497
- const hsva = safeConvertToHsva(rgba, props.allowAlpha)
498
- if (!hsva) return
499
- updateSliders(hsva)
500
- updateValueAndPosition(hsva)
427
+ function convertAndUpdateAll(rgba) {
428
+ const hsva = safeConvertToHsva(rgba, props.allowAlpha);
429
+ if (!hsva) return;
430
+ updateSliders(hsva);
431
+ updateValueAndPosition(hsva);
501
432
  }
502
-
503
- function save(): void {
504
- const rgba = safeConvertToRgba(localColor.val, props.allowAlpha)
505
- if (!rgba) return
506
- // update(localColor.val, { updatePosition: false, updateValue: false })
507
- $value.value = rgba
508
- $tempValue.value = undefined
509
- emits("save", rgba)
433
+ function save() {
434
+ const rgba = safeConvertToRgba(localColor.val, props.allowAlpha);
435
+ if (!rgba) return;
436
+ $value.value = rgba;
437
+ $tempValue.value = void 0;
438
+ emits("save", rgba);
510
439
  }
511
-
512
-
513
- function parseInput(e: Event): void {
514
- const val = (e.target as HTMLInputElement)?.value
515
- const converted = props.customRepresentation?.fromStringToHsva
516
- ? props.customRepresentation.fromStringToHsva(val)
517
- : safeConvertToHsva(val, props.allowAlpha)
518
- if (converted) {
519
- updateSliders(converted)
520
- updateValueAndPosition(converted)
521
- }
440
+ function parseInput(e) {
441
+ const val = e.target?.value;
442
+ const converted = props.customRepresentation?.fromStringToHsva ? props.customRepresentation.fromStringToHsva(val) : safeConvertToHsva(val, props.allowAlpha);
443
+ if (converted) {
444
+ updateSliders(converted);
445
+ updateValueAndPosition(converted);
446
+ }
522
447
  }
523
-
524
-
525
- let disableUpdateTempValue = false
526
-
448
+ let disableUpdateTempValue = false;
527
449
  onMounted(() => {
528
- convertAndUpdateAll($value.value)
529
- if ($tempValue.value !== undefined) {
530
- convertAndUpdateAll($tempValue.value)
531
- }
532
-
533
- const handle = document.querySelector(`#${props.id ?? fallbackId} .color-picker--all-handle`)
534
- if (handle instanceof HTMLElement) handle.focus()
535
- })
536
-
450
+ convertAndUpdateAll($value.value);
451
+ if ($tempValue.value !== void 0) {
452
+ convertAndUpdateAll($tempValue.value);
453
+ }
454
+ const handle = document.querySelector(`#${props.id ?? fallbackId} .color-picker--all-handle`);
455
+ if (handle instanceof HTMLElement) handle.focus();
456
+ });
537
457
  watch($value, () => {
538
- convertAndUpdateAll($value.value)
539
- })
540
-
458
+ convertAndUpdateAll($value.value);
459
+ });
541
460
  watch($tempValue, () => {
542
- if ($tempValue.value !== undefined) {
543
- disableUpdateTempValue = true
544
- convertAndUpdateAll($tempValue.value)
545
- setTimeout(() => { disableUpdateTempValue = false }, 0)
546
- }
547
- })
548
-
461
+ if ($tempValue.value !== void 0) {
462
+ disableUpdateTempValue = true;
463
+ convertAndUpdateAll($tempValue.value);
464
+ setTimeout(() => {
465
+ disableUpdateTempValue = false;
466
+ }, 0);
467
+ }
468
+ });
549
469
  watch(localColor, () => {
550
- updateSliders(localColor.val)
551
- localInputString.value = localColorString.value
552
- if (disableUpdateTempValue) return
553
- const rgba = safeConvertToRgba(localColor.val, props.allowAlpha)
554
- if (!rgba) return
555
- $tempValue.value = rgba
556
- })
557
-
558
- const invertColors = computed(() => !!(localColor.percent.v < 50 || (localColor.val.a === undefined || localColor.val.a < 0.5)))
470
+ updateSliders(localColor.val);
471
+ localInputString.value = localColorString.value;
472
+ if (disableUpdateTempValue) return;
473
+ const rgba = safeConvertToRgba(localColor.val, props.allowAlpha);
474
+ if (!rgba) return;
475
+ $tempValue.value = rgba;
476
+ });
477
+ const invertColors = computed(() => !!(localColor.percent.v < 50 || (localColor.val.a === void 0 || localColor.val.a < 0.5)));
559
478
  </script>