vintage-frames 0.18.0 → 0.19.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.
@@ -2,31 +2,32 @@ import { snapSys as e, systemPxQuantum as t } from "../scale.js";
2
2
  import { prefersReducedMotion as n } from "../motion.js";
3
3
  import { windowChrome as r } from "../window-chrome.js";
4
4
  import "../index.js";
5
- import { FOLDER as i, TRASH as a, appIdOf as o, childrenOf as s, enclosingFolders as c, isContainerKind as l, isInside as u, isTrashed as d, isVolume as f, itemCount as p } from "./catalog.js";
6
- import { cleanUp as ee, collisions as te, desktopLattice as ne, fieldExtent as re, fillOrder as ie, folderLattice as ae, frameOf as oe, nextFreeCell as se, pinOf as ce, pinTo as le, trashCell as ue } from "./geometry.js";
7
- import { desktopRendered as de } from "./windows.js";
8
- import { defineApp as m } from "./shell.js";
9
- import { fileByDrag as fe } from "./filing.js";
10
- import { composeAlert as pe } from "./alert.js";
5
+ import { ALIAS_KIND as i, APPLE_MENU_ITEMS as a, FOLDER as o, STARTUP_ITEMS as s, SYSTEM_FOLDER as c, TRASH as l, aliasName as u, appIdOf as ee, childrenOf as te, containerOf as ne, enclosingFolders as re, isContainerKind as d, isInside as ie, isKept as f, isTrashed as p, itemCount as m, resolve as h } from "./catalog.js";
6
+ import { cleanUp as ae, collisions as oe, desktopLattice as se, fieldExtent as ce, fillOrder as le, folderLattice as ue, frameOf as de, freeCellNear as fe, nextFreeCell as pe, pinOf as me, pinTo as he, trashCell as ge } from "./geometry.js";
7
+ import { desktopRendered as _e } from "./windows.js";
8
+ import { defineApp as g } from "./shell.js";
9
+ import { fileByDrag as ve } from "./filing.js";
10
+ import { composeAlert as ye } from "./alert.js";
11
11
  //#region src/shell/finder.ts
12
- var h = "finder", me = 306, he = 300, ge = {
12
+ var _ = "finder", be = 306, xe = 300, Se = {
13
13
  "new-folder": "New Folder",
14
14
  "empty-trash": "Empty Trash",
15
15
  paste: "Paste",
16
- "add-file": "Adding the file"
17
- }, _e = 20, ve = 18, g = {
16
+ "add-file": "Adding the file",
17
+ "make-alias": "Make Alias"
18
+ }, Ce = 20, we = 18, v = {
18
19
  left: 8,
19
20
  top: 2
20
- }, _ = {
21
+ }, y = {
21
22
  width: 12,
22
23
  height: 12
23
- }, v = {
24
- left: g.left - 1,
25
- top: g.top
26
- }, ye = {
27
- left: v.left + _.width + 3,
28
- top: g.top
29
- }, y = [
24
+ }, b = {
25
+ left: v.left - 1,
26
+ top: v.top
27
+ }, Te = {
28
+ left: b.left + y.width + 3,
29
+ top: v.top
30
+ }, x = [
30
31
  {
31
32
  menu: "file",
32
33
  label: "File",
@@ -41,6 +42,11 @@ var h = "finder", me = 306, he = 300, ge = {
41
42
  "close",
42
43
  "Close",
43
44
  "⌃W"
45
+ ],
46
+ [
47
+ "make-alias",
48
+ "Make Alias",
49
+ "⌘M"
44
50
  ]
45
51
  ]
46
52
  },
@@ -79,24 +85,29 @@ var h = "finder", me = 306, he = 300, ge = {
79
85
  label: "Special",
80
86
  items: [["clean-up", "Clean Up Desktop"], ["empty-trash", "Empty Trash…"]]
81
87
  }
82
- ];
83
- function b(e) {
84
- return y.map(({ menu: t, label: n, items: r }) => {
85
- let i = r.filter(([t]) => e(t)).map(([e, t, n], r) => `${e === "close" && r > 0 ? "<vf-separator></vf-separator>" : ""}<vf-menu-item value="${e}"${n ? ` shortcut="${n}"` : ""}>${t}</vf-menu-item>`);
88
+ ], S = [
89
+ c,
90
+ a,
91
+ s
92
+ ], C = /* @__PURE__ */ new Set(["close", "make-alias"]);
93
+ function w(e) {
94
+ return x.map(({ menu: t, label: n, items: r }) => {
95
+ let i = r.filter(([t]) => e(t)).map(([e, t, n], r) => `${C.has(e) && r > 0 ? "<vf-separator></vf-separator>" : ""}<vf-menu-item value="${e}"${n ? ` shortcut="${n}"` : ""}>${t}</vf-menu-item>`);
86
96
  return i.length ? `<vf-menu data-menu="${t}" label="${n}">${i.join("")}</vf-menu>` : "";
87
97
  }).join("");
88
98
  }
89
- var be = (e) => e.localName === "vf-icon" && e.dataset.app != null || e instanceof HTMLTemplateElement && e.dataset.folder != null;
90
- function xe(e) {
99
+ var Ee = (e) => e.localName === "vf-icon" && e.dataset.app != null || e instanceof HTMLTemplateElement && (e.dataset.folder != null || e.dataset.system != null);
100
+ function De(e) {
91
101
  let t = (e, t) => e != null && t != null && Number.isFinite(+e) && Number.isFinite(+t) ? {
92
102
  left: +e,
93
103
  top: +t
94
104
  } : void 0, n = [];
95
- for (let r of [...e.children].filter(be)) r instanceof HTMLTemplateElement ? n.push({
96
- kind: i,
105
+ for (let r of [...e.children].filter(Ee)) r instanceof HTMLTemplateElement ? n.push({
106
+ kind: o,
97
107
  name: r.dataset.folder ?? null,
98
108
  at: t(r.dataset.left, r.dataset.top),
99
- children: xe(r.content)
109
+ into: r.dataset.system,
110
+ children: De(r.content)
100
111
  }) : n.push({
101
112
  kind: "app",
102
113
  name: r.getAttribute("label"),
@@ -106,13 +117,17 @@ function xe(e) {
106
117
  });
107
118
  return n;
108
119
  }
109
- function x(i) {
110
- let x = i.volumes?.trash !== !1, S = (e) => i.commands?.[e] !== !1 && (e !== "empty-trash" || x), Se = [], Ce = (e) => e, C = i.seed === "markup" ? async (e) => {
120
+ function T(a) {
121
+ let o = a.volumes?.trash !== !1, s = (e) => a.commands?.[e] !== !1 && (e !== "empty-trash" || o), c = [], C = (e) => e, T = a.seed === "markup" ? async (e) => {
111
122
  let t = Date.now(), n = async (r, i) => {
112
123
  for (let a of r) {
124
+ if (a.into != null) {
125
+ S.includes(a.into) && e.item(a.into) && await n(a.children, a.into);
126
+ continue;
127
+ }
113
128
  let r = await e.create({
114
129
  kind: a.kind,
115
- name: a.name ?? (a.app == null ? void 0 : Ce(a.app)),
130
+ name: a.name ?? (a.app == null ? void 0 : C(a.app)),
116
131
  parent: i,
117
132
  ...a.at,
118
133
  ...a.app == null ? {} : { data: { app: a.app } },
@@ -121,90 +136,98 @@ function x(i) {
121
136
  r && a.children.length && await n(a.children, r.id);
122
137
  }
123
138
  };
124
- await n(Se, null);
125
- } : i.seed;
126
- return m({
127
- id: h,
139
+ await n(c, null);
140
+ } : a.seed;
141
+ return g({
142
+ id: _,
128
143
  name: "Finder",
129
- menus: b(S),
130
- dialogs: i.dialogs,
144
+ menus: w(s),
145
+ dialogs: a.dialogs,
131
146
  catalog: {
132
- storage: i.storage,
133
- volumes: i.volumes,
134
- seed: C
147
+ storage: a.storage,
148
+ volumes: a.volumes,
149
+ system: a.system,
150
+ seed: T
135
151
  },
136
- init(m) {
137
- let { desktop: b, windows: C } = m, w = m.catalog, T = i.art;
138
- Ce = (e) => m.app(e)?.name ?? e;
139
- let E = i.lattice?.desktop?.cell ?? 64, we = i.lattice?.folder?.cell ?? 64, Te = i.window ?? {
152
+ init(g) {
153
+ let { desktop: S, windows: w } = g, T = g.catalog, E = a.art;
154
+ C = (e) => g.app(e)?.name ?? e;
155
+ let D = a.lattice?.desktop?.cell ?? 64, O = a.lattice?.folder?.cell ?? 64, Oe = a.window ?? {
140
156
  width: 320,
141
157
  height: 223
142
- }, D = r({
158
+ }, k = r({
143
159
  scrollbars: "both",
144
- headerHeight: _e
145
- }), Ee = /* @__PURE__ */ new Map();
146
- async function O(e, t, n, r = {}) {
147
- let i = Ee.get(e);
160
+ headerHeight: Ce
161
+ }), ke = /* @__PURE__ */ new Map();
162
+ async function A(e, t, n, r = {}) {
163
+ let i = ke.get(e);
148
164
  if (i) return i(t);
149
- let a = pe(n, {
150
- art: T.caution ?? null,
165
+ let a = ye(n, {
166
+ art: E.caution ?? null,
151
167
  ...r
152
168
  });
153
- m.hold(a.dialog);
169
+ g.hold(a.dialog);
154
170
  try {
155
171
  await a.rendered();
156
- let e = m.ask(a.dialog);
172
+ let e = g.ask(a.dialog);
157
173
  return a.fit(), await e;
158
174
  } finally {
159
- m.release(a.dialog);
175
+ g.release(a.dialog);
160
176
  }
161
177
  }
162
- let k = (e) => (t) => {
178
+ let j = (e) => (t) => {
163
179
  let n = t;
164
- O("failed", {
180
+ A("failed", {
165
181
  action: e,
166
182
  error: n
167
- }, `${ge[e]} failed: ${n.message}.`);
168
- }, A = b.querySelector(":scope > vf-icon-field"), De = !A;
169
- if (!A) {
170
- A = document.createElement("vf-icon-field"), A.label = "Desktop", A.toggleAttribute("fill-width", !0), A.toggleAttribute("fill-height", !0);
171
- let e = b.querySelector(":scope > vf-menu-bar");
172
- e ? e.after(A) : b.prepend(A);
183
+ }, `${Se[e]} failed: ${n.message}.`);
184
+ }, M = S.querySelector(":scope > vf-icon-field"), Ae = !M;
185
+ if (!M) {
186
+ M = document.createElement("vf-icon-field"), M.label = "Desktop", M.toggleAttribute("fill-width", !0), M.toggleAttribute("fill-height", !0);
187
+ let e = S.querySelector(":scope > vf-menu-bar");
188
+ e ? e.after(M) : S.prepend(M);
173
189
  }
174
- let j = A, Oe = [...j.children].filter(be);
175
- Se = xe(j);
176
- for (let e of Oe) e.remove();
177
- let ke = () => C.windowsOf(h).map((e) => [C.itemOf(e), e]).filter((e) => e[0] != null), M = (e) => e.querySelector(":scope > vf-icon-field"), N = () => [[null, j], ...ke().flatMap(([e, t]) => {
178
- let n = M(t);
190
+ let N = M, je = [...N.children].filter(Ee);
191
+ c = De(N);
192
+ for (let e of je) e.remove();
193
+ let Me = () => w.windowsOf(_).map((e) => [w.itemOf(e), e]).filter((e) => e[0] != null), Ne = (e) => e.querySelector(":scope > vf-icon-field"), Pe = () => [[null, N], ...Me().flatMap(([e, t]) => {
194
+ let n = Ne(t);
179
195
  return n ? [[e, n]] : [];
180
- })], Ae = (e) => N().find(([t]) => t === e)?.[1] ?? null, P = (e) => [...e.querySelectorAll(":scope > vf-icon[data-id]")], F = () => N().flatMap(([, e]) => P(e)), I = (e) => e.dataset.id, L = (e) => F().find((t) => I(t) === e) ?? null, R = (e) => ({
196
+ })], Fe = (e) => Pe().find(([t]) => t === e)?.[1] ?? null, P = (e) => [...e.querySelectorAll(":scope > vf-icon[data-id]")], F = () => Pe().flatMap(([, e]) => P(e)), I = (e) => e.dataset.id, L = (e) => F().find((t) => I(t) === e) ?? null, R = (e) => ({
181
197
  left: e.left ?? 0,
182
198
  top: e.top ?? 0
183
- }), je = (e) => C.itemOf(e.closest("vf-window")), Me = (e) => ({
184
- width: Math.max(0, (e.width ?? 0) - D.left - D.right),
185
- height: Math.max(0, (e.height ?? 0) - D.top - D.bottom)
186
- }), Ne = (e) => {
187
- if (e == null) return ne(b.workArea, i.lattice?.desktop);
188
- let t = C.windowFor(e);
189
- return ae(t ? Me(t).width : 0, i.lattice?.folder);
190
- }, Pe = (e) => {
191
- let t = C.windowFor(e), n = t && M(t);
199
+ }), Ie = (e) => w.itemOf(e.closest("vf-window")), Le = (e) => ({
200
+ width: Math.max(0, (e.width ?? 0) - k.left - k.right),
201
+ height: Math.max(0, (e.height ?? 0) - k.top - k.bottom)
202
+ }), z = (e) => {
203
+ if (e == null) return se(S.workArea, a.lattice?.desktop);
204
+ let t = w.windowFor(e);
205
+ return ue(t ? Le(t).width : 0, a.lattice?.folder);
206
+ }, Re = (e) => {
207
+ let t = w.windowFor(e), n = t && Ne(t);
192
208
  if (!t || !n) return;
193
- let r = re(P(n).map(R), Me(t), { cell: we });
209
+ let r = ce(P(n).map(R), Le(t), { cell: O });
194
210
  n.width !== r.width && (n.width = r.width), n.height !== r.height && (n.height = r.height);
195
- }, Fe = (n, r, i) => {
211
+ }, ze = (n, r, i) => {
196
212
  if (r == null) {
197
- let r = b.workArea, a = t(n), o = (e) => Math.floor(e / a) * a, s = Math.ceil(r.top / a) * a, c = Math.max(r.left, o(r.left + r.width - E)), l = Math.max(s, o(r.top + r.height - E));
213
+ let r = S.workArea, a = t(n), o = (e) => Math.floor(e / a) * a, s = Math.ceil(r.top / a) * a, c = Math.max(r.left, o(r.left + r.width - D)), l = Math.max(s, o(r.top + r.height - D));
198
214
  n.left = Math.min(Math.max(e(i.left, n), r.left), c), n.top = Math.min(Math.max(e(i.top, n), s), l);
199
215
  } else n.left = e(Math.max(0, i.left), n), n.top = e(Math.max(0, i.top), n);
200
- }, Ie = (e) => {
201
- if (e.kind === "folder") return T.folder;
202
- if (e.kind === "trash") return p(w.get(), "trash") ? T.trashFull : T.trash;
203
- if (e.kind === "disk") return T.disk ?? T.folder;
204
- let t = m.kind(e.kind);
205
- return (typeof t?.art == "function" ? t.art(e) : t?.art) || T.document;
216
+ }, Be = (e) => {
217
+ if (e.id === "system-folder") return E.systemFolder ?? E.folder;
218
+ if (e.id === "apple-menu-items") return E.appleMenuItems ?? E.folder;
219
+ if (e.id === "startup-items") return E.startupItems ?? E.folder;
220
+ if (e.kind === "folder") return E.folder;
221
+ if (e.kind === "trash") return m(T.get(), "trash") ? E.trashFull : E.trash;
222
+ if (e.kind === "disk") return E.disk ?? E.folder;
223
+ if (e.kind === "alias") {
224
+ let t = h(T.get(), e.id);
225
+ return t ? Be(t) : E.document;
226
+ }
227
+ let t = g.kind(e.kind);
228
+ return (typeof t?.art == "function" ? t.art(e) : t?.art) || E.document;
206
229
  };
207
- function Le(e, t) {
230
+ function Ve(e, t) {
208
231
  let n = e.querySelector(":scope > vf-img > img");
209
232
  if (!n) {
210
233
  let t = document.createElement("vf-img");
@@ -212,225 +235,259 @@ function x(i) {
212
235
  }
213
236
  n.getAttribute("src") !== t && (n.src = t);
214
237
  }
215
- function Re(e) {
238
+ function He(e) {
216
239
  let t = document.createElement("vf-icon");
217
- return t.dataset.id = e.id, t.label = e.name, t.width = E, t.selectable = !0, t.movable = !0, l(e.kind) && (t.dataset.folder = e.id), t;
240
+ return t.dataset.id = e.id, t.label = e.name, t.width = D, t.selectable = !0, t.movable = !0, d(e.kind) && (t.dataset.folder = e.id), t;
218
241
  }
219
- let z = /* @__PURE__ */ new Set(), B = /* @__PURE__ */ new WeakMap();
220
- function ze(e, t, n, r) {
242
+ let B = /* @__PURE__ */ new Set(), V = /* @__PURE__ */ new WeakMap();
243
+ function Ue(e, t, n, r) {
221
244
  if (t.left != null && t.top != null) {
222
245
  let r = `${t.left},${t.top}`;
223
- if (B.get(e) === r) return;
224
- B.set(e, r), (e.left !== t.left || e.top !== t.top) && Fe(e, n, {
246
+ if (V.get(e) === r) return;
247
+ V.set(e, r), (e.left !== t.left || e.top !== t.top) && ze(e, n, {
225
248
  left: t.left,
226
249
  top: t.top
227
250
  });
228
251
  return;
229
252
  }
230
- let a = P(r).filter((t) => t !== e && t.left != null && t.top != null).map(R), o = n == null && t.id === "trash" ? ue(b.workArea, i.lattice?.desktop) : se(Ne(n), a, n == null ? E : we);
231
- Fe(e, n, o), z.add(e);
253
+ let i = P(r).filter((t) => t !== e && t.left != null && t.top != null).map(R), o = n == null && t.id === "trash" ? ge(S.workArea, a.lattice?.desktop) : pe(z(n), i, n == null ? D : O);
254
+ ze(e, n, o), B.add(e);
232
255
  }
233
- let Be = !1, V = !1;
234
- function H() {
235
- if (!(V || !Be)) {
236
- V = !0;
256
+ let We = !1, H = !1;
257
+ function U() {
258
+ if (!(H || !We)) {
259
+ H = !0;
237
260
  try {
238
- let e = w.get(), t = new Map(F().map((e) => [I(e), e])), n = /* @__PURE__ */ new Set(), r = [], i = [];
239
- for (let [a, c] of N()) for (let l of s(e, a)) {
240
- let e = t.get(l.id) ?? Re(l);
241
- e.parentElement !== c && (c.append(e), e.left = void 0, e.top = void 0, B.delete(e)), n.add(e), e.label !== l.name && (e.label = l.name), e.editable = !f(l.id) && m.kind(l.kind)?.editable !== !1, Le(e, Ie(l));
242
- let s = l.kind === "app" ? C.hasWindows(o(l) ?? "") : C.isOpen(l.id);
243
- e.open !== s && (e.open = s);
244
- let u = () => ze(e, l, a, c);
245
- l.left != null && l.top != null ? r.push(u) : i.push(u);
261
+ let e = T.get(), t = new Map(F().map((e) => [I(e), e])), n = /* @__PURE__ */ new Set(), r = [], a = [];
262
+ for (let [o, s] of Pe()) for (let c of te(e, o)) {
263
+ let e = t.get(c.id) ?? He(c);
264
+ e.parentElement !== s && (s.append(e), e.left = void 0, e.top = void 0, V.delete(e)), n.add(e), e.label !== c.name && (e.label = c.name), e.editable = !f(c.id) && g.kind(c.kind)?.editable !== !1, e.alias = c.kind === i, Ve(e, Be(c));
265
+ let l = c.kind === "app" ? w.hasWindows(ee(c) ?? "") : w.isOpen(c.id);
266
+ e.open !== l && (e.open = l);
267
+ let u = () => Ue(e, c, o, s);
268
+ c.left != null && c.top != null ? r.push(u) : a.push(u);
246
269
  }
247
270
  for (let e of t.values()) n.has(e) || e.remove();
248
- for (let e of [...r, ...i]) e();
249
- for (let [e, t] of ke()) {
250
- let n = M(t), r = w.item(e)?.name;
251
- n && r != null && n.label !== r && (n.label = r), Ue(e), Pe(e);
271
+ for (let e of [...r, ...a]) e();
272
+ for (let [e, t] of Me()) {
273
+ let n = Ne(t), r = T.item(e)?.name;
274
+ n && r != null && n.label !== r && (n.label = r), qe(e), Re(e);
252
275
  }
253
276
  } finally {
254
- V = !1;
277
+ H = !1;
255
278
  }
256
- Ve();
279
+ Ge();
257
280
  }
258
281
  }
259
- let U = !1;
260
- function Ve() {
261
- if (U = !1, !z.size) return;
282
+ let W = !1;
283
+ function Ge() {
284
+ if (W = !1, !B.size) return;
262
285
  let e = /* @__PURE__ */ new Map();
263
- for (let t of z) t.isConnected && t.left != null && t.top != null && e.set(I(t), R(t));
264
- z.clear(), w.place(e);
286
+ for (let t of B) t.isConnected && t.left != null && t.top != null && e.set(I(t), R(t));
287
+ B.clear(), T.place(e);
265
288
  }
266
- m.on(b, "vf-placement-change", (e) => {
289
+ g.on(S, "vf-placement-change", (e) => {
267
290
  let t = e.target;
268
- t.localName === "vf-icon" && t.dataset.id != null && (z.add(t), !U && (U = !0, queueMicrotask(Ve)));
269
- }), m.onDispose(w.subscribe(H)), m.onDispose(C.onWindows(H));
270
- function He() {
291
+ t.localName === "vf-icon" && t.dataset.id != null && (B.add(t), !W && (W = !0, queueMicrotask(Ge)));
292
+ }), g.onDispose(T.subscribe(U)), g.onDispose(w.onWindows(U));
293
+ function Ke() {
271
294
  let e = document.createElement("vf-img");
272
- e.dataset.trashMark = "", e.width = _.width, e.height = _.height, e.left = v.left, e.top = v.top;
295
+ e.dataset.trashMark = "", e.width = y.width, e.height = y.height, e.left = b.left, e.top = b.top;
273
296
  let t = document.createElement("img");
274
- return t.alt = "in the Trash", t.src = T.trashMark, e.append(t), e;
297
+ return t.alt = "in the Trash", t.src = E.trashMark, e.append(t), e;
275
298
  }
276
- function Ue(e) {
277
- let t = C.windowFor(e)?.querySelector(":scope > [slot=\"header\"]"), n = t?.querySelector(":scope > vf-label[data-count]");
299
+ function qe(e) {
300
+ let t = w.windowFor(e)?.querySelector(":scope > [slot=\"header\"]"), n = t?.querySelector(":scope > vf-label[data-count]");
278
301
  if (!t || !n) return;
279
- let r = w.get(), i = p(r, e), a = `${i} item${i === 1 ? "" : "s"}`;
302
+ let r = T.get(), i = m(r, e), a = `${i} item${i === 1 ? "" : "s"}`;
280
303
  n.textContent !== a && (n.textContent = a);
281
- let o = !!T.trashMark && d(r, e), s = t.querySelector(":scope > vf-img[data-trash-mark]");
282
- o && !s ? t.prepend(He()) : !o && s && s.remove();
283
- let c = o ? ye : g;
304
+ let o = !!E.trashMark && p(r, e), s = t.querySelector(":scope > vf-img[data-trash-mark]");
305
+ o && !s ? t.prepend(Ke()) : !o && s && s.remove();
306
+ let c = o ? Te : v;
284
307
  n.left !== c.left && (n.left = c.left);
285
308
  }
286
- function We(e) {
287
- let t = w.item(e)?.name ?? "", n = document.createElement("vf-window");
288
- n.heading = t, n.closable = !0, n.movable = !0, n.outlineDrag = !0, n.resizable = !0, n.scrollbars = "both", n.headerHeight = _e, n.width = Te.width, n.height = Te.height;
309
+ function Je(e) {
310
+ let t = T.item(e)?.name ?? "", n = document.createElement("vf-window");
311
+ n.heading = t, n.closable = !0, n.movable = !0, n.outlineDrag = !0, n.resizable = !0, n.scrollbars = "both", n.headerHeight = Ce, n.width = Oe.width, n.height = Oe.height;
289
312
  let r = document.createElement("vf-container");
290
- r.slot = "header", r.toggleAttribute("fill-width", !0), r.height = ve, r.rule = "bottom";
313
+ r.slot = "header", r.toggleAttribute("fill-width", !0), r.height = we, r.rule = "bottom";
291
314
  let i = document.createElement("vf-label");
292
- i.face = "body", i.dataset.count = "", i.left = g.left, i.top = g.top, r.append(i);
315
+ i.face = "body", i.dataset.count = "", i.left = v.left, i.top = v.top, r.append(i);
293
316
  let a = document.createElement("vf-icon-field");
294
317
  return a.label = t, a.left = 0, a.top = 0, n.append(r, a), n;
295
318
  }
296
- m.on(b, "vf-resize", (e) => {
297
- if (!e.detail?.commit || C.appOf(e.target) !== "finder") return;
298
- let t = C.itemOf(e.target);
299
- t != null && Pe(t);
319
+ g.on(S, "vf-resize", (e) => {
320
+ if (!e.detail?.commit || w.appOf(e.target) !== "finder") return;
321
+ let t = w.itemOf(e.target);
322
+ t != null && Re(t);
300
323
  });
301
- function W(e, t) {
302
- let n = w.item(e);
303
- n && (l(n.kind) ? C.open({
304
- app: h,
305
- item: e,
324
+ function G(e, t) {
325
+ let n = T.item(e);
326
+ if (!n) return;
327
+ let r = h(T.get(), e);
328
+ if (!r) {
329
+ A("original-missing", { alias: n }, `The alias “${n.name}” could not be opened, because the original item could not be found.`);
330
+ return;
331
+ }
332
+ d(r.kind) ? w.open({
333
+ app: _,
334
+ item: r.id,
306
335
  from: t,
307
- create: () => We(e)
308
- }) : m.kind(n.kind)?.open(n, t));
336
+ create: () => Je(r.id)
337
+ }) : g.kind(r.kind)?.open(r, t);
309
338
  }
310
- m.on(b, "vf-open", (e) => {
339
+ g.on(S, "vf-open", (e) => {
311
340
  let t = e.target;
312
- t.localName === "vf-icon" && t.dataset.id != null && (t.selected && J().length > 1 ? Ye() : W(I(t), t.cellRect()));
341
+ t.localName === "vf-icon" && t.dataset.id != null && (t.selected && J().length > 1 ? et() : G(I(t), t.cellRect()));
313
342
  });
314
- let Ge = (e) => {
315
- let t = w.get().items.filter((t) => t.kind === "app" && o(t) === e);
343
+ let Ye = (e) => {
344
+ let t = T.get().items.filter((t) => t.kind === "app" && ee(t) === e);
316
345
  return t.find((e) => L(e.id)) ?? t[0] ?? null;
317
- }, Ke = (e, t) => w.item(e) ?? (t == null ? null : Ge(t));
318
- m.onDispose(C.setHome((e, t) => {
319
- let n = Ke(e, t);
346
+ }, Xe = (e, t) => T.item(e) ?? (t == null ? null : Ye(t));
347
+ g.onDispose(w.setHome((e, t) => {
348
+ let n = Xe(e, t);
320
349
  if (!n) return null;
321
350
  let r = L(n.id)?.cellRect();
322
351
  if (r) return r;
323
- for (let e of c(w.get(), n.parent)) {
352
+ for (let e of re(T.get(), n.parent)) {
324
353
  let t = L(e)?.cellRect();
325
354
  if (t) return t;
326
355
  }
327
356
  return null;
328
357
  }, (e, t) => {
329
- let n = e == null && t == null ? null : Ke(e, t), r = P(j), i = n ? L(n.id) : r.find((e) => e.selected) ?? r[0] ?? null;
358
+ let n = e == null && t == null ? null : Xe(e, t), r = P(N), i = n ? L(n.id) : r.find((e) => e.selected) ?? r[0] ?? null;
330
359
  return i?.checkVisibility() ? (i.focus({ preventScroll: !0 }), !0) : !1;
331
- })), m.on(j, "pointerdown", () => b.clearActive());
332
- let G = (e) => {
360
+ })), g.on(N, "pointerdown", () => S.clearActive());
361
+ let K = (e) => {
333
362
  let t = e.target;
334
363
  return t.localName === "vf-icon" && t.dataset.id != null;
335
364
  };
336
- m.on(b, "vf-change", (e) => {
337
- if (!G(e)) return;
365
+ g.on(S, "vf-change", (e) => {
366
+ if (!K(e)) return;
338
367
  let t = e.target, { label: n, previous: r } = e.detail;
339
- w.rename(I(t), n).catch(() => {
368
+ T.rename(I(t), n).catch(() => {
340
369
  t.label = r;
341
370
  });
342
371
  });
343
- let K = !1;
344
- m.on(b, "vf-name-too-long", (e) => {
345
- if (!G(e) || K) return;
346
- K = !0;
372
+ let Ze = !1;
373
+ g.on(S, "vf-name-too-long", (e) => {
374
+ if (!K(e) || Ze) return;
375
+ Ze = !0;
347
376
  let { limit: t } = e.detail;
348
- O("name-too-long", { limit: t }, `That name is too long. A name can have up to ${t} characters.`).finally(() => {
349
- K = !1;
377
+ A("name-too-long", { limit: t }, `That name is too long. A name can have up to ${t} characters.`).finally(() => {
378
+ Ze = !1;
350
379
  });
351
- }), m.on(b, "vf-name-rejected", (e) => {
352
- G(e) && O("name-rejected", {}, "An item needs a name.");
353
- }), m.onDispose(fe(b, {
354
- folderOfWindow: (e) => C.appOf(e) === "finder" ? C.itemOf(e) ?? void 0 : void 0,
380
+ }), g.on(S, "vf-name-rejected", (e) => {
381
+ K(e) && A("name-rejected", {}, "An item needs a name.");
382
+ }), g.onDispose(ve(S, {
383
+ folderOfWindow: (e) => w.appOf(e) === "finder" ? w.itemOf(e) ?? void 0 : void 0,
355
384
  folderOfIcon: (e) => e.dataset.folder,
356
- containerOf: (e) => e.dataset.id == null ? void 0 : je(e),
385
+ containerOf: (e) => e.dataset.id == null ? void 0 : Ie(e),
357
386
  canFile: (e, t) => {
358
- let n = w.get();
387
+ let n = T.get();
359
388
  return e.every((e) => {
360
389
  let r = e.dataset.id;
361
- return r == null || f(r) ? !1 : t == null || e.dataset.folder == null || r !== t && !u(n, t, r);
390
+ return r == null || f(r) ? !1 : t == null || e.dataset.folder == null || r !== t && !ie(n, t, r);
362
391
  });
363
392
  },
364
393
  file: (e, t, n) => {
365
394
  let r = new Map([...n].map(([e, t]) => [I(e), t]));
366
- w.move(e.map(I), t, r).catch((e) => {
367
- O("move-failed", { error: e }, `The items couldn’t be moved: ${e.message}.`);
395
+ T.move(e.map(I), t, r).catch((e) => {
396
+ A("move-failed", { error: e }, `The items couldn’t be moved: ${e.message}.`);
368
397
  });
369
398
  }
370
399
  }));
371
- let qe = /* @__PURE__ */ new WeakMap(), q = 0;
372
- m.onDispose(C.onRaster((t, n) => {
373
- j.dragIcons([]);
400
+ let Qe = /* @__PURE__ */ new WeakMap(), q = 0;
401
+ g.onDispose(w.onRaster((t, n) => {
402
+ N.dragIcons([]);
374
403
  let r = {
375
- width: E,
376
- height: E
377
- }, a = oe(b.workArea.top);
378
- for (let i of P(j)) {
404
+ width: D,
405
+ height: D
406
+ }, i = de(S.workArea.top);
407
+ for (let a of P(N)) {
379
408
  let o = {
380
- ...R(i),
409
+ ...R(a),
381
410
  ...r
382
- }, s = qe.get(i), c = !s || s.left !== o.left || s.top !== o.top ? ce(o, t, a) : s.pin, l = le(c, n, a, { size: r });
383
- i.left = e(l.left, i), i.top = e(l.top, i), qe.set(i, {
411
+ }, s = Qe.get(a), c = !s || s.left !== o.left || s.top !== o.top ? me(o, t, i) : s.pin, l = he(c, n, i, { size: r });
412
+ a.left = e(l.left, a), a.top = e(l.top, a), Qe.set(a, {
384
413
  pin: c,
385
- left: i.left,
386
- top: i.top
414
+ left: a.left,
415
+ top: a.top
387
416
  });
388
417
  }
389
- i.cleanUpAfterResize && (window.clearTimeout(q), q = window.setTimeout(() => {
390
- q = 0, te(P(j).map((e) => ({
418
+ a.cleanUpAfterResize && (window.clearTimeout(q), q = window.setTimeout(() => {
419
+ q = 0, oe(P(N).map((e) => ({
391
420
  ...R(e),
392
421
  ...r
393
- }))).size && Je(null);
394
- }, he));
395
- })), m.onDispose(() => window.clearTimeout(q));
422
+ }))).size && $e(null);
423
+ }, xe));
424
+ })), g.onDispose(() => window.clearTimeout(q));
396
425
  let J = () => {
397
426
  let e = new Set(F().filter((e) => e.selected).map(I));
398
- return w.get().items.filter((t) => e.has(t.id));
427
+ return T.get().items.filter((t) => e.has(t.id));
399
428
  }, Y = (e) => {
400
429
  let t = new Set(e);
401
430
  for (let e of F()) e.setSelected(t.has(I(e)));
402
431
  }, X = () => {
403
- let e = b.activeWindow;
404
- return e && C.appOf(e) === "finder" ? C.itemOf(e) : null;
432
+ let e = S.activeWindow;
433
+ return e && w.appOf(e) === "finder" ? w.itemOf(e) : null;
405
434
  };
406
- async function Je(e) {
407
- let t = Ae(e);
435
+ async function $e(e) {
436
+ let t = Fe(e);
408
437
  if (!t) return;
409
- let n = Ne(e), r = P(t), i = ee(n, r.map(R)), a = r.map((e, t) => ({
438
+ let n = z(e), r = P(t), i = ae(n, r.map(R)), a = r.map((e, t) => ({
410
439
  icon: e,
411
440
  ...i[t]
412
- })).sort((e, t) => ie(n, e, t));
441
+ })).sort((e, t) => le(n, e, t));
413
442
  await t.dragIcons(a);
414
443
  }
415
- async function Ye() {
416
- let e = n() ? 0 : me;
417
- for (let [t, n] of J().entries()) t && e && await new Promise((t) => setTimeout(t, e)), W(n.id, L(n.id)?.cellRect() ?? null);
444
+ async function et() {
445
+ let e = n() ? 0 : be;
446
+ for (let [t, n] of J().entries()) t && e && await new Promise((t) => setTimeout(t, e)), G(n.id, L(n.id)?.cellRect() ?? null);
418
447
  }
419
- async function Xe(e) {
448
+ async function tt(e) {
420
449
  let t = L(e);
421
450
  t && (Y([e]), await t.updateComplete, t.startEditing());
422
451
  }
423
- let Z = () => w.get().available ? !0 : (O("storage-unavailable", {}, "Files can’t be saved in this browser session. A private window, perhaps.", { label: "Storage Unavailable" }), !1);
424
- async function Ze() {
452
+ let Z = () => T.get().available ? !0 : (A("storage-unavailable", {}, "Files can’t be saved in this browser session. A private window, perhaps.", { label: "Storage Unavailable" }), !1);
453
+ async function nt() {
454
+ if (!Z()) return;
455
+ let e = await T.create({ parent: X() }).catch(j("new-folder"));
456
+ e && await tt(e.id);
457
+ }
458
+ let rt = (e) => {
459
+ let t = T.get(), n = h(t, e.id);
460
+ return !!n && !d(n.kind) && !p(t, e.id);
461
+ };
462
+ async function it() {
425
463
  if (!Z()) return;
426
- let e = await w.create({ parent: X() }).catch(k("new-folder"));
427
- e && await Xe(e.id);
464
+ let e = /* @__PURE__ */ new Map(), t = [];
465
+ try {
466
+ for (let n of J().filter(rt)) {
467
+ let r = T.get(), a = ne(r, n.parent), o = L(n.id), s = Fe(a), c;
468
+ if (o && s) {
469
+ let t = e.get(a) ?? P(s).map(R);
470
+ c = fe(z(a), R(o), t, a == null ? D : O), e.set(a, [...t, c]);
471
+ }
472
+ let l = await T.create({
473
+ kind: i,
474
+ name: u(r, a, n.name),
475
+ parent: a,
476
+ data: { original: h(r, n.id).id },
477
+ ...c
478
+ });
479
+ l && t.push(l.id);
480
+ }
481
+ } catch (e) {
482
+ j("make-alias")(e);
483
+ }
484
+ t.length && Y(t);
428
485
  }
429
- async function Qe() {
430
- let e = p(w.get(), a);
431
- if (!x || !e) return;
432
- let t = w.trashSize(), n = Math.ceil(t / 1024), r = e === 1 ? `The Trash contains 1 item, which uses ${n}K of disk space. Are you sure you want to permanently remove it?` : `The Trash contains ${e} items, which use ${n}K of disk space. Are you sure you want to permanently remove these items?`;
433
- await O("empty-trash", {
486
+ async function at() {
487
+ let e = m(T.get(), l);
488
+ if (!o || !e) return;
489
+ let t = T.trashSize(), n = Math.ceil(t / 1024), r = e === 1 ? `The Trash contains 1 item, which uses ${n}K of disk space. Are you sure you want to permanently remove it?` : `The Trash contains ${e} items, which use ${n}K of disk space. Are you sure you want to permanently remove these items?`;
490
+ await A("empty-trash", {
434
491
  count: e,
435
492
  bytes: t
436
493
  }, r, {
@@ -443,13 +500,13 @@ function x(i) {
443
500
  value: "ok",
444
501
  default: !0
445
502
  }]
446
- }) === "ok" && await w.emptyTrash().catch(k("empty-trash"));
503
+ }) === "ok" && await T.emptyTrash().catch(j("empty-trash"));
447
504
  }
448
505
  let Q = {
449
506
  ids: [],
450
507
  text: ""
451
- }, $e = (e) => e.replace(/\r\n?/g, "\n").trimEnd();
452
- async function et() {
508
+ }, ot = (e) => e.replace(/\r\n?/g, "\n").trimEnd();
509
+ async function st() {
453
510
  let e = J().filter((e) => !f(e.id));
454
511
  if (!e.length) return;
455
512
  let t = e.map((e) => e.name).join("\n");
@@ -457,9 +514,9 @@ function x(i) {
457
514
  ids: e.map((e) => e.id),
458
515
  text: t
459
516
  };
460
- let n = e.find((e) => m.kind(e.kind)?.export);
517
+ let n = e.find((e) => g.kind(e.kind)?.export);
461
518
  try {
462
- let e = n ? await m.kind(n.kind).export(n) : null;
519
+ let e = n ? await g.kind(n.kind).export(n) : null;
463
520
  if (e?.type && e.type !== "text/plain" && typeof ClipboardItem < "u") {
464
521
  await navigator.clipboard.write([new ClipboardItem({
465
522
  "text/plain": new Blob([t], { type: "text/plain" }),
@@ -472,12 +529,12 @@ function x(i) {
472
529
  await navigator.clipboard?.writeText(t);
473
530
  } catch {}
474
531
  }
475
- async function tt(e, t) {
476
- for (let n of m.kinds.values()) if (n.claim && await n.claim(e, t)) return !0;
532
+ async function ct(e, t) {
533
+ for (let n of g.kinds.values()) if (n.claim && await n.claim(e, t)) return !0;
477
534
  return !1;
478
535
  }
479
- let nt = () => [...m.kinds.values()].some((e) => e.claim);
480
- async function rt() {
536
+ let lt = () => [...g.kinds.values()].some((e) => e.claim);
537
+ async function ut() {
481
538
  try {
482
539
  if (navigator.clipboard?.read) {
483
540
  let e = null, t = [];
@@ -497,108 +554,109 @@ function x(i) {
497
554
  } catch {}
498
555
  return null;
499
556
  }
500
- async function it(e) {
557
+ async function dt(e) {
501
558
  if (!Z()) return;
502
559
  let t = X();
503
- if (d(w.get(), t)) return;
504
- let n = e === void 0 ? await rt() : e, r = Q.ids.length > 0 && (n == null || n.text != null && $e(n.text) === $e(Q.text));
560
+ if (p(T.get(), t)) return;
561
+ let n = e === void 0 ? await ut() : e, r = Q.ids.length > 0 && (n == null || n.text != null && ot(n.text) === ot(Q.text));
505
562
  try {
506
563
  if (r) {
507
- let e = await w.copy(Q.ids, t);
564
+ let e = await T.copy(Q.ids, t);
508
565
  e.length && Y(e.map((e) => e.id));
509
- } else for (let e of n?.files ?? []) await tt(e, t);
566
+ } else for (let e of n?.files ?? []) await ct(e, t);
510
567
  } catch (e) {
511
- k("paste")(e);
568
+ j("paste")(e);
512
569
  }
513
570
  }
514
- m.on(document, "paste", (e) => {
515
- if (!S("paste") || C.front !== "finder" || m.modalOpen() || m.typing()) return;
571
+ g.on(document, "paste", (e) => {
572
+ if (!s("paste") || w.front !== "finder" || g.modalOpen() || g.typing()) return;
516
573
  let t = e.clipboardData;
517
- t && (e.preventDefault(), it({
574
+ t && (e.preventDefault(), dt({
518
575
  text: t.getData("text/plain") || null,
519
576
  files: [...t.files]
520
577
  }));
521
578
  });
522
- let at = (e) => [...e.dataTransfer?.types ?? []].includes("Files");
523
- m.on(b, "dragover", (e) => {
524
- at(e) && nt() && e.preventDefault();
525
- }), m.on(b, "drop", (e) => {
526
- if (!at(e) || !nt()) return;
579
+ let ft = (e) => [...e.dataTransfer?.types ?? []].includes("Files");
580
+ g.on(S, "dragover", (e) => {
581
+ ft(e) && lt() && e.preventDefault();
582
+ }), g.on(S, "drop", (e) => {
583
+ if (!ft(e) || !lt()) return;
527
584
  e.preventDefault();
528
585
  let t = e, n = [...t.dataTransfer?.files ?? []], r = document.elementsFromPoint(t.clientX, t.clientY).find((e) => e.localName === "vf-window");
529
- if (r && C.appOf(r) !== "finder" || (r ? b.bringToFront(r) : b.clearActive(), !Z())) return;
530
- let i = r ? C.itemOf(r) : null;
531
- d(w.get(), i) || (async () => {
532
- for (let e of n) await tt(e, i);
533
- })().catch(k("add-file"));
586
+ if (r && w.appOf(r) !== "finder" || (r ? S.bringToFront(r) : S.clearActive(), !Z())) return;
587
+ let i = r ? w.itemOf(r) : null;
588
+ p(T.get(), i) || (async () => {
589
+ for (let e of n) await ct(e, i);
590
+ })().catch(j("add-file"));
534
591
  });
535
- let ot = {
536
- open: () => void Ye(),
537
- "new-folder": () => void Ze(),
592
+ let pt = {
593
+ open: () => void et(),
594
+ "new-folder": () => void nt(),
538
595
  close: () => {
539
- let e = X(), t = e == null ? null : C.windowFor(e);
540
- t && C.requestClose(t);
596
+ let e = X(), t = e == null ? null : w.windowFor(e);
597
+ t && w.requestClose(t);
541
598
  },
542
- copy: () => void et(),
543
- paste: () => void it(),
599
+ "make-alias": () => void it(),
600
+ copy: () => void st(),
601
+ paste: () => void dt(),
544
602
  "select-all": () => {
545
- let e = Ae(X());
603
+ let e = Fe(X());
546
604
  e && Y(P(e).map(I));
547
605
  },
548
- arrange: () => C.arrange(),
549
- "clean-up": () => void Je(X()),
550
- "empty-trash": () => void Qe()
606
+ arrange: () => w.arrange(),
607
+ "clean-up": () => void $e(X()),
608
+ "empty-trash": () => void at()
551
609
  }, $ = (e, t) => {
552
- S(e) && m.gate(m.item(e), t);
610
+ s(e) && g.gate(g.item(e), t);
553
611
  };
554
- if ($("open", () => !m.typing() && J().length > 0), $("new-folder", () => !d(w.get(), X())), $("close", () => X() != null), $("copy", () => !m.typing() && J().some((e) => !f(e.id))), $("paste", () => !m.typing() && !d(w.get(), X())), $("select-all", () => !m.typing()), $("arrange", () => !C.arranged()), $("empty-trash", () => p(w.get(), a) > 0), S("clean-up")) {
555
- let e = m.item("clean-up");
556
- m.gate(e, () => {
612
+ if ($("open", () => !g.typing() && J().length > 0), $("new-folder", () => !p(T.get(), X())), $("close", () => X() != null), $("make-alias", () => !g.typing() && J().some(rt)), $("copy", () => !g.typing() && J().some((e) => !f(e.id))), $("paste", () => !g.typing() && !p(T.get(), X())), $("select-all", () => !g.typing()), $("arrange", () => !w.arranged()), $("empty-trash", () => m(T.get(), l) > 0), s("clean-up")) {
613
+ let e = g.item("clean-up");
614
+ g.gate(e, () => {
557
615
  let t = X() == null ? "Clean Up Desktop" : "Clean Up Window";
558
616
  return e.textContent !== t && (e.textContent = t), !0;
559
617
  });
560
618
  }
561
- let st = !0, ct = (e) => {
562
- let t = m.menus.find((t) => t.dataset.menu === e);
619
+ let mt = !0, ht = (e) => {
620
+ let t = g.menus.find((t) => t.dataset.menu === e);
563
621
  if (t) return t;
564
- if (!st) throw Error(`vintage-frames/shell (finder): no ${e} menu; add to it from extend`);
622
+ if (!mt) throw Error(`vintage-frames/shell (finder): no ${e} menu; add to it from extend`);
565
623
  let n = document.createElement("vf-menu");
566
- n.dataset.menu = e, n.label = y.find((t) => t.menu === e).label;
567
- let r = y.map((e) => e.menu), i = m.menus.findIndex((t) => r.indexOf(t.dataset.menu) > r.indexOf(e));
568
- return m.menus.splice(i < 0 ? m.menus.length : i, 0, n), n;
569
- }, lt = {
570
- catalog: w,
624
+ n.dataset.menu = e, n.label = x.find((t) => t.menu === e).label;
625
+ let r = x.map((e) => e.menu), i = g.menus.findIndex((t) => r.indexOf(t.dataset.menu) > r.indexOf(e));
626
+ return g.menus.splice(i < 0 ? g.menus.length : i, 0, n), n;
627
+ }, gt = {
628
+ catalog: T,
571
629
  selection: J,
572
630
  select: Y,
573
631
  activeFolder: X,
574
632
  open: ({ item: e, from: t = null } = {}) => {
575
- e != null && W(e, t);
633
+ e != null && G(e, t);
576
634
  },
577
- rename: Xe,
578
- cleanUp: Je,
635
+ rename: tt,
636
+ cleanUp: $e,
579
637
  iconFor: L,
580
638
  addCommand(e) {
581
- let t = ct(e.menu);
639
+ let t = ht(e.menu);
582
640
  e.separator && t.append(document.createElement("vf-separator"));
583
641
  let n = document.createElement("vf-menu-item");
584
- return n.setAttribute("value", e.value), e.shortcut && n.setAttribute("shortcut", e.shortcut), n.textContent = e.label, t.append(n), ot[e.value] = e.run, e.enabled && m.gate(n, e.enabled), n;
642
+ return n.setAttribute("value", e.value), e.shortcut && n.setAttribute("shortcut", e.shortcut), n.textContent = e.label, t.append(n), pt[e.value] = e.run, e.enabled && g.gate(n, e.enabled), n;
585
643
  },
586
644
  alertWith(e, t) {
587
- Ee.set(e, t);
645
+ ke.set(e, t);
588
646
  },
589
647
  storageReady: Z
590
648
  };
591
- i.extend?.(lt, m), st = !1, m.onMenu((e) => ot[e]?.());
592
- let ut = !1;
593
- return m.onDispose(() => {
594
- ut = !0;
595
- for (let e of P(j)) e.remove();
596
- De ? j.remove() : j.append(...Oe);
597
- }), de(b).then(() => {
598
- ut || (Be = !0, H());
599
- }), lt;
649
+ a.extend?.(gt, g), mt = !1, g.onMenu((e) => pt[e]?.());
650
+ let _t = !1;
651
+ return g.onDispose(() => {
652
+ _t = !0;
653
+ for (let e of P(N)) e.remove();
654
+ Ae ? N.remove() : N.append(...je);
655
+ }), _e(S).then(() => {
656
+ _t || (We = !0, U());
657
+ }), gt;
600
658
  }
601
659
  });
602
660
  }
603
661
  //#endregion
604
- export { h as FINDER, x as finder };
662
+ export { _ as FINDER, T as finder };