poe-svelte-ui-lib 1.2.8 → 1.2.10

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.
@@ -66,90 +66,88 @@
66
66
  </script>
67
67
 
68
68
  <div class={twMerge(`relative flex w-full flex-col items-center `, wrapperClass)}>
69
- <div class="relative flex w-full grow items-center">
70
- <button
71
- {id}
72
- class="{twMerge(
73
- `relative m-0 inline-block w-full items-center rounded-2xl
69
+ <button
70
+ {id}
71
+ class="{twMerge(
72
+ `relative m-0 inline-block w-full items-center rounded-2xl
74
73
  px-2 py-1 font-semibold transition duration-200 select-none
75
74
  ${content.icon && !content.name ? 'bg-transparent p-0' : 'bg-blue border border-(--bg-color) '}
76
75
  ${disabled ? 'cursor-not-allowed opacity-50' : 'cursor-pointer active:scale-97'} `,
77
- componentClass,
78
- )} bg-(--bg-color)"
79
- onclick={handleClick}
80
- {disabled}
81
- aria-label={content.name}
82
- onmouseenter={() => {
83
- if (content.info?.text) showInfo = true
84
- }}
85
- onmouseleave={() => {
86
- if (content.info?.text) showInfo = false
87
- }}
88
- >
89
- <span class=" flex flex-row items-center justify-center gap-2">
90
- {#if content?.icon}
91
- <span
92
- class={`flex items-center justify-center overflow-visible
76
+ componentClass,
77
+ )} bg-(--bg-color)"
78
+ onclick={handleClick}
79
+ {disabled}
80
+ aria-label={content.name}
81
+ onmouseenter={() => {
82
+ if (content.info?.text) showInfo = true
83
+ }}
84
+ onmouseleave={() => {
85
+ if (content.info?.text) showInfo = false
86
+ }}
87
+ >
88
+ <span class=" flex flex-row items-center justify-center gap-2">
89
+ {#if content?.icon}
90
+ <span
91
+ class={`flex items-center justify-center overflow-visible
93
92
  ${content.name ? 'h-8 w-8' : `${svgSize()}`} [&_svg]:h-full [&_svg]:max-h-full [&_svg]:w-full [&_svg]:max-w-full`}
94
- >
95
- {#if typeof content?.icon === 'string'}
96
- {@html content.icon}
97
- {:else}
98
- {@const IconComponent = content?.icon}
99
- <IconComponent />
100
- {/if}
101
- </span>
102
- {/if}
93
+ >
94
+ {#if typeof content?.icon === 'string'}
95
+ {@html content.icon}
96
+ {:else}
97
+ {@const IconComponent = content?.icon}
98
+ <IconComponent />
99
+ {/if}
100
+ </span>
101
+ {/if}
103
102
 
104
- {#if content.name}
105
- <div class="flex-1">
106
- {content.name}
107
- {#if keyBind}
108
- <div class="text-xs opacity-70">
109
- ({keyBind.ctrlKey ? 'Ctrl+' : ''}{keyBind.shiftKey ? 'Shift+' : ''}{keyBind.altKey ? 'Alt+' : ''}{keyBind.key})
110
- </div>
111
- {/if}
112
- </div>
113
- {/if}
114
- </span>
115
- </button>
103
+ {#if content.name}
104
+ <div class="flex-1">
105
+ {content.name}
106
+ {#if keyBind}
107
+ <div class="text-xs opacity-70">
108
+ ({keyBind.ctrlKey ? 'Ctrl+' : ''}{keyBind.shiftKey ? 'Shift+' : ''}{keyBind.altKey ? 'Alt+' : ''}{keyBind.key})
109
+ </div>
110
+ {/if}
111
+ </div>
112
+ {/if}
113
+ </span>
114
+ </button>
116
115
 
117
- {#if showInfo && content.info?.side === 'top'}
118
- <div
119
- transition:fly={{ y: -15, duration: 300 }}
120
- class="absolute bottom-full left-1/2 z-50 mb-2 w-max max-w-xs rounded-md bg-(--container-color) px-3 py-1 text-sm shadow-lg"
121
- style="transform: translateX(-50%);"
122
- >
123
- {content.info?.text}
124
- <div class="absolute top-full left-1/2 h-2 w-2 -translate-x-1/2 -translate-y-1/2 rotate-45 transform bg-(--container-color)"></div>
125
- </div>
126
- {:else if showInfo && content.info?.side === 'bottom'}
127
- <div
128
- transition:fly={{ y: 15, duration: 300 }}
129
- class="absolute top-full left-1/2 z-50 mt-2 w-max max-w-xs rounded-md bg-(--container-color) px-3 py-1 text-sm shadow-lg"
130
- style="transform: translateX(-50%);"
131
- >
132
- {content.info?.text}
133
- <div class="absolute bottom-full left-1/2 h-2 w-2 -translate-x-1/2 translate-y-1/2 rotate-45 transform bg-(--container-color)"></div>
134
- </div>
135
- {:else if showInfo && content.info?.side === 'left'}
136
- <div
137
- transition:fly={{ x: 15, duration: 300 }}
138
- class="absolute top-1/2 right-full z-50 mr-2 w-max max-w-xs rounded-md bg-(--container-color) px-3 py-1 text-sm shadow-lg"
139
- style="transform: translateY(-50%);"
140
- >
141
- {content.info?.text}
142
- <div class="absolute top-1/2 -right-2 h-2 w-2 -translate-x-1/2 -translate-y-1/2 rotate-45 transform bg-(--container-color)"></div>
143
- </div>
144
- {:else if showInfo && content.info?.side === 'right'}
145
- <div
146
- transition:fly={{ x: -15, duration: 300 }}
147
- class="absolute top-1/2 left-full z-50 ml-2 w-max max-w-xs rounded-md bg-(--container-color) px-3 py-1 text-sm shadow-lg"
148
- style="transform: translateY(-50%);"
149
- >
150
- {content.info?.text}
151
- <div class="absolute top-1/2 -left-2 h-2 w-2 translate-x-1/2 -translate-y-1/2 -rotate-45 transform bg-(--container-color)"></div>
152
- </div>
153
- {/if}
154
- </div>
116
+ {#if showInfo && content.info?.side === 'top'}
117
+ <div
118
+ transition:fly={{ y: -15, duration: 300 }}
119
+ class="absolute bottom-full left-1/2 z-50 mb-2 w-max max-w-xs rounded-md bg-(--container-color) px-3 py-1 text-sm shadow-lg"
120
+ style="transform: translateX(-50%);"
121
+ >
122
+ {content.info?.text}
123
+ <div class="absolute top-full left-1/2 h-2 w-2 -translate-x-1/2 -translate-y-1/2 rotate-45 transform bg-(--container-color)"></div>
124
+ </div>
125
+ {:else if showInfo && content.info?.side === 'bottom'}
126
+ <div
127
+ transition:fly={{ y: 15, duration: 300 }}
128
+ class="absolute top-full left-1/2 z-50 mt-2 w-max max-w-xs rounded-md bg-(--container-color) px-3 py-1 text-sm shadow-lg"
129
+ style="transform: translateX(-50%);"
130
+ >
131
+ {content.info?.text}
132
+ <div class="absolute bottom-full left-1/2 h-2 w-2 -translate-x-1/2 translate-y-1/2 rotate-45 transform bg-(--container-color)"></div>
133
+ </div>
134
+ {:else if showInfo && content.info?.side === 'left'}
135
+ <div
136
+ transition:fly={{ x: 15, duration: 300 }}
137
+ class="absolute top-1/2 right-full z-50 mr-2 w-max max-w-xs rounded-md bg-(--container-color) px-3 py-1 text-sm shadow-lg"
138
+ style="transform: translateY(-50%);"
139
+ >
140
+ {content.info?.text}
141
+ <div class="absolute top-1/2 -right-2 h-2 w-2 -translate-x-1/2 -translate-y-1/2 rotate-45 transform bg-(--container-color)"></div>
142
+ </div>
143
+ {:else if showInfo && content.info?.side === 'right'}
144
+ <div
145
+ transition:fly={{ x: -15, duration: 300 }}
146
+ class="absolute top-1/2 left-full z-50 ml-2 w-max max-w-xs rounded-md bg-(--container-color) px-3 py-1 text-sm shadow-lg"
147
+ style="transform: translateY(-50%);"
148
+ >
149
+ {content.info?.text}
150
+ <div class="absolute top-1/2 -left-2 h-2 w-2 translate-x-1/2 -translate-y-1/2 -rotate-45 transform bg-(--container-color)"></div>
151
+ </div>
152
+ {/if}
155
153
  </div>
@@ -9,7 +9,7 @@
9
9
  wrapperClass = '',
10
10
  label = { name: '', class: '', captionLeft: '', captionRight: '' },
11
11
  height = '2rem',
12
- type = 'horizontal',
12
+ type = 'vertical',
13
13
  value = $bindable(),
14
14
  onChange = () => {},
15
15
  }: ISwitchProps = $props()
@@ -17,7 +17,11 @@
17
17
  const options = [1, 2]
18
18
  let checked = $derived(value === options[1])
19
19
 
20
- let knobTransform = $derived(checked ? `translateX(calc(${height}))` : 'translateX(0)')
20
+ let knobTransform = $derived(
21
+ checked
22
+ ? `${type === 'horizontal' ? `translateX(calc(${height}))` : `translateY(calc(-${height}/2))`}`
23
+ : `${type === 'horizontal' ? 'translateX(0)' : `translateY(calc(${height}/2))`}`,
24
+ )
21
25
 
22
26
  $effect(() => {
23
27
  if (value === undefined || value === null) value = options[0]
@@ -45,47 +49,79 @@
45
49
  )
46
50
  </script>
47
51
 
48
- <div class={twMerge(`bg-blue relative flex w-full flex-col items-center justify-center`, wrapperClass)}>
49
- {#if label.name}
50
- <h5 class={twMerge(`w-full px-4 text-center`, label.class)}>{label.name}</h5>
51
- {/if}
52
+ {#if type !== 'checkbox'}
53
+ <div class={twMerge(`bg-blue relative flex w-full flex-col items-center justify-center`, wrapperClass)}>
54
+ {#if label.name}
55
+ <h5 class={twMerge(`w-full px-4 text-center`, label.class)}>{label.name}</h5>
56
+ {/if}
57
+
58
+ <div class="relative flex w-full grow items-center justify-center bg-transparent">
59
+ {#if type === 'horizontal'}
60
+ <button
61
+ class="mr-2 {disabled ? 'opacity-60' : 'cursor-pointer'}"
62
+ style="width: {maxCaptionWidth}; text-align: end;"
63
+ onclick={() => handleCaptionClick(1)}>{label.captionLeft}</button
64
+ >
65
+ {/if}
52
66
 
53
- <div class="relative flex w-full grow items-center justify-center bg-transparent">
54
- <button
55
- class="mr-2 {disabled ? 'opacity-60' : 'cursor-pointer'}"
56
- style="width: {maxCaptionWidth}; text-align: end;"
57
- onclick={() => handleCaptionClick(1)}>{label.captionLeft}</button
58
- >
59
- <label
60
- class="relative flex items-center justify-between rounded-full border
67
+ <label
68
+ class="relative flex items-center justify-between rounded-full border
61
69
  {checked ? 'border-(--bg-color)' : 'border-(--gray-color)'}
62
70
  {disabled ? 'opacity-60' : ''}"
63
- >
64
- <input
65
- {id}
66
- type="checkbox"
67
- class="absolute left-1/2 h-full w-full -translate-x-1/2 cursor-pointer appearance-none rounded-md"
68
- bind:checked
69
- {disabled}
70
- onchange={handleToggle}
71
- />
72
- <span
73
- class="relative flex items-center rounded-full transition-all duration-250
74
- {checked ? 'bg-(--bg-color)' : 'bg-(--gray-color)'}
75
- {disabled ? '' : 'cursor-pointer'}"
76
- style="width: {`calc(${height} * 2)`}; height: {height};"
77
71
  >
72
+ <input
73
+ {id}
74
+ type="checkbox"
75
+ class="absolute left-1/2 h-full w-full -translate-x-1/2 cursor-pointer appearance-none rounded-md"
76
+ bind:checked
77
+ {disabled}
78
+ onchange={handleToggle}
79
+ />
78
80
  <span
79
- class="absolute rounded-full bg-(--back-color) transition-all duration-250
81
+ class="relative flex items-center rounded-full transition-all duration-250
82
+ {checked ? 'bg-(--bg-color)' : 'bg-(--gray-color)'}
83
+ {disabled ? '' : 'cursor-pointer'}"
84
+ style="{type === 'horizontal' ? 'width' : 'height'}: {`calc(${height} * 2)`}; {type === 'horizontal' ? 'height' : 'width'}: {height};"
85
+ >
86
+ <span
87
+ class="absolute rounded-full bg-(--back-color) transition-all duration-250
80
88
  {disabled ? 'opacity-60' : 'cursor-pointer'}"
81
- style="width: {`calc(${height} * 0.75)`}; height: {`calc(${height} * 0.75)`}; margin: 0 {`calc(${height} * 0.1)`}; transform: {knobTransform};"
82
- ></span>
83
- </span>
89
+ style="width: {`calc(${height} * 0.8)`}; height: {`calc(${height} * 0.8)`}; margin: 0 {`calc(${height} * 0.1)`}; transform: {knobTransform};"
90
+ ></span>
91
+ </span>
92
+ </label>
93
+ {#if type === 'horizontal'}
94
+ <button
95
+ class="ml-2 {disabled ? 'opacity-60' : 'cursor-pointer'}"
96
+ style="width: {maxCaptionWidth}; text-align: start;"
97
+ onclick={() => handleCaptionClick(2)}>{label.captionRight}</button
98
+ >
99
+ {/if}
100
+ </div>
101
+ </div>
102
+ {:else}
103
+ <div class={twMerge('bg-blue m-1 flex items-center justify-center gap-2', wrapperClass)}>
104
+ <input
105
+ {id}
106
+ type="checkbox"
107
+ bind:checked
108
+ {disabled}
109
+ class="
110
+ relative size-8 cursor-pointer appearance-none rounded-2xl border border-(--bg-color)
111
+ bg-white transition duration-300 after:origin-bottom-left after:opacity-0
112
+ checked:border-(--bg-color)
113
+ checked:bg-(--bg-color) checked:after:absolute checked:after:left-[5.5px]
114
+ checked:after:h-[13.5px] checked:after:w-[7.5px] checked:after:rotate-43
115
+ checked:after:border-2 checked:after:border-t-0
116
+ checked:after:border-l-0 checked:after:border-solid
117
+ checked:after:border-white checked:after:opacity-100
118
+ checked:after:content-[''] hover:shadow-md
119
+ disabled:cursor-not-allowed disabled:opacity-70
120
+ "
121
+ onchange={handleToggle}
122
+ />
123
+ <label for={id} class={twMerge("{disabled ? 'cursor-not-allowed opacity-70' : 'cursor-pointer'} ml-1 select-none", label.class)}>
124
+ {label.name}
84
125
  </label>
85
- <button
86
- class="ml-2 {disabled ? 'opacity-60' : 'cursor-pointer'}"
87
- style="width: {maxCaptionWidth}; text-align: start;"
88
- onclick={() => handleCaptionClick(2)}>{label.captionRight}</button
89
- >
90
126
  </div>
91
- </div>
127
+ {/if}
@@ -56,19 +56,6 @@
56
56
  } else if (width.class.includes('w-auto')) return 1
57
57
  else return 2
58
58
  })
59
-
60
- const handleImageUpload = (event: Event) => {
61
- const input = event.target as HTMLInputElement
62
- if (!input.files || input.files.length === 0) return
63
-
64
- const file = input.files[0]
65
- const reader = new FileReader()
66
- reader.onload = (e) => {
67
- const base64String = e.target?.result as string
68
- updateProperty('image', base64String, component, onPropertyChange)
69
- }
70
- reader.readAsDataURL(file)
71
- }
72
59
  </script>
73
60
 
74
61
  {#if forConstructor}
@@ -121,19 +108,11 @@
121
108
  }}
122
109
  value={initialWidth()}
123
110
  onChange={(value) => {
124
- if (value === 2) {
125
- component.properties.items.forEach((_item: any, index: number) => {
126
- const items = [...(component.properties?.items || [])]
127
- items[index]['class'] = twMerge(items[index].class, `w-[${(1 / items.length) * 100}%]`)
128
- updateProperty('items', items, component, onPropertyChange)
129
- })
130
- } else {
131
- component.properties.items.forEach((_item: any, index: number) => {
132
- const items = [...(component.properties?.items || [])]
133
- items[index]['class'] = twMerge(items[index].class, 'w-auto')
134
- updateProperty('items', items, component, onPropertyChange)
135
- })
136
- }
111
+ component.properties.items.forEach((_item: any, index: number) => {
112
+ const items = [...(component.properties?.items || [])]
113
+ items[index]['class'] = twMerge(items[index].class, value === 2 ? `w-[${(1 / items.length) * 100}%]` : 'w-auto')
114
+ updateProperty('items', items, component, onPropertyChange)
115
+ })
137
116
  }}
138
117
  />
139
118
  </div>
@@ -146,14 +125,16 @@
146
125
  wrapperClass="w-8"
147
126
  content={{ icon: ButtonAdd }}
148
127
  onClick={() => {
149
- let tabWidth = Math.max(...Array.from(document.body.querySelectorAll('.tab')).map((item) => (item as HTMLElement).offsetWidth))
150
128
  const newItem: { name: string; icon: string; class: string } = {
151
129
  name: `Tab ${component.properties?.items.length + 1}`,
152
- class: `w-${initialWidth() === 2 ? `[${tabWidth}px]` : 'auto'} text-${initialColor?.value.slice(3)}-500 ${initialPosition?.value}`,
130
+ class: `text-${initialColor?.value.slice(3)}-500 ${initialPosition?.value}`,
153
131
  icon: '',
154
132
  }
155
133
  const items = [...(component.properties?.items || []), newItem]
156
- updateProperty('items', items, component, onPropertyChange)
134
+ items.forEach((_item: any, index: number) => {
135
+ items[index]['class'] = twMerge(items[index].class, initialWidth() === 2 ? `w-[${(1 / items.length) * 100}%]` : 'w-auto')
136
+ updateProperty('items', items, component, onPropertyChange)
137
+ })
157
138
  }}
158
139
  />
159
140
  </div>
@@ -194,6 +175,10 @@
194
175
  onClick={() => {
195
176
  const items = [...(component.properties?.items || [])]
196
177
  items.splice(index, 1)
178
+ items.forEach((_item: any, index: number) => {
179
+ items[index]['class'] = twMerge(items[index].class, initialWidth() === 2 ? `w-[${(1 / items.length) * 100}%]` : 'w-auto')
180
+ updateProperty('items', items, component, onPropertyChange)
181
+ })
197
182
  updateProperty('items', items, component, onPropertyChange)
198
183
  }}
199
184
  />
package/dist/types.d.ts CHANGED
@@ -269,7 +269,6 @@ export interface ITabsProps {
269
269
  icon?: string;
270
270
  class?: string;
271
271
  children?: Snippet;
272
- width?: string;
273
272
  }[];
274
273
  apiArray?: UIComponent[];
275
274
  Components?: Snippet<[component: UIComponent, fixedHeight: boolean]>;
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "poe-svelte-ui-lib",
3
- "version": "1.2.8",
3
+ "version": "1.2.10",
4
4
  "license": "MIT",
5
5
  "type": "module",
6
6
  "scripts": {