@coyalabs/bts-style 1.3.21 → 1.3.23
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.
|
@@ -10,8 +10,8 @@
|
|
|
10
10
|
import { VARIANT_FILLED } from '../../Base/variantTypes.js';
|
|
11
11
|
|
|
12
12
|
// Subscribe to the actual stack
|
|
13
|
-
/** @type {Array<{id: string, title: string, subtitle?: string, component: any, props: any, widthRatio: number}>} */
|
|
14
|
-
let popupStack = [];
|
|
13
|
+
/** @type {Array<{id: string, title: string, subtitle?: string, component: any, props: any, widthRatio: number, disableClose?: boolean}>} */
|
|
14
|
+
let popupStack = [];
|
|
15
15
|
popupStore.stack.subscribe((s) => {
|
|
16
16
|
popupStack = s;
|
|
17
17
|
});
|
|
@@ -19,8 +19,16 @@
|
|
|
19
19
|
/** @type {{submit?: () => void, confirm?: () => void, cancel?: () => void, focusInput?: () => void} | null} */
|
|
20
20
|
let activePopupInstance = null;
|
|
21
21
|
|
|
22
|
-
/** @type {HTMLDivElement | null} */
|
|
23
|
-
let activeDialogRef = null;
|
|
22
|
+
/** @type {HTMLDivElement | null} */
|
|
23
|
+
let activeDialogRef = null;
|
|
24
|
+
let pointerStartedOnOverlay = false;
|
|
25
|
+
|
|
26
|
+
$: activePopup = popupStack[popupStack.length - 1] || null;
|
|
27
|
+
|
|
28
|
+
function closeTopPopup() {
|
|
29
|
+
if (activePopup?.disableClose) return;
|
|
30
|
+
popupStore.close();
|
|
31
|
+
}
|
|
24
32
|
|
|
25
33
|
function focusActivePopup() {
|
|
26
34
|
void tick().then(() => {
|
|
@@ -50,11 +58,12 @@
|
|
|
50
58
|
}
|
|
51
59
|
}
|
|
52
60
|
|
|
53
|
-
if (event.key === 'Escape') {
|
|
54
|
-
event.preventDefault();
|
|
55
|
-
if (
|
|
56
|
-
|
|
57
|
-
|
|
61
|
+
if (event.key === 'Escape') {
|
|
62
|
+
event.preventDefault();
|
|
63
|
+
if (activePopup?.disableClose) return;
|
|
64
|
+
if (activePopupInstance?.cancel) {
|
|
65
|
+
activePopupInstance.cancel();
|
|
66
|
+
} else {
|
|
58
67
|
popupStore.close();
|
|
59
68
|
}
|
|
60
69
|
return;
|
|
@@ -82,17 +91,31 @@
|
|
|
82
91
|
activePopupInstance.submit();
|
|
83
92
|
return;
|
|
84
93
|
}
|
|
85
|
-
|
|
86
|
-
activePopupInstance?.confirm?.();
|
|
87
|
-
}
|
|
94
|
+
|
|
95
|
+
activePopupInstance?.confirm?.();
|
|
96
|
+
}
|
|
97
|
+
|
|
98
|
+
function handleOverlayPointerdown(event) {
|
|
99
|
+
pointerStartedOnOverlay = event.target === event.currentTarget;
|
|
100
|
+
}
|
|
101
|
+
|
|
102
|
+
function handleOverlayClick(event) {
|
|
103
|
+
if (!pointerStartedOnOverlay || event.target !== event.currentTarget) {
|
|
104
|
+
pointerStartedOnOverlay = false;
|
|
105
|
+
return;
|
|
106
|
+
}
|
|
107
|
+
|
|
108
|
+
pointerStartedOnOverlay = false;
|
|
109
|
+
closeTopPopup();
|
|
110
|
+
}
|
|
88
111
|
|
|
89
112
|
$: if (popupStack.length > 0) {
|
|
90
113
|
focusActivePopup();
|
|
91
114
|
}
|
|
92
115
|
</script>
|
|
93
116
|
|
|
94
|
-
{#if popupStack.length > 0}
|
|
95
|
-
<div class="overlay" transition:fade={{ duration: 200 }} on:click={
|
|
117
|
+
{#if popupStack.length > 0}
|
|
118
|
+
<div class="overlay" transition:fade={{ duration: 200 }} on:pointerdown={handleOverlayPointerdown} on:click={handleOverlayClick} role="presentation">
|
|
96
119
|
{#each popupStack as popup, index (popup.id)}
|
|
97
120
|
{@const isTop = index === popupStack.length - 1}
|
|
98
121
|
{@const depth = popupStack.length - 1 - index}
|
|
@@ -116,12 +139,14 @@
|
|
|
116
139
|
tabindex="-1"
|
|
117
140
|
>
|
|
118
141
|
<BaseContainer padding="1.5rem" borderRadiusTopLeft="35px" borderRadiusTopRight="35px" borderRadiusBottomLeft="35px" borderRadiusBottomRight="35px" theme={VARIANT_FILLED}>
|
|
119
|
-
<header>
|
|
120
|
-
<TextHeader title={popup.title} subtitle={popup.subtitle || ''} />
|
|
121
|
-
|
|
122
|
-
<
|
|
123
|
-
|
|
124
|
-
|
|
142
|
+
<header>
|
|
143
|
+
<TextHeader title={popup.title} subtitle={popup.subtitle || ''} />
|
|
144
|
+
{#if !popup.disableClose}
|
|
145
|
+
<div class="close-btn">
|
|
146
|
+
<IconButton svg={icons.cross} size="20px" variant="toned" on:click={popupStore.close} />
|
|
147
|
+
</div>
|
|
148
|
+
{/if}
|
|
149
|
+
</header>
|
|
125
150
|
<main>
|
|
126
151
|
<svelte:component bind:this={activePopupInstance} this={popup.component} {...popup.props} />
|
|
127
152
|
</main>
|
|
@@ -6,6 +6,7 @@ export namespace popupStore {
|
|
|
6
6
|
component: any;
|
|
7
7
|
props: {};
|
|
8
8
|
widthRatio?: undefined;
|
|
9
|
+
disableClose?: undefined;
|
|
9
10
|
} | {
|
|
10
11
|
isOpen: boolean;
|
|
11
12
|
title: string;
|
|
@@ -13,6 +14,7 @@ export namespace popupStore {
|
|
|
13
14
|
component: any;
|
|
14
15
|
props: any;
|
|
15
16
|
widthRatio: number;
|
|
17
|
+
disableClose: boolean;
|
|
16
18
|
}>, invalidate?: () => void) => import("svelte/store").Unsubscriber;
|
|
17
19
|
namespace stack {
|
|
18
20
|
let subscribe_1: (this: void, run: import("svelte/store").Subscriber<PopupState[]>, invalidate?: () => void) => import("svelte/store").Unsubscriber;
|
|
@@ -21,17 +23,20 @@ export namespace popupStore {
|
|
|
21
23
|
function open(title: string, component: any, props?: {}, subtitle?: string): void;
|
|
22
24
|
function close(): void;
|
|
23
25
|
function closeAll(): void;
|
|
26
|
+
function setCloseDisabled(disabled: boolean): void;
|
|
24
27
|
function confirm(title: string, message: string, options?: {
|
|
25
28
|
onConfirm?: (() => void) | undefined;
|
|
26
29
|
onCancel?: (() => void) | undefined;
|
|
27
30
|
confirmText?: string | undefined;
|
|
28
31
|
cancelText?: string | undefined;
|
|
29
32
|
popupWidthRatio?: number | undefined;
|
|
33
|
+
disableClose?: boolean | undefined;
|
|
30
34
|
}): void;
|
|
31
35
|
function alert(title: string, message: string, options?: {
|
|
32
36
|
onOk?: (() => void) | undefined;
|
|
33
37
|
okText?: string | undefined;
|
|
34
38
|
popupWidthRatio?: number | undefined;
|
|
39
|
+
disableClose?: boolean | undefined;
|
|
35
40
|
}): void;
|
|
36
41
|
function prompt(title: string, message: string, options?: {
|
|
37
42
|
onSubmit?: ((value: string) => void) | undefined;
|
|
@@ -41,6 +46,7 @@ export namespace popupStore {
|
|
|
41
46
|
cancelText?: string | undefined;
|
|
42
47
|
label?: string | undefined;
|
|
43
48
|
popupWidthRatio?: number | undefined;
|
|
49
|
+
disableClose?: boolean | undefined;
|
|
44
50
|
}): void;
|
|
45
51
|
}
|
|
46
52
|
export type PopupState = {
|
|
@@ -50,4 +56,5 @@ export type PopupState = {
|
|
|
50
56
|
props: any;
|
|
51
57
|
id: string;
|
|
52
58
|
widthRatio: number;
|
|
59
|
+
disableClose: boolean;
|
|
53
60
|
};
|
|
@@ -8,9 +8,10 @@ import PromptPopup from './PromptPopup.svelte';
|
|
|
8
8
|
* @property {string} title
|
|
9
9
|
* @property {string} [subtitle]
|
|
10
10
|
* @property {any} component
|
|
11
|
-
* @property {any} props
|
|
12
|
-
* @property {string} id
|
|
13
|
-
* @property {number} widthRatio
|
|
11
|
+
* @property {any} props
|
|
12
|
+
* @property {string} id
|
|
13
|
+
* @property {number} widthRatio
|
|
14
|
+
* @property {boolean} disableClose
|
|
14
15
|
*/
|
|
15
16
|
|
|
16
17
|
/**
|
|
@@ -32,13 +33,14 @@ function splitPopupProps(rawProps = {}) {
|
|
|
32
33
|
};
|
|
33
34
|
}
|
|
34
35
|
|
|
35
|
-
const { popupWidthRatio, ...props } = rawProps;
|
|
36
|
-
|
|
37
|
-
return {
|
|
38
|
-
props,
|
|
39
|
-
widthRatio: normalizePopupWidthRatio(popupWidthRatio)
|
|
40
|
-
|
|
41
|
-
}
|
|
36
|
+
const { popupWidthRatio, disableClose = false, ...props } = rawProps;
|
|
37
|
+
|
|
38
|
+
return {
|
|
39
|
+
props,
|
|
40
|
+
widthRatio: normalizePopupWidthRatio(popupWidthRatio),
|
|
41
|
+
disableClose: disableClose === true
|
|
42
|
+
};
|
|
43
|
+
}
|
|
42
44
|
|
|
43
45
|
/**
|
|
44
46
|
* @param {string} title
|
|
@@ -48,17 +50,18 @@ function splitPopupProps(rawProps = {}) {
|
|
|
48
50
|
* @returns {PopupState}
|
|
49
51
|
*/
|
|
50
52
|
function createPopupEntry(title, subtitle, component, rawProps = {}) {
|
|
51
|
-
const { props, widthRatio } = splitPopupProps(rawProps);
|
|
53
|
+
const { props, widthRatio, disableClose } = splitPopupProps(rawProps);
|
|
52
54
|
|
|
53
55
|
return {
|
|
54
56
|
id: crypto.randomUUID(),
|
|
55
57
|
title,
|
|
56
|
-
subtitle,
|
|
57
|
-
component,
|
|
58
|
-
props,
|
|
59
|
-
widthRatio
|
|
60
|
-
|
|
61
|
-
}
|
|
58
|
+
subtitle,
|
|
59
|
+
component,
|
|
60
|
+
props,
|
|
61
|
+
widthRatio,
|
|
62
|
+
disableClose
|
|
63
|
+
};
|
|
64
|
+
}
|
|
62
65
|
|
|
63
66
|
function createPopupStore() {
|
|
64
67
|
/** @type {import('svelte/store').Writable<PopupState[]>} */
|
|
@@ -79,12 +82,13 @@ function createPopupStore() {
|
|
|
79
82
|
return {
|
|
80
83
|
isOpen: true,
|
|
81
84
|
title: top.title,
|
|
82
|
-
subtitle: top.subtitle || '',
|
|
83
|
-
component: top.component,
|
|
84
|
-
props: top.props,
|
|
85
|
-
widthRatio: top.widthRatio
|
|
86
|
-
|
|
87
|
-
|
|
85
|
+
subtitle: top.subtitle || '',
|
|
86
|
+
component: top.component,
|
|
87
|
+
props: top.props,
|
|
88
|
+
widthRatio: top.widthRatio,
|
|
89
|
+
disableClose: top.disableClose
|
|
90
|
+
};
|
|
91
|
+
});
|
|
88
92
|
|
|
89
93
|
return {
|
|
90
94
|
subscribe: currentPopup.subscribe,
|
|
@@ -100,9 +104,19 @@ function createPopupStore() {
|
|
|
100
104
|
stack.update(s => s.slice(0, -1));
|
|
101
105
|
},
|
|
102
106
|
|
|
103
|
-
closeAll: () => {
|
|
104
|
-
stack.set([]);
|
|
105
|
-
},
|
|
107
|
+
closeAll: () => {
|
|
108
|
+
stack.set([]);
|
|
109
|
+
},
|
|
110
|
+
|
|
111
|
+
setCloseDisabled: (/** @type {boolean} */ disabled) => {
|
|
112
|
+
stack.update(s => {
|
|
113
|
+
if (s.length === 0) return s;
|
|
114
|
+
const next = [...s];
|
|
115
|
+
const top = next[next.length - 1];
|
|
116
|
+
next[next.length - 1] = { ...top, disableClose: disabled === true };
|
|
117
|
+
return next;
|
|
118
|
+
});
|
|
119
|
+
},
|
|
106
120
|
|
|
107
121
|
/**
|
|
108
122
|
* Show a confirmation popup with two buttons
|
|
@@ -112,8 +126,9 @@ function createPopupStore() {
|
|
|
112
126
|
* @param {() => void} [options.onConfirm]
|
|
113
127
|
* @param {() => void} [options.onCancel]
|
|
114
128
|
* @param {string} [options.confirmText]
|
|
115
|
-
* @param {string} [options.cancelText]
|
|
116
|
-
* @param {number} [options.popupWidthRatio]
|
|
129
|
+
* @param {string} [options.cancelText]
|
|
130
|
+
* @param {number} [options.popupWidthRatio]
|
|
131
|
+
* @param {boolean} [options.disableClose]
|
|
117
132
|
*/
|
|
118
133
|
confirm: (title, message, options = {}) => {
|
|
119
134
|
stack.update(s => [...s, createPopupEntry(title, message, ConfirmPopup, options)]);
|
|
@@ -125,8 +140,9 @@ function createPopupStore() {
|
|
|
125
140
|
* @param {string} message
|
|
126
141
|
* @param {Object} options
|
|
127
142
|
* @param {() => void} [options.onOk]
|
|
128
|
-
* @param {string} [options.okText]
|
|
129
|
-
* @param {number} [options.popupWidthRatio]
|
|
143
|
+
* @param {string} [options.okText]
|
|
144
|
+
* @param {number} [options.popupWidthRatio]
|
|
145
|
+
* @param {boolean} [options.disableClose]
|
|
130
146
|
*/
|
|
131
147
|
alert: (title, message, options = {}) => {
|
|
132
148
|
stack.update(s => [...s, createPopupEntry(title, message, AlertPopup, options)]);
|
|
@@ -141,9 +157,10 @@ function createPopupStore() {
|
|
|
141
157
|
* @param {() => void} [options.onCancel]
|
|
142
158
|
* @param {string} [options.placeholder]
|
|
143
159
|
* @param {string} [options.submitText]
|
|
144
|
-
* @param {string} [options.cancelText]
|
|
145
|
-
* @param {string} [options.label]
|
|
146
|
-
* @param {number} [options.popupWidthRatio]
|
|
160
|
+
* @param {string} [options.cancelText]
|
|
161
|
+
* @param {string} [options.label]
|
|
162
|
+
* @param {number} [options.popupWidthRatio]
|
|
163
|
+
* @param {boolean} [options.disableClose]
|
|
147
164
|
*/
|
|
148
165
|
prompt: (title, message, options = {}) => {
|
|
149
166
|
stack.update(s => [...s, createPopupEntry(title, message, PromptPopup, options)]);
|
|
@@ -10,7 +10,7 @@
|
|
|
10
10
|
|
|
11
11
|
/** @typedef {import('../Base/variantTypes.js').BaseContainerVariant} BaseContainerVariant */
|
|
12
12
|
|
|
13
|
-
/** @type {{ name: string, type: 'file' | 'folder' | 'custom', children?: any[], data?: any, variant?: BaseContainerVariant, suffixIcon?: string, isPending?: boolean }[]} */
|
|
13
|
+
/** @type {{ name: string, type: 'file' | 'folder' | 'custom', children?: any[], data?: any, variant?: BaseContainerVariant, icon?: string, suffixIcon?: string, isPending?: boolean }[]} */
|
|
14
14
|
export let items = [];
|
|
15
15
|
|
|
16
16
|
/** @type {boolean} */
|
|
@@ -331,7 +331,7 @@
|
|
|
331
331
|
>
|
|
332
332
|
<Button
|
|
333
333
|
theme={item.variant || VARIANT_SECONDARY}
|
|
334
|
-
icon={itemIcon}
|
|
334
|
+
icon={item.icon || itemIcon}
|
|
335
335
|
correctTextOffset={true}
|
|
336
336
|
actionIconSize="15px"
|
|
337
337
|
borderRadiusTopLeft={isNested ? '18px' : '25px'}
|
|
@@ -6,6 +6,7 @@ type TreeDirectory = SvelteComponent<{
|
|
|
6
6
|
children?: any[] | undefined;
|
|
7
7
|
data?: any;
|
|
8
8
|
variant?: BaseContainerVariant | undefined;
|
|
9
|
+
icon?: string | undefined;
|
|
9
10
|
suffixIcon?: string | undefined;
|
|
10
11
|
isPending?: boolean | undefined;
|
|
11
12
|
}[] | undefined;
|
|
@@ -34,6 +35,7 @@ type TreeDirectory = SvelteComponent<{
|
|
|
34
35
|
children?: any[] | undefined;
|
|
35
36
|
data?: any;
|
|
36
37
|
variant?: BaseContainerVariant | undefined;
|
|
38
|
+
icon?: string | undefined;
|
|
37
39
|
suffixIcon?: string | undefined;
|
|
38
40
|
isPending?: boolean | undefined;
|
|
39
41
|
};
|
|
@@ -56,6 +58,7 @@ declare const TreeDirectory: $$__sveltets_2_IsomorphicComponent<{
|
|
|
56
58
|
children?: any[];
|
|
57
59
|
data?: any;
|
|
58
60
|
variant?: import("../Base/variantTypes.js").BaseContainerVariant;
|
|
61
|
+
icon?: string;
|
|
59
62
|
suffixIcon?: string;
|
|
60
63
|
isPending?: boolean;
|
|
61
64
|
}[] | undefined;
|
|
@@ -84,6 +87,7 @@ declare const TreeDirectory: $$__sveltets_2_IsomorphicComponent<{
|
|
|
84
87
|
children?: any[];
|
|
85
88
|
data?: any;
|
|
86
89
|
variant?: import("../Base/variantTypes.js").BaseContainerVariant;
|
|
90
|
+
icon?: string;
|
|
87
91
|
suffixIcon?: string;
|
|
88
92
|
isPending?: boolean;
|
|
89
93
|
};
|