poe-svelte-ui-lib 1.0.1 → 1.0.4

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 (61) hide show
  1. package/LICENSE +3 -3
  2. package/README.md +1 -0
  3. package/dist/Accordion/Accordion.svelte +53 -53
  4. package/dist/Button/Button.svelte +111 -144
  5. package/dist/Button/Button.svelte.d.ts +1 -34
  6. package/dist/ColorPicker/ColorPicker.svelte +205 -207
  7. package/dist/FileAttach/FileAttach.svelte +103 -103
  8. package/dist/Graph/Graph.svelte +270 -270
  9. package/dist/Input/Input.svelte +240 -239
  10. package/dist/Loader.svelte +12 -12
  11. package/dist/MessageModal.svelte +54 -54
  12. package/dist/ProgressBar/ProgressBar.svelte +48 -48
  13. package/dist/Select/Select.svelte +189 -191
  14. package/dist/Slider/Slider.svelte +260 -260
  15. package/dist/Switch/Switch.svelte +84 -83
  16. package/dist/Table/Table.svelte +275 -276
  17. package/dist/TextField/TextField.svelte +22 -22
  18. package/dist/index.d.ts +0 -11
  19. package/dist/index.js +0 -11
  20. package/dist/{appIcons → libIcons}/ButtonAdd.svelte +10 -10
  21. package/dist/{appIcons → libIcons}/ButtonDelete.svelte +13 -13
  22. package/dist/{appIcons → libIcons}/LoaderRotate.svelte +9 -9
  23. package/dist/options.d.ts +11 -11
  24. package/dist/options.js +27 -27
  25. package/dist/types.d.ts +1 -1
  26. package/package.json +48 -47
  27. package/dist/Accordion/AccordionProps.svelte +0 -70
  28. package/dist/Accordion/AccordionProps.svelte.d.ts +0 -10
  29. package/dist/Button/ButtonProps.svelte +0 -200
  30. package/dist/Button/ButtonProps.svelte.d.ts +0 -10
  31. package/dist/ColorPicker/ColorPickerProps.svelte +0 -100
  32. package/dist/ColorPicker/ColorPickerProps.svelte.d.ts +0 -10
  33. package/dist/Graph/GraphProps.svelte +0 -56
  34. package/dist/Graph/GraphProps.svelte.d.ts +0 -10
  35. package/dist/Input/InputProps.svelte +0 -221
  36. package/dist/Input/InputProps.svelte.d.ts +0 -10
  37. package/dist/ProgressBar/ProgressBarProps.svelte +0 -145
  38. package/dist/ProgressBar/ProgressBarProps.svelte.d.ts +0 -10
  39. package/dist/Select/SelectProps.svelte +0 -260
  40. package/dist/Select/SelectProps.svelte.d.ts +0 -10
  41. package/dist/Slider/SliderProps.svelte +0 -161
  42. package/dist/Slider/SliderProps.svelte.d.ts +0 -10
  43. package/dist/Switch/SwitchProps.svelte +0 -144
  44. package/dist/Switch/SwitchProps.svelte.d.ts +0 -10
  45. package/dist/Table/TableProps.svelte +0 -286
  46. package/dist/Table/TableProps.svelte.d.ts +0 -10
  47. package/dist/TextField/TextFieldProps.svelte +0 -92
  48. package/dist/TextField/TextFieldProps.svelte.d.ts +0 -10
  49. package/dist/locales/CircleFlagsEn.svelte +0 -14
  50. package/dist/locales/CircleFlagsEn.svelte.d.ts +0 -26
  51. package/dist/locales/CircleFlagsRu.svelte +0 -8
  52. package/dist/locales/CircleFlagsRu.svelte.d.ts +0 -26
  53. package/dist/locales/CircleFlagsZh.svelte +0 -8
  54. package/dist/locales/CircleFlagsZh.svelte.d.ts +0 -26
  55. package/dist/locales/i18n.d.ts +0 -10
  56. package/dist/locales/i18n.js +0 -36
  57. package/dist/locales/translations.d.ts +0 -7
  58. package/dist/locales/translations.js +0 -450
  59. /package/dist/{appIcons → libIcons}/ButtonAdd.svelte.d.ts +0 -0
  60. /package/dist/{appIcons → libIcons}/ButtonDelete.svelte.d.ts +0 -0
  61. /package/dist/{appIcons → libIcons}/LoaderRotate.svelte.d.ts +0 -0
@@ -1,48 +1,48 @@
1
- <!-- $lib/ElementsUI/ProgressBar.svelte -->
2
- <script lang="ts">
3
- import type { IProgressBarProps } from '../types'
4
-
5
- let {
6
- id = { name: '', value: crypto.randomUUID() },
7
- label = { name: '', class: '' },
8
- value = $bindable(0),
9
- range = {
10
- min: 0,
11
- max: 100,
12
- units: '%',
13
- },
14
- wrapperClass = '',
15
- }: IProgressBarProps = $props()
16
-
17
- let numericValue = $state(0)
18
- const min = $derived(range.min ?? 0)
19
- const max = $derived(range.max ?? 100)
20
-
21
- $effect(() => {
22
- if (typeof value === 'number' && !isNaN(value)) {
23
- numericValue = Math.max(min, Math.min(max, value))
24
- } else if (typeof value === 'string') {
25
- const parsedValue = parseFloat(value)
26
- if (!isNaN(parsedValue)) {
27
- numericValue = Math.max(min, Math.min(max, parsedValue))
28
- }
29
- } else {
30
- numericValue = min
31
- }
32
- })
33
-
34
- let progressPercent = $derived((((value as number) - min) / (max - min)) * 100)
35
- </script>
36
-
37
- <div id={id.value} class={`relative flex w-full flex-col items-center ${wrapperClass}`}>
38
- {#if label.name}
39
- <h5 class={`mb-1 w-full px-4 text-center ${label.class}`}>{label.name}</h5>
40
- {/if}
41
-
42
- <div class="flex w-full flex-col items-center">
43
- <div class="relative h-2 w-full rounded bg-gray-400">
44
- <div class="absolute top-0 left-0 h-full rounded bg-[var(--bg-color)]" style="width: {progressPercent}%;"></div>
45
- </div>
46
- <span class="ml-2 font-semibold">{numericValue.toFixed(2)}{range.units}</span>
47
- </div>
48
- </div>
1
+ <!-- $lib/ElementsUI/ProgressBar.svelte -->
2
+ <script lang="ts">
3
+ import type { IProgressBarProps } from '../types'
4
+
5
+ let {
6
+ id = { name: '', value: crypto.randomUUID() },
7
+ label = { name: '', class: '' },
8
+ value = $bindable(0),
9
+ range = {
10
+ min: 0,
11
+ max: 100,
12
+ units: '%',
13
+ },
14
+ wrapperClass = '',
15
+ }: IProgressBarProps = $props()
16
+
17
+ let numericValue = $state(0)
18
+ const min = $derived(range.min ?? 0)
19
+ const max = $derived(range.max ?? 100)
20
+
21
+ $effect(() => {
22
+ if (typeof value === 'number' && !isNaN(value)) {
23
+ numericValue = Math.max(min, Math.min(max, value))
24
+ } else if (typeof value === 'string') {
25
+ const parsedValue = parseFloat(value)
26
+ if (!isNaN(parsedValue)) {
27
+ numericValue = Math.max(min, Math.min(max, parsedValue))
28
+ }
29
+ } else {
30
+ numericValue = min
31
+ }
32
+ })
33
+
34
+ let progressPercent = $derived((((value as number) - min) / (max - min)) * 100)
35
+ </script>
36
+
37
+ <div id={id.value} class={`relative flex w-full flex-col items-center ${wrapperClass}`}>
38
+ {#if label.name}
39
+ <h5 class={`mb-1 w-full px-4 text-center ${label.class}`}>{label.name}</h5>
40
+ {/if}
41
+
42
+ <div class="flex w-full flex-col items-center">
43
+ <div class="relative h-2 w-full rounded bg-gray-400">
44
+ <div class="absolute top-0 left-0 h-full rounded bg-[var(--bg-color)]" style="width: {progressPercent}%;"></div>
45
+ </div>
46
+ <span class="ml-2 font-semibold">{numericValue.toFixed(2)}{range.units}</span>
47
+ </div>
48
+ </div>
@@ -1,191 +1,189 @@
1
- <!-- $lib/ElementUI/Select.svelte -->
2
- <script lang="ts" generics="T = unknown">
3
- import { slide } from 'svelte/transition'
4
- import { onMount } from 'svelte'
5
- import type { ISelectOption, ISelectProps } from '../types'
6
- import { t } from '../locales/i18n'
7
-
8
- let isDropdownOpen = $state(false)
9
- let dropdownElement: HTMLDivElement
10
-
11
- let searchValue = $state('')
12
- let filteredOptions = $state<ISelectOption<T>[]>([])
13
-
14
- let {
15
- id = { name: '', value: crypto.randomUUID() },
16
- wrapperClass = 'bg-max',
17
- disabled = false,
18
- label = { name: '', class: '' },
19
- type = 'select',
20
- value = $bindable(),
21
- options = [],
22
- onUpdate,
23
- }: ISelectProps<T> = $props()
24
-
25
- /* Закрытие при клике вне компонента */
26
- const handleClickOutside = (event: MouseEvent) => {
27
- if (dropdownElement && !dropdownElement.contains(event.target as Node)) {
28
- isDropdownOpen = false
29
- }
30
- }
31
-
32
- onMount(() => {
33
- if (type === 'select' || type === 'input') document.addEventListener('click', handleClickOutside)
34
- if (type === 'input') searchValue = value?.name ?? ''
35
- return () => {
36
- if (type === 'select' || type === 'input') document.removeEventListener('click', handleClickOutside)
37
- }
38
- })
39
-
40
- const toggleDropdown = (event: MouseEvent) => {
41
- event.stopPropagation()
42
- if (!disabled) {
43
- isDropdownOpen = !isDropdownOpen
44
- filteredOptions = []
45
- }
46
- }
47
-
48
- const selectOption = (option: ISelectOption<T>, event: MouseEvent) => {
49
- event.stopPropagation()
50
- if (!disabled) {
51
- value = option
52
- isDropdownOpen = false
53
- searchValue = option.name?.toString() ?? ''
54
- filteredOptions = []
55
- onUpdate?.(value)
56
- }
57
- }
58
-
59
- const handleSearch = (inputValue: string) => {
60
- searchValue = inputValue
61
-
62
- if (inputValue.trim() === '') {
63
- isDropdownOpen = false
64
- filteredOptions = []
65
- } else {
66
- filteredOptions = options.filter((option) => {
67
- const optionName = option.name?.toString() || ''
68
- return optionName.toLowerCase().includes(inputValue.toLowerCase())
69
- })
70
- isDropdownOpen = filteredOptions.length > 0
71
-
72
- const selectedFromList = options.some((option) => option.name?.toString() === searchValue)
73
- console.log(selectedFromList)
74
-
75
- if (!selectedFromList) {
76
- const newOption: ISelectOption<T> = {
77
- id: `input-${searchValue}`,
78
- name: searchValue,
79
- value: searchValue as T,
80
- }
81
-
82
- value = newOption
83
- onUpdate?.(newOption)
84
- }
85
- }
86
- }
87
- </script>
88
-
89
- <div class={`bg-max relative flex w-full flex-col items-center ${wrapperClass}`} bind:this={dropdownElement}>
90
- {#if label.name}
91
- <h5 class={`w-full px-4 ${label.class}`}>{label.name}</h5>
92
- {/if}
93
- {#if type === 'select'}
94
- <button
95
- id={id.value}
96
- value={value?.value ? String(value.value) : ''}
97
- class="w-full rounded-2xl border border-[var(--border-color)] p-1 text-center duration-250
98
- {value?.class} {disabled ? 'opacity-50' : 'cursor-pointer hover:shadow-lg'}"
99
- style="background: color-mix(in srgb, var(--bg-color), var(--back-color) 70%);"
100
- onclick={toggleDropdown}
101
- aria-haspopup="true"
102
- aria-expanded={isDropdownOpen}
103
- {disabled}
104
- >
105
- {value?.name || $t('common.select_tag')}
106
- </button>
107
-
108
- {#if isDropdownOpen}
109
- <div
110
- class="absolute top-full left-1/2 z-50 -translate-x-1/2 rounded-b-2xl border border-t-0 border-[var(--border-color)]"
111
- style="width: calc(100% - 1.8rem);"
112
- transition:slide={{ duration: 250 }}
113
- >
114
- {#each options as option, index (option.id)}
115
- <button
116
- id={option.id}
117
- value={option?.value ? String(option.value) : ''}
118
- class="flex h-full w-full cursor-pointer items-center justify-center p-1 duration-250 hover:!bg-[var(--field-color)]
119
- {option.class} {index === options.length - 1 ? 'rounded-b-2xl' : ''} "
120
- onclick={(e) => selectOption(option, e)}
121
- {disabled}
122
- style="background: color-mix(in srgb, var(--bg-color), var(--back-color) 70%);"
123
- >
124
- {option.name}
125
- </button>
126
- {/each}
127
- </div>
128
- {/if}
129
- {:else if type === 'buttons'}
130
- <div id={id.value} class="flex h-full w-full flex-row justify-center">
131
- {#each options as option, index (option.id)}
132
- <button
133
- id={option.id}
134
- class="m-0 inline-block min-w-0 flex-1 items-center border
135
- border-[var(--border-color)] bg-[var(--bg-color)] px-2 py-1 font-semibold transition-all duration-200 select-none
136
- {option.disabled || disabled ? 'opacity-50' : 'cursor-pointer hover:shadow-lg'}
137
- {option.value === value?.value && value !== null ? 'z-10 text-blue-600 ring-2 ring-[var(--blue-color)]' : ''}
138
- {option.class} {options.length > 0 && index === 0 ? 'rounded-l-2xl' : ''} {index === options.length - 1 ? 'rounded-r-2xl' : ''}"
139
- onclick={(e) => selectOption(option, e)}
140
- disabled={option.disabled}
141
- >
142
- <span class="flex flex-row items-center justify-center gap-4">
143
- {#if option.icon?.component}
144
- {@const IconComponent = option.icon?.component}
145
- <IconComponent {...option.icon?.properties} />
146
- {/if}
147
- {#if option.name}
148
- <div class="flex-1">
149
- {option.name}
150
- </div>
151
- {/if}
152
- </span>
153
- </button>
154
- {/each}
155
- </div>
156
- {:else if type === 'input'}
157
- <input
158
- bind:value={searchValue}
159
- class="w-full appearance-none rounded-2xl border px-4 py-1 text-center transition-shadow
160
- outline-none hover:shadow-md focus:border-blue-400
161
- [&::-webkit-inner-spin-button]:hidden [&::-webkit-outer-spin-button]:hidden
162
- {disabled ? 'cursor-not-allowed opacity-50' : 'cursor-text'} border-[var(--border-color)]"
163
- style="background: color-mix(in srgb, var(--bg-color), var(--back-color) 70%);"
164
- id={id.value}
165
- {disabled}
166
- oninput={(e) => handleSearch((e.currentTarget as HTMLInputElement).value)}
167
- />
168
-
169
- {#if isDropdownOpen}
170
- <div
171
- class="absolute top-full left-1/2 z-50 -translate-x-1/2 rounded-b-2xl border border-t-0 border-[var(--border-color)]"
172
- style="width: calc(100% - 1.8rem);"
173
- transition:slide={{ duration: 250 }}
174
- >
175
- {#each filteredOptions as option, index (option.id)}
176
- <button
177
- id={option.id}
178
- value={option?.value ? String(option.value) : ''}
179
- class="flex h-full w-full cursor-pointer items-center justify-center p-1 duration-250 hover:!bg-[var(--field-color)]
180
- {option.class} {index === filteredOptions.length - 1 ? 'rounded-b-2xl' : ''} "
181
- onclick={(e) => selectOption(option, e)}
182
- {disabled}
183
- style="background: color-mix(in srgb, var(--bg-color), var(--back-color) 70%);"
184
- >
185
- {option.name}
186
- </button>
187
- {/each}
188
- </div>
189
- {/if}
190
- {/if}
191
- </div>
1
+ <!-- $lib/ElementUI/Select.svelte -->
2
+ <script lang="ts" generics="T = unknown">
3
+ import { slide } from 'svelte/transition'
4
+ import { onMount } from 'svelte'
5
+ import type { ISelectOption, ISelectProps } from '../types'
6
+
7
+ let isDropdownOpen = $state(false)
8
+ let dropdownElement: HTMLDivElement
9
+
10
+ let searchValue = $state('')
11
+ let filteredOptions = $state<ISelectOption<T>[]>([])
12
+
13
+ let {
14
+ id = { name: '', value: crypto.randomUUID() },
15
+ wrapperClass = 'bg-max',
16
+ disabled = false,
17
+ label = { name: '', class: '' },
18
+ type = 'select',
19
+ value = $bindable(),
20
+ options = [],
21
+ onUpdate,
22
+ }: ISelectProps<T> = $props()
23
+
24
+ /* Закрытие при клике вне компонента */
25
+ const handleClickOutside = (event: MouseEvent) => {
26
+ if (dropdownElement && !dropdownElement.contains(event.target as Node)) {
27
+ isDropdownOpen = false
28
+ }
29
+ }
30
+
31
+ onMount(() => {
32
+ if (type === 'select' || type === 'input') document.addEventListener('click', handleClickOutside)
33
+ if (type === 'input') searchValue = value?.name ?? ''
34
+ return () => {
35
+ if (type === 'select' || type === 'input') document.removeEventListener('click', handleClickOutside)
36
+ }
37
+ })
38
+
39
+ const toggleDropdown = (event: MouseEvent) => {
40
+ event.stopPropagation()
41
+ if (!disabled) {
42
+ isDropdownOpen = !isDropdownOpen
43
+ filteredOptions = []
44
+ }
45
+ }
46
+
47
+ const selectOption = (option: ISelectOption<T>, event: MouseEvent) => {
48
+ event.stopPropagation()
49
+ if (!disabled) {
50
+ value = option
51
+ isDropdownOpen = false
52
+ searchValue = option.name?.toString() ?? ''
53
+ filteredOptions = []
54
+ onUpdate?.(value)
55
+ }
56
+ }
57
+
58
+ const handleSearch = (inputValue: string) => {
59
+ searchValue = inputValue
60
+
61
+ if (inputValue.trim() === '') {
62
+ isDropdownOpen = false
63
+ filteredOptions = []
64
+ } else {
65
+ filteredOptions = options.filter((option) => {
66
+ const optionName = option.name?.toString() || ''
67
+ return optionName.toLowerCase().includes(inputValue.toLowerCase())
68
+ })
69
+ isDropdownOpen = filteredOptions.length > 0
70
+
71
+ const selectedFromList = options.some((option) => option.name?.toString() === searchValue)
72
+ console.log(selectedFromList)
73
+
74
+ if (!selectedFromList) {
75
+ const newOption: ISelectOption<T> = {
76
+ id: `input-${searchValue}`,
77
+ name: searchValue,
78
+ value: searchValue as T,
79
+ }
80
+
81
+ value = newOption
82
+ onUpdate?.(newOption)
83
+ }
84
+ }
85
+ }
86
+ </script>
87
+
88
+ <div class={`bg-max relative flex w-full flex-col items-center ${wrapperClass}`} bind:this={dropdownElement}>
89
+ {#if label.name}
90
+ <h5 class={`w-full px-4 ${label.class}`}>{label.name}</h5>
91
+ {/if}
92
+ {#if type === 'select'}
93
+ <button
94
+ id={id.value}
95
+ value={value?.value ? String(value.value) : ''}
96
+ class="w-full rounded-2xl border border-[var(--border-color)] p-1 text-center duration-250
97
+ {value?.class} {disabled ? 'opacity-50' : 'cursor-pointer hover:shadow-lg'}"
98
+ style="background: color-mix(in srgb, var(--bg-color), var(--back-color) 70%);"
99
+ onclick={toggleDropdown}
100
+ aria-haspopup="true"
101
+ aria-expanded={isDropdownOpen}
102
+ {disabled}
103
+ >
104
+ {value?.name || ''}
105
+ </button>
106
+
107
+ {#if isDropdownOpen}
108
+ <div
109
+ class="absolute top-full left-1/2 z-50 -translate-x-1/2 rounded-b-2xl border border-t-0 border-[var(--border-color)]"
110
+ style="width: calc(100% - 1.8rem);"
111
+ transition:slide={{ duration: 250 }}
112
+ >
113
+ {#each options as option, index (option.id)}
114
+ <button
115
+ id={option.id}
116
+ value={option?.value ? String(option.value) : ''}
117
+ class="flex h-full w-full cursor-pointer items-center justify-center p-1 duration-250 hover:!bg-[var(--field-color)]
118
+ {option.class} {index === options.length - 1 ? 'rounded-b-2xl' : ''} "
119
+ onclick={(e) => selectOption(option, e)}
120
+ {disabled}
121
+ style="background: color-mix(in srgb, var(--bg-color), var(--back-color) 70%);"
122
+ >
123
+ {option.name}
124
+ </button>
125
+ {/each}
126
+ </div>
127
+ {/if}
128
+ {:else if type === 'buttons'}
129
+ <div id={id.value} class="flex h-full w-full flex-row justify-center">
130
+ {#each options as option, index (option.id)}
131
+ <button
132
+ id={option.id}
133
+ class="m-0 inline-block min-w-0 flex-1 items-center bg-[var(--bg-color)] px-2 py-1 font-semibold shadow-sm transition-all duration-200 select-none
134
+ {option.disabled || disabled ? 'opacity-50' : 'cursor-pointer hover:shadow-md'}
135
+ {option.value === value?.value && value !== null ? 'z-10 !border-[var(--blue-color)] text-cyan-500 ring-3 ring-[var(--blue-color)]' : ''}
136
+ {option.class} {options.length > 0 && index === 0 ? 'rounded-l-2xl' : ''} {index === options.length - 1 ? 'rounded-r-2xl' : ''}"
137
+ onclick={(e) => selectOption(option, e)}
138
+ disabled={option.disabled}
139
+ >
140
+ <span class="flex flex-row items-center justify-center gap-4">
141
+ {#if option.icon?.component}
142
+ {@const IconComponent = option.icon?.component}
143
+ <IconComponent {...option.icon?.properties} />
144
+ {/if}
145
+ {#if option.name}
146
+ <div class="flex-1">
147
+ {option.name}
148
+ </div>
149
+ {/if}
150
+ </span>
151
+ </button>
152
+ {/each}
153
+ </div>
154
+ {:else if type === 'input'}
155
+ <input
156
+ bind:value={searchValue}
157
+ class="w-full appearance-none rounded-2xl border px-4 py-1 text-center transition-shadow
158
+ outline-none hover:shadow-md focus:border-blue-400
159
+ [&::-webkit-inner-spin-button]:hidden [&::-webkit-outer-spin-button]:hidden
160
+ {disabled ? 'cursor-not-allowed opacity-50' : 'cursor-text'} border-[var(--border-color)]"
161
+ style="background: color-mix(in srgb, var(--bg-color), var(--back-color) 70%);"
162
+ id={id.value}
163
+ {disabled}
164
+ oninput={(e) => handleSearch((e.currentTarget as HTMLInputElement).value)}
165
+ />
166
+
167
+ {#if isDropdownOpen}
168
+ <div
169
+ class="absolute top-full left-1/2 z-50 -translate-x-1/2 rounded-b-2xl border border-t-0 border-[var(--border-color)]"
170
+ style="width: calc(100% - 1.8rem);"
171
+ transition:slide={{ duration: 250 }}
172
+ >
173
+ {#each filteredOptions as option, index (option.id)}
174
+ <button
175
+ id={option.id}
176
+ value={option?.value ? String(option.value) : ''}
177
+ class="flex h-full w-full cursor-pointer items-center justify-center p-1 duration-250 hover:!bg-[var(--field-color)]
178
+ {option.class} {index === filteredOptions.length - 1 ? 'rounded-b-2xl' : ''} "
179
+ onclick={(e) => selectOption(option, e)}
180
+ {disabled}
181
+ style="background: color-mix(in srgb, var(--bg-color), var(--back-color) 70%);"
182
+ >
183
+ {option.name}
184
+ </button>
185
+ {/each}
186
+ </div>
187
+ {/if}
188
+ {/if}
189
+ </div>