@hashrytech/quick-components-kit 0.19.16 → 0.20.0
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/CHANGELOG.md +12 -0
- package/dist/components/text-input/TextInput.svelte +14 -1
- package/dist/components/toast/Toast.svelte +68 -0
- package/dist/components/toast/Toast.svelte.d.ts +11 -0
- package/dist/components/toast/ToastContainer.svelte +37 -0
- package/dist/components/toast/ToastContainer.svelte.d.ts +9 -0
- package/dist/components/toast/index.d.ts +3 -0
- package/dist/components/toast/index.js +4 -0
- package/dist/components/toast/toastFunctions.d.ts +24 -0
- package/dist/components/toast/toastFunctions.js +68 -0
- package/dist/index.d.ts +1 -0
- package/dist/index.js +1 -0
- package/package.json +1 -1
package/CHANGELOG.md
CHANGED
|
@@ -137,6 +137,20 @@
|
|
|
137
137
|
(e.target as HTMLInputElement).value = localValue; // reflect sanitized value in the UI
|
|
138
138
|
}
|
|
139
139
|
|
|
140
|
+
if(max && max > 0){
|
|
141
|
+
if(Number(value) > max){
|
|
142
|
+
localValue = String(max);
|
|
143
|
+
(e.target as HTMLInputElement).value = localValue; // reflect max value in the UI
|
|
144
|
+
}
|
|
145
|
+
}
|
|
146
|
+
|
|
147
|
+
if(min && min > 0){
|
|
148
|
+
if(Number(value) < min){
|
|
149
|
+
localValue = String(min);
|
|
150
|
+
(e.target as HTMLInputElement).value = localValue; // reflect min value in the UI
|
|
151
|
+
}
|
|
152
|
+
}
|
|
153
|
+
|
|
140
154
|
clearTimeout(debounceTimer);
|
|
141
155
|
debounceTimer = setTimeout(() => {
|
|
142
156
|
value = localValue; // sync to bound value after delay
|
|
@@ -165,7 +179,6 @@
|
|
|
165
179
|
return String(num);
|
|
166
180
|
}
|
|
167
181
|
|
|
168
|
-
|
|
169
182
|
</script>
|
|
170
183
|
|
|
171
184
|
<div class={twMerge("", firstDivClass)}>
|
|
@@ -0,0 +1,68 @@
|
|
|
1
|
+
<script lang="ts" module>
|
|
2
|
+
import type { Snippet } from 'svelte';
|
|
3
|
+
import type { ClassNameValue } from 'tailwind-merge';
|
|
4
|
+
|
|
5
|
+
export type ToastType = 'success' | 'info' | 'debug' | 'warning' | 'error';
|
|
6
|
+
export type ToastPosition = 'top-left' | 'top-center' | 'top-right' | 'bottom-left' | 'bottom-center' | 'bottom-right';
|
|
7
|
+
|
|
8
|
+
</script>
|
|
9
|
+
|
|
10
|
+
<script lang="ts">
|
|
11
|
+
import { fly } from 'svelte/transition';
|
|
12
|
+
import { onMount, onDestroy } from 'svelte';
|
|
13
|
+
import { toastIcons, toastTypeClasses, toastTypeIconColours, toastOptions } from './index.js';
|
|
14
|
+
|
|
15
|
+
let { toastType="info", message = "This is a generic toast message", subMessage="", delToast} :
|
|
16
|
+
{ toastType:ToastType, message:string, subMessage:string, delToast?: ()=> void} = $props();
|
|
17
|
+
|
|
18
|
+
let open: boolean = $state(false);
|
|
19
|
+
|
|
20
|
+
let autoTimer: ReturnType<typeof setTimeout>;
|
|
21
|
+
|
|
22
|
+
onMount(async () => {
|
|
23
|
+
open = true;
|
|
24
|
+
if(toastOptions.autoRemove){
|
|
25
|
+
autoTimer = setTimeout(async () => {await handle_close();}, toastOptions.removalTimeout);
|
|
26
|
+
}
|
|
27
|
+
});
|
|
28
|
+
|
|
29
|
+
onDestroy(() => {
|
|
30
|
+
clearTimeout(autoTimer);
|
|
31
|
+
});
|
|
32
|
+
|
|
33
|
+
async function handle_close(){
|
|
34
|
+
open = false;
|
|
35
|
+
await new Promise(r => setTimeout(r, 200));
|
|
36
|
+
delToast?.();
|
|
37
|
+
}
|
|
38
|
+
|
|
39
|
+
</script>
|
|
40
|
+
|
|
41
|
+
|
|
42
|
+
{#if open}
|
|
43
|
+
<div transition:fly={{ delay: toastOptions.transitionDelay, duration: toastOptions.transitionDuration, y: toastOptions.transitionY, easing: toastOptions.transitionEasing }} class="flex flex-row rounded-lg mt-2 py-0.5 h-full min-h-[4rem] shadow-lg w-full max-w-md ring-1
|
|
44
|
+
border-none pointer-events-auto text-neutral-700 {toastTypeClasses[toastType]}">
|
|
45
|
+
<div class="flex flex-row gap-4 items-center w-full justify-center rounded-sm mx-4">
|
|
46
|
+
|
|
47
|
+
<div class="flex flex-row items-center justify-center">
|
|
48
|
+
<span class="{toastIcons[toastType]} {toastTypeIconColours[toastType]} size-8 outline-hidden"></span>
|
|
49
|
+
</div>
|
|
50
|
+
|
|
51
|
+
<div class="flex flex-col gap-1 px-2 w-full rounded-sm p-2">
|
|
52
|
+
<p class="text-sm font-medium break-all xs:break-word">{@html message}</p>
|
|
53
|
+
{#if subMessage}
|
|
54
|
+
<p class="text-xs font-light break-all xs:break-word">{@html subMessage}</p>
|
|
55
|
+
{/if}
|
|
56
|
+
</div>
|
|
57
|
+
|
|
58
|
+
{#if toastOptions.closeButtonIcon}
|
|
59
|
+
<button aria-label="close" class="cursor-pointer rounded-full size-6 hover:scale-105" onclick={handle_close}>
|
|
60
|
+
<span class="{toastOptions.closeButtonIcon} size-6 outline-hidden text-neutral-700"></span>
|
|
61
|
+
</button>
|
|
62
|
+
{/if}
|
|
63
|
+
|
|
64
|
+
</div>
|
|
65
|
+
</div>
|
|
66
|
+
{/if}
|
|
67
|
+
|
|
68
|
+
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
export type ToastType = 'success' | 'info' | 'debug' | 'warning' | 'error';
|
|
2
|
+
export type ToastPosition = 'top-left' | 'top-center' | 'top-right' | 'bottom-left' | 'bottom-center' | 'bottom-right';
|
|
3
|
+
type $$ComponentProps = {
|
|
4
|
+
toastType: ToastType;
|
|
5
|
+
message: string;
|
|
6
|
+
subMessage: string;
|
|
7
|
+
delToast?: () => void;
|
|
8
|
+
};
|
|
9
|
+
declare const Toast: import("svelte").Component<$$ComponentProps, {}, "">;
|
|
10
|
+
type Toast = ReturnType<typeof Toast>;
|
|
11
|
+
export default Toast;
|
|
@@ -0,0 +1,37 @@
|
|
|
1
|
+
<script lang="ts">
|
|
2
|
+
import Toast, { type ToastPosition } from './Toast.svelte';
|
|
3
|
+
|
|
4
|
+
let { position = 'top-right', id = "toast_area", reverseFlex = false }: { position?: ToastPosition, id?: string, reverseFlex?: boolean } = $props();
|
|
5
|
+
|
|
6
|
+
// Position classes using Tailwind
|
|
7
|
+
const positionClasses: Record<ToastPosition, string> = {
|
|
8
|
+
'top-left': 'top-0 left-0',
|
|
9
|
+
'top-center': 'top-0 left-1/2 -translate-x-1/2',
|
|
10
|
+
'top-right': 'top-0 right-0',
|
|
11
|
+
'bottom-left': 'bottom-0 left-0 flex-col-reverse',
|
|
12
|
+
'bottom-center': 'bottom-0 left-1/2 -translate-x-1/2 flex-col-reverse',
|
|
13
|
+
'bottom-right': 'bottom-0 right-0 flex-col-reverse'
|
|
14
|
+
};
|
|
15
|
+
|
|
16
|
+
</script>
|
|
17
|
+
|
|
18
|
+
<div {id} class="fixed z-[9999] flex {reverseFlex ? 'flex-col-reverse' : 'flex-col'} gap-3 p-4 pointer-events-none {positionClasses[position]}">
|
|
19
|
+
|
|
20
|
+
</div>
|
|
21
|
+
|
|
22
|
+
<style>
|
|
23
|
+
/* Responsive adjustments */
|
|
24
|
+
@media (max-width: 640px) {
|
|
25
|
+
div {
|
|
26
|
+
left: 0 !important;
|
|
27
|
+
right: 0 !important;
|
|
28
|
+
transform: none !important;
|
|
29
|
+
align-items: center;
|
|
30
|
+
}
|
|
31
|
+
|
|
32
|
+
div :global(> *) {
|
|
33
|
+
width: calc(100% - 2rem);
|
|
34
|
+
max-width: 400px;
|
|
35
|
+
}
|
|
36
|
+
}
|
|
37
|
+
</style>
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
import { type ToastPosition } from './Toast.svelte';
|
|
2
|
+
type $$ComponentProps = {
|
|
3
|
+
position?: ToastPosition;
|
|
4
|
+
id?: string;
|
|
5
|
+
reverseFlex?: boolean;
|
|
6
|
+
};
|
|
7
|
+
declare const ToastContainer: import("svelte").Component<$$ComponentProps, {}, "">;
|
|
8
|
+
type ToastContainer = ReturnType<typeof ToastContainer>;
|
|
9
|
+
export default ToastContainer;
|
|
@@ -0,0 +1,3 @@
|
|
|
1
|
+
export { default as ToastContainer } from './ToastContainer.svelte';
|
|
2
|
+
export { default as Toast } from './Toast.svelte';
|
|
3
|
+
export { showToast, successToast, failToast, infoToast, warningToast, debugToast, toastIcons, toastTypeClasses, toastTypeIconColours, closeButtonIcon, toastOptions } from './toastFunctions.js';
|
|
@@ -0,0 +1,4 @@
|
|
|
1
|
+
// src/lib/index.ts
|
|
2
|
+
export { default as ToastContainer } from './ToastContainer.svelte';
|
|
3
|
+
export { default as Toast } from './Toast.svelte';
|
|
4
|
+
export { showToast, successToast, failToast, infoToast, warningToast, debugToast, toastIcons, toastTypeClasses, toastTypeIconColours, closeButtonIcon, toastOptions } from './toastFunctions.js';
|
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
import type { ToastType } from "./Toast.svelte";
|
|
2
|
+
export type ToastOptions = {
|
|
3
|
+
icons: Record<ToastType, string>;
|
|
4
|
+
classes: Record<string, string>;
|
|
5
|
+
colours: Record<ToastType, string>;
|
|
6
|
+
closeButtonIcon: string;
|
|
7
|
+
transitionDelay: number;
|
|
8
|
+
transitionDuration: number;
|
|
9
|
+
transitionY: number;
|
|
10
|
+
transitionEasing: (t: number) => number;
|
|
11
|
+
removalTimeout: number;
|
|
12
|
+
autoRemove: boolean;
|
|
13
|
+
};
|
|
14
|
+
export declare const closeButtonIcon: string[];
|
|
15
|
+
export declare const toastTypeClasses: Record<ToastType, string>;
|
|
16
|
+
export declare const toastTypeIconColours: Record<ToastType, string>;
|
|
17
|
+
export declare const toastIcons: Record<ToastType, string>;
|
|
18
|
+
export declare const toastOptions: ToastOptions;
|
|
19
|
+
export declare function showToast(type: ToastType, message: string, subMessage?: string, target?: Element | null): void;
|
|
20
|
+
export declare function successToast(message: string, subMessage?: string, target?: Element | null): void;
|
|
21
|
+
export declare function failToast(message: string, subMessage?: string, target?: Element | null): void;
|
|
22
|
+
export declare function infoToast(message: string, subMessage?: string, target?: Element | null): void;
|
|
23
|
+
export declare function warningToast(message: string, subMessage?: string, target?: Element | null): void;
|
|
24
|
+
export declare function debugToast(message: string, subMessage?: string, target?: Element | null): void;
|
|
@@ -0,0 +1,68 @@
|
|
|
1
|
+
import { mount, unmount } from 'svelte';
|
|
2
|
+
import Toast from "./Toast.svelte";
|
|
3
|
+
import { elasticInOut } from 'svelte/easing';
|
|
4
|
+
export const closeButtonIcon = [];
|
|
5
|
+
/* Tailwind classes for different toast types */
|
|
6
|
+
export const toastTypeClasses = {
|
|
7
|
+
info: "ring-sky-500 border-sky-500 bg-sky-50",
|
|
8
|
+
success: "ring-green-500 border-green-500 bg-green-50",
|
|
9
|
+
warning: "ring-yellow-500 border-yellow-500 bg-yellow-50",
|
|
10
|
+
error: "ring-red-500 border-red-500 bg-red-50",
|
|
11
|
+
debug: "ring-neutral-500 border-neutral-500 bg-neutral-50",
|
|
12
|
+
};
|
|
13
|
+
/* Tailwind icon colour classes for different toast types */
|
|
14
|
+
export const toastTypeIconColours = {
|
|
15
|
+
info: "text-blue-500",
|
|
16
|
+
success: "text-green-500",
|
|
17
|
+
warning: "text-yellow-500",
|
|
18
|
+
error: "text-red-500",
|
|
19
|
+
debug: "text-neutral-500",
|
|
20
|
+
};
|
|
21
|
+
/* Icons for different toast types
|
|
22
|
+
Globally available state variables for toast:
|
|
23
|
+
toastIcons['info'] = "icon-[ion--information-circle]";
|
|
24
|
+
toastIcons['success'] = "icon-[ion--checkmark-circle]";
|
|
25
|
+
toastIcons['warning'] = "icon-[ion--warning]";
|
|
26
|
+
toastIcons['error'] = "icon-[ion--close-circle]";
|
|
27
|
+
toastIcons['debug'] = "icon-[ion--bug]";
|
|
28
|
+
*/
|
|
29
|
+
export const toastIcons = {
|
|
30
|
+
info: "",
|
|
31
|
+
success: "",
|
|
32
|
+
warning: "",
|
|
33
|
+
error: "",
|
|
34
|
+
debug: "",
|
|
35
|
+
};
|
|
36
|
+
export const toastOptions = {
|
|
37
|
+
icons: toastIcons,
|
|
38
|
+
classes: toastTypeClasses,
|
|
39
|
+
colours: toastTypeIconColours,
|
|
40
|
+
closeButtonIcon: "",
|
|
41
|
+
transitionDelay: 0,
|
|
42
|
+
transitionDuration: 200,
|
|
43
|
+
transitionY: -100,
|
|
44
|
+
transitionEasing: elasticInOut,
|
|
45
|
+
removalTimeout: 8000,
|
|
46
|
+
autoRemove: true
|
|
47
|
+
};
|
|
48
|
+
export function showToast(type, message, subMessage = "", target = document.querySelector("#toast_area")) {
|
|
49
|
+
if (target !== null) {
|
|
50
|
+
const delToast = () => { unmount(toast, { outro: true }); };
|
|
51
|
+
const toast = mount(Toast, { target: target, props: { toastType: type, message: message, subMessage: subMessage, delToast: delToast } });
|
|
52
|
+
}
|
|
53
|
+
}
|
|
54
|
+
export function successToast(message, subMessage = "", target = document.querySelector("#toast_area")) {
|
|
55
|
+
showToast('success', message, subMessage, target);
|
|
56
|
+
}
|
|
57
|
+
export function failToast(message, subMessage = "", target = document.querySelector("#toast_area")) {
|
|
58
|
+
showToast('error', message, subMessage, target);
|
|
59
|
+
}
|
|
60
|
+
export function infoToast(message, subMessage = "", target = document.querySelector("#toast_area")) {
|
|
61
|
+
showToast('info', message, subMessage, target);
|
|
62
|
+
}
|
|
63
|
+
export function warningToast(message, subMessage = "", target = document.querySelector("#toast_area")) {
|
|
64
|
+
showToast('warning', message, subMessage, target);
|
|
65
|
+
}
|
|
66
|
+
export function debugToast(message, subMessage = "", target = document.querySelector("#toast_area")) {
|
|
67
|
+
showToast('debug', message, subMessage, target);
|
|
68
|
+
}
|
package/dist/index.d.ts
CHANGED
|
@@ -13,6 +13,7 @@ export * from './components/checkbox/index.js';
|
|
|
13
13
|
export * from './components/tab-navigation/index.js';
|
|
14
14
|
export * from './components/portal/index.js';
|
|
15
15
|
export * from './components/table/index.js';
|
|
16
|
+
export * from './components/toast/index.js';
|
|
16
17
|
export * from './actions/disable-scroll.js';
|
|
17
18
|
export * from './actions/on-keydown.js';
|
|
18
19
|
export * from './actions/lock-scroll.js';
|
package/dist/index.js
CHANGED
|
@@ -14,6 +14,7 @@ export * from './components/checkbox/index.js';
|
|
|
14
14
|
export * from './components/tab-navigation/index.js';
|
|
15
15
|
export * from './components/portal/index.js';
|
|
16
16
|
export * from './components/table/index.js';
|
|
17
|
+
export * from './components/toast/index.js';
|
|
17
18
|
// Actions
|
|
18
19
|
export * from './actions/disable-scroll.js';
|
|
19
20
|
export * from './actions/on-keydown.js';
|