@floegence/floe-webapp-core 0.86.64 → 0.86.67
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/dist/components/ui/DirectoryPicker.js +5 -4
- package/dist/components/ui/FileOpenPicker.js +27 -26
- package/dist/components/ui/FileSavePicker.js +29 -28
- package/dist/components/ui/picker/PickerBase.d.ts +1 -0
- package/dist/components/ui/picker/PickerBase.js +242 -213
- package/dist/components/ui/picker/PickerNavigation.d.ts +2 -0
- package/dist/components/ui/picker/PickerNavigation.js +84 -79
- package/dist/progress-shimmer.css +10 -0
- package/dist/styles.css +1 -1
- package/package.json +1 -1
|
@@ -1,8 +1,8 @@
|
|
|
1
1
|
import { createComponent as n, mergeProps as s, insert as i, effect as g, setAttribute as u, template as m } from "solid-js/web";
|
|
2
2
|
import { createMemo as f } from "solid-js";
|
|
3
|
-
import { cn as
|
|
3
|
+
import { cn as h } from "../../utils/cn.js";
|
|
4
4
|
import { Button as o } from "./Button.js";
|
|
5
|
-
import { Dialog as
|
|
5
|
+
import { Dialog as d } from "./Dialog.js";
|
|
6
6
|
import { usePickerNavigation as v, PickerPanel as P, pickerCopy as b } from "./picker/PickerBase.js";
|
|
7
7
|
import { parsePickerPath as w } from "./picker/PickerNavigation.js";
|
|
8
8
|
var C = /* @__PURE__ */ m('<div class="flex w-full items-center gap-2"><span class="min-w-0 flex-1 truncate text-[length:var(--floe-type-caption)] text-[var(--floe-ink-soft)]">');
|
|
@@ -12,7 +12,8 @@ function $(e) {
|
|
|
12
12
|
const r = t.currentPath();
|
|
13
13
|
e.onSelect(r), e.onOpenChange(!1);
|
|
14
14
|
};
|
|
15
|
-
return n(
|
|
15
|
+
return n(d, {
|
|
16
|
+
escapeKeyPhase: "bubble",
|
|
16
17
|
get open() {
|
|
17
18
|
return e.open;
|
|
18
19
|
},
|
|
@@ -23,7 +24,7 @@ function $(e) {
|
|
|
23
24
|
return e.title ?? "Select Directory";
|
|
24
25
|
},
|
|
25
26
|
get class() {
|
|
26
|
-
return
|
|
27
|
+
return h("max-w-lg", e.class);
|
|
27
28
|
},
|
|
28
29
|
get footer() {
|
|
29
30
|
return (() => {
|
|
@@ -1,34 +1,34 @@
|
|
|
1
|
-
import { createComponent as a, insert as c, mergeProps as z, spread as
|
|
2
|
-
import { createSignal as U, mergeProps as Y, createMemo as q, Show as
|
|
1
|
+
import { createComponent as a, insert as c, mergeProps as z, spread as E, use as L, effect as j, setAttribute as M, className as V, memo as H, template as v, delegateEvents as R } from "solid-js/web";
|
|
2
|
+
import { createSignal as U, mergeProps as Y, createMemo as q, Show as w, For as G } from "solid-js";
|
|
3
3
|
import { cn as N } from "../../utils/cn.js";
|
|
4
4
|
import { deferNonBlocking as J } from "../../utils/defer.js";
|
|
5
5
|
import { Check as Q } from "../icons/index.js";
|
|
6
6
|
import { FileItemIcon as W } from "../file-browser/FileIcons.js";
|
|
7
7
|
import { Button as D } from "./Button.js";
|
|
8
8
|
import { Dialog as X } from "./Dialog.js";
|
|
9
|
-
import { usePickerNavigation as Z, PickerPanel as ee, normalizePath as
|
|
9
|
+
import { usePickerNavigation as Z, PickerPanel as ee, normalizePath as y, pickerCopy as b } from "./picker/PickerBase.js";
|
|
10
10
|
import { pickerParentPath as te } from "./picker/PickerNavigation.js";
|
|
11
11
|
var ne = /* @__PURE__ */ v('<div class="flex min-h-[140px] overflow-hidden rounded-xs border border-[var(--floe-line)]"><div>'), ie = /* @__PURE__ */ v('<div class="flex flex-col gap-2 -mt-1">'), le = /* @__PURE__ */ v('<div class="flex items-center w-full gap-2"><span class="flex-1 text-[length:var(--floe-type-caption)] text-[var(--floe-ink-soft)] truncate">'), re = /* @__PURE__ */ v('<div class="flex h-full items-center justify-center px-4 text-center text-[length:var(--floe-type-supporting)] text-[var(--floe-ink-soft)]">'), oe = /* @__PURE__ */ v('<span class="ml-auto flex h-5 min-w-5 items-center justify-center rounded-full bg-primary px-1 text-caption text-primary-foreground">'), ae = /* @__PURE__ */ v("<button type=button role=option><span class=truncate>");
|
|
12
12
|
function ce(e, s) {
|
|
13
|
-
const u =
|
|
13
|
+
const u = k(s), d = /* @__PURE__ */ new Set(), f = [];
|
|
14
14
|
for (const h of e ?? []) {
|
|
15
|
-
const i =
|
|
15
|
+
const i = y(h);
|
|
16
16
|
if (!(i === "/" || d.has(i)) && (d.add(i), f.push(i), f.length >= u))
|
|
17
17
|
break;
|
|
18
18
|
}
|
|
19
19
|
return f;
|
|
20
20
|
}
|
|
21
21
|
function se(e, s, u, d) {
|
|
22
|
-
const f =
|
|
22
|
+
const f = y(s);
|
|
23
23
|
if (f === "/") return [...e];
|
|
24
24
|
if (u === "single") return [f];
|
|
25
25
|
const h = e.indexOf(f);
|
|
26
|
-
return h >= 0 ? e.filter((i, g) => g !== h) : e.length >=
|
|
26
|
+
return h >= 0 ? e.filter((i, g) => g !== h) : e.length >= k(d) ? [...e] : [...e, f];
|
|
27
27
|
}
|
|
28
|
-
function
|
|
28
|
+
function k(e) {
|
|
29
29
|
return e == null || !Number.isFinite(e) ? Number.POSITIVE_INFINITY : Math.max(1, Math.floor(e));
|
|
30
30
|
}
|
|
31
|
-
function
|
|
31
|
+
function ye(e) {
|
|
32
32
|
const s = () => e.selectionMode ?? "single", [u, d] = U([]), f = () => {
|
|
33
33
|
if (e.initialPath) return e.initialPath;
|
|
34
34
|
const t = e.initialSelectedPaths?.[0];
|
|
@@ -42,17 +42,18 @@ function ke(e) {
|
|
|
42
42
|
}
|
|
43
43
|
}), i = Z(h, () => e.open, void 0, () => {
|
|
44
44
|
d(ce(e.initialSelectedPaths, s() === "single" ? 1 : e.maxSelections));
|
|
45
|
-
}), g = q(() => i.entries().filter((t) => t.type === "file" && (!e.fileFilter || e.fileFilter(t)))), T = (t) => u().indexOf(
|
|
45
|
+
}), g = q(() => i.entries().filter((t) => t.type === "file" && (!e.fileFilter || e.fileFilter(t)))), T = (t) => u().indexOf(y(t)), K = () => s() === "multiple" && u().length >= k(e.maxSelections), A = (t) => {
|
|
46
46
|
d((o) => se(o, t.path, s(), e.maxSelections));
|
|
47
47
|
}, P = (t = u()) => {
|
|
48
48
|
if (e.disabled || t.length === 0 || i.view() !== "browse" || !i.valid()) return;
|
|
49
49
|
const o = e.onSelect;
|
|
50
50
|
e.onOpenChange(!1), J(() => o([...t]));
|
|
51
|
-
},
|
|
51
|
+
}, B = (t, o) => {
|
|
52
52
|
let l;
|
|
53
53
|
t.key === "ArrowDown" && (l = Math.min(o + 1, g().length - 1)), t.key === "ArrowUp" && (l = Math.max(o - 1, 0)), t.key === "Home" && (l = 0), t.key === "End" && (l = g().length - 1), !(l == null || l < 0) && (t.preventDefault(), $[l]?.focus());
|
|
54
54
|
}, $ = [];
|
|
55
55
|
return a(X, {
|
|
56
|
+
escapeKeyPhase: "bubble",
|
|
56
57
|
get open() {
|
|
57
58
|
return e.open;
|
|
58
59
|
},
|
|
@@ -70,13 +71,13 @@ function ke(e) {
|
|
|
70
71
|
var t = le(), o = t.firstChild;
|
|
71
72
|
return c(o, (() => {
|
|
72
73
|
var l = H(() => u().length === 0);
|
|
73
|
-
return () => l() ?
|
|
74
|
+
return () => l() ? b(e).noFilesSelected : b(e).selectedCount(u().length);
|
|
74
75
|
})()), c(t, a(D, {
|
|
75
76
|
variant: "ghost",
|
|
76
77
|
size: "sm",
|
|
77
78
|
onClick: () => e.onOpenChange(!1),
|
|
78
79
|
get children() {
|
|
79
|
-
return e.cancelText ??
|
|
80
|
+
return e.cancelText ?? b(e).cancel;
|
|
80
81
|
}
|
|
81
82
|
}), null), c(t, a(D, {
|
|
82
83
|
variant: "primary",
|
|
@@ -95,26 +96,26 @@ function ke(e) {
|
|
|
95
96
|
var t = ie();
|
|
96
97
|
return c(t, a(ee, z(e, {
|
|
97
98
|
source: i
|
|
98
|
-
})), null), c(t, a(
|
|
99
|
+
})), null), c(t, a(w, {
|
|
99
100
|
get when() {
|
|
100
101
|
return i.view() === "browse";
|
|
101
102
|
},
|
|
102
103
|
get children() {
|
|
103
104
|
var o = ne(), l = o.firstChild;
|
|
104
|
-
return
|
|
105
|
+
return E(l, z(() => e.scrollViewportProps, {
|
|
105
106
|
class: "max-h-[200px] min-h-[140px] min-w-0 flex-1 overflow-y-auto",
|
|
106
107
|
role: "listbox",
|
|
107
108
|
get "aria-multiselectable"() {
|
|
108
109
|
return s() === "multiple" ? "true" : void 0;
|
|
109
110
|
}
|
|
110
|
-
}), !1, !0), c(l, a(
|
|
111
|
+
}), !1, !0), c(l, a(w, {
|
|
111
112
|
get when() {
|
|
112
113
|
return g().length > 0;
|
|
113
114
|
},
|
|
114
115
|
get fallback() {
|
|
115
116
|
return (() => {
|
|
116
117
|
var m = re();
|
|
117
|
-
return c(m, () => e.emptyText ??
|
|
118
|
+
return c(m, () => e.emptyText ?? b(e).emptyFiles), m;
|
|
118
119
|
})();
|
|
119
120
|
},
|
|
120
121
|
get children() {
|
|
@@ -123,24 +124,24 @@ function ke(e) {
|
|
|
123
124
|
return g();
|
|
124
125
|
},
|
|
125
126
|
children: (m, S) => {
|
|
126
|
-
const x = () => T(m.path), F = () =>
|
|
127
|
+
const x = () => T(m.path), F = () => K() && x() < 0;
|
|
127
128
|
return (() => {
|
|
128
129
|
var r = ae(), _ = r.firstChild;
|
|
129
|
-
return r.$$keydown = (n) =>
|
|
130
|
-
s() === "single" && P([
|
|
131
|
-
}, r.$$click = () =>
|
|
130
|
+
return r.$$keydown = (n) => B(n, S()), r.$$dblclick = () => {
|
|
131
|
+
s() === "single" && P([y(m.path)]);
|
|
132
|
+
}, r.$$click = () => A(m), L((n) => {
|
|
132
133
|
$[S()] = n;
|
|
133
134
|
}, r), c(r, a(W, {
|
|
134
135
|
item: m,
|
|
135
136
|
size: 16,
|
|
136
137
|
class: "w-4 h-4 flex-shrink-0"
|
|
137
|
-
}), _), c(_, () => m.name), c(r, a(
|
|
138
|
+
}), _), c(_, () => m.name), c(r, a(w, {
|
|
138
139
|
get when() {
|
|
139
140
|
return x() >= 0;
|
|
140
141
|
},
|
|
141
142
|
get children() {
|
|
142
143
|
var n = oe();
|
|
143
|
-
return c(n, a(
|
|
144
|
+
return c(n, a(w, {
|
|
144
145
|
get when() {
|
|
145
146
|
return s() === "multiple";
|
|
146
147
|
},
|
|
@@ -155,8 +156,8 @@ function ke(e) {
|
|
|
155
156
|
})), n;
|
|
156
157
|
}
|
|
157
158
|
}), null), j((n) => {
|
|
158
|
-
var
|
|
159
|
-
return
|
|
159
|
+
var p = x() >= 0, C = F(), I = F() ? b(e).selectionLimit : m.name, O = N("flex min-h-9 w-full cursor-pointer items-center gap-2 px-2 py-1.5 text-left text-xs", "transition-colors duration-[var(--floe-duration-fast)] ease-[var(--floe-ease-out)] hover:bg-[var(--floe-state-hover)]", "focus:outline-none focus-visible:ring-1 focus-visible:ring-inset focus-visible:ring-ring", "disabled:cursor-not-allowed disabled:opacity-45", x() >= 0 && "bg-[var(--floe-state-selected)] text-foreground font-medium");
|
|
160
|
+
return p !== n.e && M(r, "aria-selected", n.e = p), C !== n.t && (r.disabled = n.t = C), I !== n.a && M(r, "title", n.a = I), O !== n.o && V(r, n.o = O), n;
|
|
160
161
|
}, {
|
|
161
162
|
e: void 0,
|
|
162
163
|
t: void 0,
|
|
@@ -175,7 +176,7 @@ function ke(e) {
|
|
|
175
176
|
}
|
|
176
177
|
R(["click", "dblclick", "keydown"]);
|
|
177
178
|
export {
|
|
178
|
-
|
|
179
|
+
ye as FileOpenPicker,
|
|
179
180
|
ce as normalizeFileOpenSelection,
|
|
180
181
|
se as updateFileOpenSelection
|
|
181
182
|
};
|
|
@@ -1,6 +1,6 @@
|
|
|
1
|
-
import { createComponent as a, insert as n, mergeProps as
|
|
2
|
-
import { createSignal as
|
|
3
|
-
import { cn as
|
|
1
|
+
import { createComponent as a, insert as n, mergeProps as w, spread as z, effect as b, className as B, setAttribute as E, template as f, delegateEvents as D } from "solid-js/web";
|
|
2
|
+
import { createSignal as k, createMemo as _, createEffect as I, on as K, Show as h, For as O } from "solid-js";
|
|
3
|
+
import { cn as F } from "../../utils/cn.js";
|
|
4
4
|
import { Dialog as T } from "./Dialog.js";
|
|
5
5
|
import { Button as C } from "./Button.js";
|
|
6
6
|
import { Input as M } from "./Input.js";
|
|
@@ -9,17 +9,17 @@ import { deferNonBlocking as q } from "../../utils/defer.js";
|
|
|
9
9
|
import { usePickerNavigation as A, PickerPanel as R, pickerCopy as d } from "./picker/PickerBase.js";
|
|
10
10
|
var V = /* @__PURE__ */ f('<div class="flex min-h-[100px] overflow-hidden rounded-xs border border-[var(--floe-line)]"><div>'), G = /* @__PURE__ */ f('<div class="flex flex-col gap-2 -mt-1">'), H = /* @__PURE__ */ f('<div class="flex flex-col w-full gap-2"><div class="flex items-center gap-1.5"><label class="text-[length:var(--floe-type-supporting)] text-[var(--floe-ink-soft)] flex-shrink-0"></label><div class=flex-1></div></div><div class="flex items-center gap-2"><span class="flex-1 text-[length:var(--floe-type-caption)] text-[var(--floe-ink-soft)] truncate">'), J = /* @__PURE__ */ f('<div class="flex items-center justify-center h-full text-[length:var(--floe-type-supporting)] text-[var(--floe-ink-soft)]">'), L = /* @__PURE__ */ f('<span class="ml-auto text-[length:var(--floe-type-caption)] text-[var(--floe-ink-ghost)] flex-shrink-0">'), Q = /* @__PURE__ */ f("<button type=button><span class=truncate>");
|
|
11
11
|
function ie(e) {
|
|
12
|
-
const [
|
|
12
|
+
const [c, g] = k(e.initialFileName ?? ""), [N, u] = k(""), o = A(e, () => e.open, void 0, () => {
|
|
13
13
|
g(e.initialFileName ?? ""), u("");
|
|
14
|
-
}), x =
|
|
15
|
-
I(
|
|
14
|
+
}), x = _(() => o.entries().filter((t) => t.type === "file"));
|
|
15
|
+
I(K(c, () => {
|
|
16
16
|
u("");
|
|
17
17
|
}));
|
|
18
18
|
const y = (t) => {
|
|
19
19
|
g(t.name), u("");
|
|
20
20
|
}, $ = () => {
|
|
21
21
|
if (e.disabled || o.view() !== "browse" || !o.valid()) return;
|
|
22
|
-
const t =
|
|
22
|
+
const t = c().trim();
|
|
23
23
|
if (!t) {
|
|
24
24
|
u(d(e).fileNameRequired);
|
|
25
25
|
return;
|
|
@@ -31,17 +31,18 @@ function ie(e) {
|
|
|
31
31
|
return;
|
|
32
32
|
}
|
|
33
33
|
}
|
|
34
|
-
const l = o.currentPath(),
|
|
35
|
-
e.onOpenChange(!1), q(() =>
|
|
36
|
-
},
|
|
34
|
+
const l = o.currentPath(), s = e.onSave;
|
|
35
|
+
e.onOpenChange(!1), q(() => s(l, t));
|
|
36
|
+
}, P = () => {
|
|
37
37
|
e.onOpenChange(!1);
|
|
38
|
-
},
|
|
38
|
+
}, S = (t) => {
|
|
39
39
|
t.key === "Enter" && (t.preventDefault(), $());
|
|
40
|
-
},
|
|
41
|
-
const t = o.currentPath(), l =
|
|
40
|
+
}, p = _(() => {
|
|
41
|
+
const t = o.currentPath(), l = c().trim();
|
|
42
42
|
return l ? t === "/" ? `/${l}` : `${t}/${l}` : t;
|
|
43
43
|
});
|
|
44
44
|
return a(T, {
|
|
45
|
+
escapeKeyPhase: "bubble",
|
|
45
46
|
get open() {
|
|
46
47
|
return e.open;
|
|
47
48
|
},
|
|
@@ -52,26 +53,26 @@ function ie(e) {
|
|
|
52
53
|
return e.title ?? "Save File";
|
|
53
54
|
},
|
|
54
55
|
get class() {
|
|
55
|
-
return
|
|
56
|
+
return F("max-w-2xl", e.class);
|
|
56
57
|
},
|
|
57
58
|
get footer() {
|
|
58
59
|
return (() => {
|
|
59
|
-
var t = H(), l = t.firstChild,
|
|
60
|
-
return n(
|
|
60
|
+
var t = H(), l = t.firstChild, s = l.firstChild, r = s.nextSibling, i = l.nextSibling, m = i.firstChild;
|
|
61
|
+
return n(s, () => d(e).fileName), n(r, a(M, {
|
|
61
62
|
size: "sm",
|
|
62
63
|
get value() {
|
|
63
|
-
return
|
|
64
|
+
return c();
|
|
64
65
|
},
|
|
65
66
|
onInput: (v) => g(v.currentTarget.value),
|
|
66
|
-
onKeyDown:
|
|
67
|
+
onKeyDown: S,
|
|
67
68
|
placeholder: "filename.ext",
|
|
68
69
|
get error() {
|
|
69
70
|
return N();
|
|
70
71
|
}
|
|
71
|
-
})), n(m,
|
|
72
|
+
})), n(m, p), n(i, a(C, {
|
|
72
73
|
variant: "ghost",
|
|
73
74
|
size: "sm",
|
|
74
|
-
onClick:
|
|
75
|
+
onClick: P,
|
|
75
76
|
get children() {
|
|
76
77
|
return e.cancelText ?? d(e).cancel;
|
|
77
78
|
}
|
|
@@ -80,27 +81,27 @@ function ie(e) {
|
|
|
80
81
|
size: "sm",
|
|
81
82
|
onClick: $,
|
|
82
83
|
get disabled() {
|
|
83
|
-
return !
|
|
84
|
+
return !c().trim() || o.view() !== "browse" || !o.valid();
|
|
84
85
|
},
|
|
85
86
|
get children() {
|
|
86
87
|
return e.confirmText ?? "Save";
|
|
87
88
|
}
|
|
88
|
-
}), null),
|
|
89
|
+
}), null), b(() => E(m, "title", p())), t;
|
|
89
90
|
})();
|
|
90
91
|
},
|
|
91
92
|
get children() {
|
|
92
93
|
var t = G();
|
|
93
|
-
return n(t, a(R,
|
|
94
|
+
return n(t, a(R, w(e, {
|
|
94
95
|
source: o
|
|
95
96
|
})), null), n(t, a(h, {
|
|
96
97
|
get when() {
|
|
97
98
|
return o.view() === "browse";
|
|
98
99
|
},
|
|
99
100
|
get children() {
|
|
100
|
-
var l = V(),
|
|
101
|
-
return z(
|
|
101
|
+
var l = V(), s = l.firstChild;
|
|
102
|
+
return z(s, w(() => e.scrollViewportProps, {
|
|
102
103
|
class: "max-h-[160px] w-full min-w-0 overflow-y-auto"
|
|
103
|
-
}), !1, !0), n(
|
|
104
|
+
}), !1, !0), n(s, a(h, {
|
|
104
105
|
get when() {
|
|
105
106
|
return x().length > 0;
|
|
106
107
|
},
|
|
@@ -111,7 +112,7 @@ function ie(e) {
|
|
|
111
112
|
})();
|
|
112
113
|
},
|
|
113
114
|
get children() {
|
|
114
|
-
return a(
|
|
115
|
+
return a(O, {
|
|
115
116
|
get each() {
|
|
116
117
|
return x();
|
|
117
118
|
},
|
|
@@ -129,7 +130,7 @@ function ie(e) {
|
|
|
129
130
|
var v = L();
|
|
130
131
|
return n(v, () => U(r.size)), v;
|
|
131
132
|
}
|
|
132
|
-
}), null),
|
|
133
|
+
}), null), b(() => B(i, F("flex items-center gap-1.5 w-full text-left text-xs py-1.5 px-2 cursor-pointer", "transition-colors duration-[var(--floe-duration-instant)]", "hover:bg-[var(--floe-state-hover)]", "focus:outline-none focus-visible:ring-1 focus-visible:ring-inset focus-visible:ring-ring", c() === r.name && "bg-[var(--floe-state-selected)] text-foreground font-medium"))), i;
|
|
133
134
|
})()
|
|
134
135
|
});
|
|
135
136
|
}
|
|
@@ -67,6 +67,7 @@ export declare function usePickerNavigation(props: PickerPanelProps, open: Acces
|
|
|
67
67
|
open: (path?: string) => Promise<void>;
|
|
68
68
|
close: () => void;
|
|
69
69
|
navigate: (rawPath: string) => Promise<boolean>;
|
|
70
|
+
captureIntent(): () => boolean;
|
|
70
71
|
setPathInput(value: string): void;
|
|
71
72
|
setShowHidden(value: boolean): Promise<void>;
|
|
72
73
|
retry(): Promise<void>;
|