vitepress-plugin-filelist 0.5.1 → 0.6.1
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/README.md +20 -2
- package/dist/client/browser/index.d.ts +41 -0
- package/dist/client/browser/index.js +553 -169
- package/dist/client/ssr/index.d.ts +41 -0
- package/dist/client/ssr/index.js +393 -100
- package/dist/client/style.css +153 -0
- package/package.json +2 -2
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import "../style.css";
|
|
2
|
-
import { Fragment, computed, createCommentVNode, createElementBlock, createElementVNode, createTextVNode, createVNode, defineComponent, nextTick, normalizeClass, normalizeStyle, onBeforeUnmount, onMounted, openBlock, ref, renderList, toDisplayString, unref, useId, vModelSelect, vModelText, watch, withDirectives, withKeys, withModifiers } from "vue";
|
|
2
|
+
import { Fragment, computed, createCommentVNode, createElementBlock, createElementVNode, createTextVNode, createVNode, defineComponent, nextTick, normalizeClass, normalizeStyle, onBeforeUnmount, onMounted, openBlock, reactive, ref, renderList, toDisplayString, unref, useId, vModelSelect, vModelText, watch, withDirectives, withKeys, withModifiers } from "vue";
|
|
3
3
|
// src/client/utils.ts
|
|
4
4
|
function joinPath(parent, name) {
|
|
5
5
|
return (parent.endsWith("/") ? parent : `${parent}/`) + name;
|
|
@@ -329,6 +329,7 @@ function createOpenListApi(base, token) {
|
|
|
329
329
|
return url;
|
|
330
330
|
},
|
|
331
331
|
directUrl,
|
|
332
|
+
isAttachmentUrl: (url) => !!root && (url.startsWith(`${root}/p/`) || url.startsWith(`${root}/d/`)),
|
|
332
333
|
clearCache(path) {
|
|
333
334
|
if (!path) urls.clear();
|
|
334
335
|
else for (const key of [...urls.keys()]) if (isWithin(key, path)) urls.delete(key);
|
|
@@ -517,16 +518,99 @@ function createDemoApi(delay = 220) {
|
|
|
517
518
|
}),
|
|
518
519
|
fileUrl: async () => "",
|
|
519
520
|
directUrl: () => "",
|
|
521
|
+
isAttachmentUrl: () => false,
|
|
520
522
|
clearCache: () => {}
|
|
521
523
|
};
|
|
522
524
|
}
|
|
525
|
+
// src/client/ConfirmDialog.vue
|
|
526
|
+
const _hoisted_1$3 = ["aria-label"];
|
|
527
|
+
const _hoisted_2$3 = {
|
|
528
|
+
key: 0,
|
|
529
|
+
class: "fl-confirm-panel"
|
|
530
|
+
};
|
|
531
|
+
const _hoisted_3$2 = { class: "fl-confirm-title" };
|
|
532
|
+
const _hoisted_4$2 = { class: "fl-confirm-text" };
|
|
533
|
+
const _hoisted_5$2 = {
|
|
534
|
+
key: 0,
|
|
535
|
+
class: "fl-confirm-text"
|
|
536
|
+
};
|
|
537
|
+
const _hoisted_6$2 = { class: "fl-confirm-actions" };
|
|
538
|
+
const _sfc_main$3 = /*@__PURE__*/ defineComponent({
|
|
539
|
+
__name: "ConfirmDialog",
|
|
540
|
+
props: {
|
|
541
|
+
open: { type: Boolean },
|
|
542
|
+
title: {},
|
|
543
|
+
text: {},
|
|
544
|
+
tip: {},
|
|
545
|
+
confirmLabel: {},
|
|
546
|
+
cancelLabel: {}
|
|
547
|
+
},
|
|
548
|
+
emits: ["confirm", "close"],
|
|
549
|
+
setup(__props, { emit: __emit }) {
|
|
550
|
+
/** Small native <dialog> for a yes / no question or a notice (bottom sheet on phones). */
|
|
551
|
+
const props = __props;
|
|
552
|
+
const emit = __emit;
|
|
553
|
+
const dialog = ref();
|
|
554
|
+
watch(() => props.open, (open) => {
|
|
555
|
+
const el = dialog.value;
|
|
556
|
+
if (!el) return;
|
|
557
|
+
if (open && !el.open) {
|
|
558
|
+
if (typeof el.showModal === "function") el.showModal();
|
|
559
|
+
else el.setAttribute("open", "");
|
|
560
|
+
} else if (!open && el.open) {
|
|
561
|
+
if (typeof el.close === "function") el.close();
|
|
562
|
+
else el.removeAttribute("open");
|
|
563
|
+
}
|
|
564
|
+
}, { flush: "post" });
|
|
565
|
+
function onNativeClose() {
|
|
566
|
+
if (props.open) emit("close");
|
|
567
|
+
}
|
|
568
|
+
function onBackdrop(event) {
|
|
569
|
+
if (event.target === dialog.value) emit("close");
|
|
570
|
+
}
|
|
571
|
+
return (_ctx, _cache) => {
|
|
572
|
+
return openBlock(), createElementBlock("dialog", {
|
|
573
|
+
ref_key: "dialog",
|
|
574
|
+
ref: dialog,
|
|
575
|
+
class: "fl-confirm",
|
|
576
|
+
"aria-label": __props.title,
|
|
577
|
+
onClose: onNativeClose,
|
|
578
|
+
onClick: onBackdrop
|
|
579
|
+
}, [__props.open ? (openBlock(), createElementBlock("div", _hoisted_2$3, [
|
|
580
|
+
createElementVNode("p", _hoisted_3$2, toDisplayString(__props.title), 1),
|
|
581
|
+
createElementVNode("p", _hoisted_4$2, toDisplayString(__props.text), 1),
|
|
582
|
+
__props.tip ? (openBlock(), createElementBlock("p", _hoisted_5$2, toDisplayString(__props.tip), 1)) : createCommentVNode("v-if", true),
|
|
583
|
+
createElementVNode("div", _hoisted_6$2, [__props.confirmLabel ? (openBlock(), createElementBlock("button", {
|
|
584
|
+
key: 0,
|
|
585
|
+
class: "fl-btn",
|
|
586
|
+
type: "button",
|
|
587
|
+
onClick: _cache[0] || (_cache[0] = ($event) => emit("close"))
|
|
588
|
+
}, toDisplayString(__props.cancelLabel), 1)) : createCommentVNode("v-if", true), createElementVNode("button", {
|
|
589
|
+
class: "fl-btn fl-btn-primary",
|
|
590
|
+
type: "button",
|
|
591
|
+
autofocus: "",
|
|
592
|
+
onClick: _cache[1] || (_cache[1] = ($event) => __props.confirmLabel ? emit("confirm") : emit("close"))
|
|
593
|
+
}, toDisplayString(__props.confirmLabel || __props.cancelLabel), 1)])
|
|
594
|
+
])) : createCommentVNode("v-if", true)], 40, _hoisted_1$3);
|
|
595
|
+
};
|
|
596
|
+
}
|
|
597
|
+
});
|
|
523
598
|
// src/client/download.ts
|
|
524
|
-
/**
|
|
525
|
-
|
|
599
|
+
/**
|
|
600
|
+
* Hand a file URL to the browser's own download manager.
|
|
601
|
+
*
|
|
602
|
+
* `sameTab` is for links known to answer as attachments (OpenList `/p/`, `/d/`):
|
|
603
|
+
* the browser downloads and the page stays put, with no tab flashing open.
|
|
604
|
+
* Other links (a storage provider's direct URL may display inline) open in a
|
|
605
|
+
* new tab so the document page is never replaced. `download` also keeps a
|
|
606
|
+
* same-origin link out of the VitePress router and names the file.
|
|
607
|
+
*/
|
|
608
|
+
function openUrl(url, options) {
|
|
526
609
|
const anchor = document.createElement("a");
|
|
527
610
|
anchor.href = url;
|
|
528
|
-
anchor.
|
|
611
|
+
anchor.download = options.name;
|
|
529
612
|
anchor.rel = "noopener";
|
|
613
|
+
if (!options.sameTab) anchor.target = "_blank";
|
|
530
614
|
document.body.appendChild(anchor);
|
|
531
615
|
anchor.click();
|
|
532
616
|
anchor.remove();
|
|
@@ -545,32 +629,113 @@ function saveBlob(blob, name) {
|
|
|
545
629
|
function zipFileName(title) {
|
|
546
630
|
return `${title.replace(/[\\/:*?"<>|]/g, "_")}.zip`;
|
|
547
631
|
}
|
|
632
|
+
/** Whether the browser can write a ZIP straight into a file the user picks (Chromium). */
|
|
633
|
+
function canStreamToDisk() {
|
|
634
|
+
return typeof window !== "undefined" && window.isSecureContext && "showSaveFilePicker" in window;
|
|
635
|
+
}
|
|
548
636
|
/**
|
|
549
|
-
*
|
|
550
|
-
*
|
|
551
|
-
* fetching; packing is the rest.
|
|
637
|
+
* Ask where to save the ZIP. Call it straight from the click, before any other
|
|
638
|
+
* `await`, or the browser refuses. Resolves `null` when the user cancels.
|
|
552
639
|
*/
|
|
553
|
-
async function
|
|
554
|
-
|
|
555
|
-
|
|
556
|
-
|
|
557
|
-
|
|
558
|
-
|
|
559
|
-
|
|
560
|
-
|
|
561
|
-
|
|
562
|
-
|
|
563
|
-
|
|
564
|
-
|
|
565
|
-
|
|
640
|
+
async function pickZipFile(name) {
|
|
641
|
+
try {
|
|
642
|
+
return await window.showSaveFilePicker({
|
|
643
|
+
suggestedName: name,
|
|
644
|
+
types: [{
|
|
645
|
+
description: "ZIP",
|
|
646
|
+
accept: { "application/zip": [".zip"] }
|
|
647
|
+
}]
|
|
648
|
+
});
|
|
649
|
+
} catch (error) {
|
|
650
|
+
if (error instanceof DOMException && error.name === "AbortError") return null;
|
|
651
|
+
throw error;
|
|
652
|
+
}
|
|
653
|
+
}
|
|
654
|
+
/**
|
|
655
|
+
* The ZIP as a stream: files are fetched a few at a time and passed through
|
|
656
|
+
* as they arrive, stored without compression (most shared files are already
|
|
657
|
+
* compressed). Clashing entry names get ` (2)`, ` (3)`...
|
|
658
|
+
*/
|
|
659
|
+
/** Files fetched at once: hides per-file latency, stays under the browser's 6 per host. */
|
|
660
|
+
const CONCURRENCY = 4;
|
|
661
|
+
/** Progress updates at most this often (ms), so the bar does not re-render per chunk. */
|
|
662
|
+
const PROGRESS_INTERVAL = 100;
|
|
663
|
+
async function zipStream(files, options) {
|
|
664
|
+
const { makeZip } = await import("client-zip");
|
|
665
|
+
const progress = {
|
|
666
|
+
bytes: 0,
|
|
667
|
+
totalBytes: files.reduce((sum, file) => sum + (Number.isFinite(file.size) ? file.size : 0), 0),
|
|
668
|
+
files: 0,
|
|
669
|
+
totalFiles: files.length
|
|
566
670
|
};
|
|
567
|
-
|
|
568
|
-
const
|
|
569
|
-
|
|
570
|
-
|
|
571
|
-
|
|
572
|
-
|
|
573
|
-
|
|
671
|
+
let reportedAt = 0;
|
|
672
|
+
const report = (force = false) => {
|
|
673
|
+
const now = Date.now();
|
|
674
|
+
if (!force && now - reportedAt < PROGRESS_INTERVAL) return;
|
|
675
|
+
reportedAt = now;
|
|
676
|
+
options.onProgress({ ...progress });
|
|
677
|
+
};
|
|
678
|
+
report(true);
|
|
679
|
+
async function* entries() {
|
|
680
|
+
const used = /* @__PURE__ */ new Set();
|
|
681
|
+
const ahead = [];
|
|
682
|
+
let started = 0;
|
|
683
|
+
const startNext = () => {
|
|
684
|
+
const file = files[started++];
|
|
685
|
+
const response = options.urlOf(file).then((url) => fetch(url, { signal: options.signal }));
|
|
686
|
+
response.catch(() => {});
|
|
687
|
+
ahead.push(response);
|
|
688
|
+
};
|
|
689
|
+
while (started < files.length && ahead.length < CONCURRENCY) startNext();
|
|
690
|
+
for (const file of files) {
|
|
691
|
+
const response = await ahead.shift();
|
|
692
|
+
if (started < files.length) startNext();
|
|
693
|
+
if (!response.ok || !response.body) throw new Error(`${file.name}:HTTP ${response.status}`);
|
|
694
|
+
const counted = response.body.pipeThrough(new TransformStream({
|
|
695
|
+
transform(chunk, controller) {
|
|
696
|
+
progress.bytes += chunk.byteLength;
|
|
697
|
+
report();
|
|
698
|
+
controller.enqueue(chunk);
|
|
699
|
+
},
|
|
700
|
+
flush() {
|
|
701
|
+
progress.files += 1;
|
|
702
|
+
report(progress.files === progress.totalFiles);
|
|
703
|
+
}
|
|
704
|
+
}));
|
|
705
|
+
const modified = new Date(file.modified);
|
|
706
|
+
yield {
|
|
707
|
+
name: uniqueEntryName(zipEntryName(file.zipPath), used),
|
|
708
|
+
lastModified: Number.isNaN(modified.getTime()) ? void 0 : modified,
|
|
709
|
+
input: counted
|
|
710
|
+
};
|
|
711
|
+
}
|
|
712
|
+
}
|
|
713
|
+
return makeZip(entries());
|
|
714
|
+
}
|
|
715
|
+
/** Stream the ZIP into a picked file; memory use stays small whatever the size. */
|
|
716
|
+
async function zipToFile(handle, files, options) {
|
|
717
|
+
const stream = await zipStream(files, options);
|
|
718
|
+
const writable = await handle.createWritable();
|
|
719
|
+
await stream.pipeTo(writable, { signal: options.signal });
|
|
720
|
+
}
|
|
721
|
+
/** Build the ZIP in memory (browsers without file streaming). */
|
|
722
|
+
async function zipToBlob(files, options) {
|
|
723
|
+
const reader = (await zipStream(files, options)).getReader();
|
|
724
|
+
const chunks = [];
|
|
725
|
+
const abort = () => void reader.cancel(options.signal.reason).catch(() => {});
|
|
726
|
+
options.signal.addEventListener("abort", abort, { once: true });
|
|
727
|
+
if (options.signal.aborted) abort();
|
|
728
|
+
try {
|
|
729
|
+
for (;;) {
|
|
730
|
+
const { done, value } = await reader.read();
|
|
731
|
+
if (done) break;
|
|
732
|
+
chunks.push(value);
|
|
733
|
+
}
|
|
734
|
+
} finally {
|
|
735
|
+
options.signal.removeEventListener("abort", abort);
|
|
736
|
+
}
|
|
737
|
+
options.signal.throwIfAborted();
|
|
738
|
+
return new Blob(chunks, { type: "application/zip" });
|
|
574
739
|
}
|
|
575
740
|
// src/client/icons.ts
|
|
576
741
|
/** Stroke icons on a 24×24 grid, drawn by `Icon.vue`. */
|
|
@@ -733,7 +898,22 @@ const fileListLocales = {
|
|
|
733
898
|
remembered: "已记住",
|
|
734
899
|
forgetPassword: "忘记",
|
|
735
900
|
unlockFolder: "输入 {name} 的密码",
|
|
736
|
-
networkHint: "可能被跨域拦截:请检查 OpenList 的 cors.allow_origins,或 OpenList-Worker 的 ALLOW_URLS。"
|
|
901
|
+
networkHint: "可能被跨域拦截:请检查 OpenList 的 cors.allow_origins,或 OpenList-Worker 的 ALLOW_URLS。",
|
|
902
|
+
downloadStarted: "已交给浏览器下载:{name}",
|
|
903
|
+
batchProgress: "{done} / {total} · {files} / {count} 个文件",
|
|
904
|
+
batchDone: "已打包 {name}({count} 个文件,{size})",
|
|
905
|
+
batchCanceled: "已取消下载",
|
|
906
|
+
zipWarnTitle: "文件较大({size})",
|
|
907
|
+
zipWarnText: "当前浏览器要先把文件全部放进内存再打包,超过 {limit} 可能失败或让页面崩溃。建议分批下载。",
|
|
908
|
+
zipStreamTip: "在 Chrome 或 Edge 中可以边下载边保存,不受大小限制。",
|
|
909
|
+
zipContinue: "仍然下载",
|
|
910
|
+
zipBlockTitle: "无法打包 {size}",
|
|
911
|
+
zipBlockText: "当前浏览器一次最多打包 {limit},请分批勾选下载。",
|
|
912
|
+
gotIt: "知道了",
|
|
913
|
+
moreRemaining: "还有 {count} 项",
|
|
914
|
+
showMore: "显示更多",
|
|
915
|
+
showAll: "全部显示",
|
|
916
|
+
showRest: "显示剩余 {count} 项"
|
|
737
917
|
},
|
|
738
918
|
"en-US": {
|
|
739
919
|
allFiles: "All files",
|
|
@@ -796,7 +976,22 @@ const fileListLocales = {
|
|
|
796
976
|
remembered: "Remembered",
|
|
797
977
|
forgetPassword: "Forget",
|
|
798
978
|
unlockFolder: "Enter the password for {name}",
|
|
799
|
-
networkHint: "Possibly blocked by CORS: check cors.allow_origins in OpenList, or ALLOW_URLS in OpenList-Worker."
|
|
979
|
+
networkHint: "Possibly blocked by CORS: check cors.allow_origins in OpenList, or ALLOW_URLS in OpenList-Worker.",
|
|
980
|
+
downloadStarted: "Downloading {name} in your browser",
|
|
981
|
+
batchProgress: "{done} / {total} · {files} / {count} files",
|
|
982
|
+
batchDone: "Saved {name} ({count} files, {size})",
|
|
983
|
+
batchCanceled: "Download cancelled",
|
|
984
|
+
zipWarnTitle: "Large download ({size})",
|
|
985
|
+
zipWarnText: "This browser has to hold every file in memory to build the ZIP. Above {limit} it may fail or crash the page. Consider downloading in smaller batches.",
|
|
986
|
+
zipStreamTip: "Chrome and Edge save while downloading, with no size limit.",
|
|
987
|
+
zipContinue: "Download anyway",
|
|
988
|
+
zipBlockTitle: "Cannot zip {size}",
|
|
989
|
+
zipBlockText: "This browser can zip at most {limit} at once. Select fewer files.",
|
|
990
|
+
gotIt: "OK",
|
|
991
|
+
moreRemaining: "{count} more",
|
|
992
|
+
showMore: "Show more",
|
|
993
|
+
showAll: "Show all",
|
|
994
|
+
showRest: "Show the remaining {count}"
|
|
800
995
|
}
|
|
801
996
|
};
|
|
802
997
|
function formatLabel(template, values = {}) {
|
|
@@ -1392,113 +1587,129 @@ const _hoisted_3 = {
|
|
|
1392
1587
|
role: "status"
|
|
1393
1588
|
};
|
|
1394
1589
|
const _hoisted_4 = { class: "fl-selection-count" };
|
|
1395
|
-
const _hoisted_5 = {
|
|
1590
|
+
const _hoisted_5 = {
|
|
1591
|
+
key: 0,
|
|
1592
|
+
class: "fl-selection-size"
|
|
1593
|
+
};
|
|
1396
1594
|
const _hoisted_6 = {
|
|
1397
1595
|
key: 1,
|
|
1596
|
+
class: "fl-selection",
|
|
1597
|
+
role: "status"
|
|
1598
|
+
};
|
|
1599
|
+
const _hoisted_7 = { class: "fl-selection-count" };
|
|
1600
|
+
const _hoisted_8 = { class: "fl-selection-size" };
|
|
1601
|
+
const _hoisted_9 = {
|
|
1602
|
+
key: 2,
|
|
1398
1603
|
class: "fl-title"
|
|
1399
1604
|
};
|
|
1400
|
-
const
|
|
1401
|
-
const
|
|
1605
|
+
const _hoisted_10 = { class: "fl-title-text" };
|
|
1606
|
+
const _hoisted_11 = {
|
|
1402
1607
|
key: 0,
|
|
1403
1608
|
class: "fl-demo-badge"
|
|
1404
1609
|
};
|
|
1405
|
-
const
|
|
1406
|
-
const
|
|
1407
|
-
const
|
|
1408
|
-
const
|
|
1409
|
-
const
|
|
1410
|
-
const
|
|
1610
|
+
const _hoisted_12 = ["aria-label", "title"];
|
|
1611
|
+
const _hoisted_13 = { class: "fl-clear-text" };
|
|
1612
|
+
const _hoisted_14 = { class: "fl-tools" };
|
|
1613
|
+
const _hoisted_15 = { class: "fl-search" };
|
|
1614
|
+
const _hoisted_16 = ["placeholder", "aria-label"];
|
|
1615
|
+
const _hoisted_17 = [
|
|
1411
1616
|
"disabled",
|
|
1412
1617
|
"aria-label",
|
|
1413
1618
|
"title"
|
|
1414
1619
|
];
|
|
1415
|
-
const
|
|
1416
|
-
const
|
|
1417
|
-
const _hoisted_17 = {
|
|
1620
|
+
const _hoisted_18 = { class: "fl-row fl-head" };
|
|
1621
|
+
const _hoisted_19 = {
|
|
1418
1622
|
key: 0,
|
|
1419
1623
|
class: "fl-progress",
|
|
1420
1624
|
"aria-hidden": "true"
|
|
1421
1625
|
};
|
|
1422
|
-
const
|
|
1423
|
-
const
|
|
1626
|
+
const _hoisted_20 = { class: "fl-cell fl-cell-check" };
|
|
1627
|
+
const _hoisted_21 = [
|
|
1424
1628
|
"aria-label",
|
|
1629
|
+
"disabled",
|
|
1425
1630
|
"checked",
|
|
1426
1631
|
".indeterminate"
|
|
1427
1632
|
];
|
|
1428
|
-
const
|
|
1429
|
-
const
|
|
1633
|
+
const _hoisted_22 = ["aria-sort", "onClick"];
|
|
1634
|
+
const _hoisted_23 = {
|
|
1430
1635
|
class: "fl-sort",
|
|
1431
1636
|
"aria-hidden": "true"
|
|
1432
1637
|
};
|
|
1433
|
-
const
|
|
1434
|
-
const
|
|
1435
|
-
const
|
|
1638
|
+
const _hoisted_24 = { class: "fl-cell fl-cell-op" };
|
|
1639
|
+
const _hoisted_25 = { class: "fl-sort-select" };
|
|
1640
|
+
const _hoisted_26 = {
|
|
1436
1641
|
class: "fl-sort-current",
|
|
1437
1642
|
"aria-hidden": "true"
|
|
1438
1643
|
};
|
|
1439
|
-
const
|
|
1440
|
-
const
|
|
1441
|
-
const
|
|
1644
|
+
const _hoisted_27 = ["aria-label"];
|
|
1645
|
+
const _hoisted_28 = ["value"];
|
|
1646
|
+
const _hoisted_29 = {
|
|
1442
1647
|
key: 0,
|
|
1443
1648
|
class: "fl-status"
|
|
1444
1649
|
};
|
|
1445
|
-
const
|
|
1446
|
-
const
|
|
1447
|
-
const
|
|
1448
|
-
const
|
|
1650
|
+
const _hoisted_30 = ["for"];
|
|
1651
|
+
const _hoisted_31 = ["id"];
|
|
1652
|
+
const _hoisted_32 = { class: "fl-unlock" };
|
|
1653
|
+
const _hoisted_33 = [
|
|
1449
1654
|
"id",
|
|
1450
1655
|
"data-unlock",
|
|
1451
1656
|
"placeholder",
|
|
1452
1657
|
"aria-invalid",
|
|
1453
1658
|
"aria-describedby"
|
|
1454
1659
|
];
|
|
1455
|
-
const
|
|
1660
|
+
const _hoisted_34 = [
|
|
1456
1661
|
"aria-pressed",
|
|
1457
1662
|
"aria-label",
|
|
1458
1663
|
"title"
|
|
1459
1664
|
];
|
|
1460
|
-
const
|
|
1461
|
-
const
|
|
1665
|
+
const _hoisted_35 = ["disabled"];
|
|
1666
|
+
const _hoisted_36 = {
|
|
1462
1667
|
key: 2,
|
|
1463
1668
|
class: "fl-status fl-error"
|
|
1464
1669
|
};
|
|
1465
|
-
const
|
|
1670
|
+
const _hoisted_37 = {
|
|
1466
1671
|
key: 0,
|
|
1467
1672
|
class: "fl-hint"
|
|
1468
1673
|
};
|
|
1469
|
-
const
|
|
1674
|
+
const _hoisted_38 = {
|
|
1470
1675
|
key: 1,
|
|
1471
1676
|
class: "fl-hint"
|
|
1472
1677
|
};
|
|
1473
|
-
const
|
|
1678
|
+
const _hoisted_39 = {
|
|
1474
1679
|
key: 3,
|
|
1475
1680
|
class: "fl-status"
|
|
1476
1681
|
};
|
|
1477
|
-
const
|
|
1478
|
-
const
|
|
1682
|
+
const _hoisted_40 = { class: "fl-cell fl-more-cell" };
|
|
1683
|
+
const _hoisted_41 = { class: "fl-more-count" };
|
|
1684
|
+
const _hoisted_42 = ["onClick"];
|
|
1685
|
+
const _hoisted_43 = { class: "fl-more-page" };
|
|
1686
|
+
const _hoisted_44 = ["onClick"];
|
|
1687
|
+
const _hoisted_45 = ["onClick"];
|
|
1688
|
+
const _hoisted_46 = { class: "fl-cell fl-cell-check" };
|
|
1689
|
+
const _hoisted_47 = [
|
|
1479
1690
|
"disabled",
|
|
1480
1691
|
"aria-label",
|
|
1481
1692
|
"checked",
|
|
1482
1693
|
".indeterminate",
|
|
1483
1694
|
"onChange"
|
|
1484
1695
|
];
|
|
1485
|
-
const
|
|
1486
|
-
const
|
|
1696
|
+
const _hoisted_48 = ["title"];
|
|
1697
|
+
const _hoisted_49 = [
|
|
1487
1698
|
"aria-label",
|
|
1488
1699
|
"title",
|
|
1489
1700
|
"onClick"
|
|
1490
1701
|
];
|
|
1491
|
-
const
|
|
1702
|
+
const _hoisted_50 = [
|
|
1492
1703
|
"aria-label",
|
|
1493
1704
|
"aria-expanded",
|
|
1494
1705
|
"onClick"
|
|
1495
1706
|
];
|
|
1496
|
-
const
|
|
1707
|
+
const _hoisted_51 = {
|
|
1497
1708
|
key: 2,
|
|
1498
1709
|
class: "fl-arrow-placeholder",
|
|
1499
1710
|
"aria-hidden": "true"
|
|
1500
1711
|
};
|
|
1501
|
-
const
|
|
1712
|
+
const _hoisted_52 = {
|
|
1502
1713
|
key: 3,
|
|
1503
1714
|
class: "fl-folder-icon",
|
|
1504
1715
|
viewBox: "0 0 24 24",
|
|
@@ -1506,27 +1717,27 @@ const _hoisted_44 = {
|
|
|
1506
1717
|
height: "18",
|
|
1507
1718
|
"aria-hidden": "true"
|
|
1508
1719
|
};
|
|
1509
|
-
const
|
|
1510
|
-
const
|
|
1511
|
-
const
|
|
1512
|
-
const
|
|
1513
|
-
const
|
|
1720
|
+
const _hoisted_53 = ["data-kind"];
|
|
1721
|
+
const _hoisted_54 = { class: "fl-label" };
|
|
1722
|
+
const _hoisted_55 = ["onClick"];
|
|
1723
|
+
const _hoisted_56 = { class: "fl-meta" };
|
|
1724
|
+
const _hoisted_57 = {
|
|
1514
1725
|
key: 5,
|
|
1515
1726
|
class: "fl-count"
|
|
1516
1727
|
};
|
|
1517
|
-
const
|
|
1518
|
-
const
|
|
1728
|
+
const _hoisted_58 = ["id"];
|
|
1729
|
+
const _hoisted_59 = [
|
|
1519
1730
|
"aria-label",
|
|
1520
1731
|
"title",
|
|
1521
1732
|
"onClick"
|
|
1522
1733
|
];
|
|
1523
|
-
const
|
|
1734
|
+
const _hoisted_60 = {
|
|
1524
1735
|
key: 8,
|
|
1525
1736
|
class: "fl-loading",
|
|
1526
1737
|
"aria-hidden": "true"
|
|
1527
1738
|
};
|
|
1528
|
-
const
|
|
1529
|
-
const
|
|
1739
|
+
const _hoisted_61 = ["onSubmit", "onKeydown"];
|
|
1740
|
+
const _hoisted_62 = [
|
|
1530
1741
|
"onUpdate:modelValue",
|
|
1531
1742
|
"data-unlock",
|
|
1532
1743
|
"placeholder",
|
|
@@ -1534,43 +1745,45 @@ const _hoisted_54 = [
|
|
|
1534
1745
|
"aria-invalid",
|
|
1535
1746
|
"aria-describedby"
|
|
1536
1747
|
];
|
|
1537
|
-
const
|
|
1748
|
+
const _hoisted_63 = [
|
|
1538
1749
|
"aria-pressed",
|
|
1539
1750
|
"aria-label",
|
|
1540
1751
|
"title",
|
|
1541
1752
|
"onClick"
|
|
1542
1753
|
];
|
|
1543
|
-
const
|
|
1544
|
-
const
|
|
1754
|
+
const _hoisted_64 = ["disabled"];
|
|
1755
|
+
const _hoisted_65 = [
|
|
1545
1756
|
"aria-label",
|
|
1546
1757
|
"title",
|
|
1547
1758
|
"onClick"
|
|
1548
1759
|
];
|
|
1549
|
-
const
|
|
1550
|
-
const
|
|
1551
|
-
const
|
|
1552
|
-
const
|
|
1553
|
-
const
|
|
1760
|
+
const _hoisted_66 = { class: "fl-cell fl-cell-size" };
|
|
1761
|
+
const _hoisted_67 = { class: "fl-cell fl-cell-date" };
|
|
1762
|
+
const _hoisted_68 = { class: "fl-cell fl-cell-op" };
|
|
1763
|
+
const _hoisted_69 = ["aria-label", "onClick"];
|
|
1764
|
+
const _hoisted_70 = [
|
|
1554
1765
|
"aria-label",
|
|
1555
1766
|
"aria-expanded",
|
|
1556
1767
|
"onClick"
|
|
1557
1768
|
];
|
|
1558
|
-
const
|
|
1769
|
+
const _hoisted_71 = [
|
|
1559
1770
|
"aria-label",
|
|
1560
1771
|
"title",
|
|
1561
1772
|
"onClick"
|
|
1562
1773
|
];
|
|
1563
|
-
const
|
|
1774
|
+
const _hoisted_72 = [
|
|
1564
1775
|
"aria-label",
|
|
1565
1776
|
"title",
|
|
1566
1777
|
"onClick"
|
|
1567
1778
|
];
|
|
1568
|
-
const
|
|
1569
|
-
const
|
|
1779
|
+
const _hoisted_73 = { class: "fl-foot" };
|
|
1780
|
+
const _hoisted_74 = {
|
|
1570
1781
|
key: 4,
|
|
1571
1782
|
class: "fl-toast",
|
|
1572
1783
|
role: "status"
|
|
1573
1784
|
};
|
|
1785
|
+
/** Rows shown per folder, beyond the first page; kept across refreshes. */
|
|
1786
|
+
const MB = 1048576;
|
|
1574
1787
|
const _sfc_main = /*@__PURE__*/ defineComponent({
|
|
1575
1788
|
__name: "FileList",
|
|
1576
1789
|
props: {
|
|
@@ -1588,6 +1801,9 @@ const _sfc_main = /*@__PURE__*/ defineComponent({
|
|
|
1588
1801
|
type: Boolean,
|
|
1589
1802
|
default: true
|
|
1590
1803
|
},
|
|
1804
|
+
pageSize: { default: 200 },
|
|
1805
|
+
zipWarnSize: {},
|
|
1806
|
+
zipMaxSize: {},
|
|
1591
1807
|
locale: { default: "zh-CN" },
|
|
1592
1808
|
labels: {}
|
|
1593
1809
|
},
|
|
@@ -1630,7 +1846,8 @@ const _sfc_main = /*@__PURE__*/ defineComponent({
|
|
|
1630
1846
|
const siteTitle = ref("");
|
|
1631
1847
|
const iframePreviews = ref("");
|
|
1632
1848
|
const batchBusy = ref(false);
|
|
1633
|
-
const
|
|
1849
|
+
const zipProgress = ref(null);
|
|
1850
|
+
let zipAbort = null;
|
|
1634
1851
|
let toastTimer;
|
|
1635
1852
|
/** The folder listed in single-path mode, as the parent of the top rows. */
|
|
1636
1853
|
const listedFolder = computed(() => ({
|
|
@@ -1863,6 +2080,7 @@ const _sfc_main = /*@__PURE__*/ defineComponent({
|
|
|
1863
2080
|
errorMsg.value = "";
|
|
1864
2081
|
try {
|
|
1865
2082
|
roots.value = await buildTree();
|
|
2083
|
+
shown.clear();
|
|
1866
2084
|
rootLock.value = null;
|
|
1867
2085
|
selected.value = /* @__PURE__ */ new Set();
|
|
1868
2086
|
api.value.clearCache();
|
|
@@ -1943,20 +2161,41 @@ const _sfc_main = /*@__PURE__*/ defineComponent({
|
|
|
1943
2161
|
applySort(key, direction !== "desc");
|
|
1944
2162
|
}
|
|
1945
2163
|
});
|
|
1946
|
-
|
|
2164
|
+
/** A “show more” row closing a folder whose children are cut at `pageSize`. */
|
|
2165
|
+
const shown = reactive(/* @__PURE__ */ new Map());
|
|
2166
|
+
function limitOf(key) {
|
|
2167
|
+
const size = Math.max(0, Math.floor(props.pageSize ?? 200));
|
|
2168
|
+
return size ? shown.get(key) ?? size : Number.POSITIVE_INFINITY;
|
|
2169
|
+
}
|
|
2170
|
+
function showMore(row, all) {
|
|
2171
|
+
const size = Math.max(1, Math.floor(props.pageSize ?? 200));
|
|
2172
|
+
shown.set(row.key, all ? Number.POSITIVE_INFINITY : limitOf(row.key) + size);
|
|
2173
|
+
}
|
|
2174
|
+
function isMore(row) {
|
|
2175
|
+
return "more" in row;
|
|
2176
|
+
}
|
|
2177
|
+
const rows = computed(() => {
|
|
1947
2178
|
const out = [];
|
|
1948
2179
|
const query = keyword.value.trim().toLowerCase();
|
|
1949
2180
|
const matches = (node) => !query || node.name.toLowerCase().includes(query) || node.is_dir && node.children.some(matches);
|
|
1950
|
-
const walk = (nodes) => {
|
|
1951
|
-
|
|
1952
|
-
|
|
2181
|
+
const walk = (nodes, key, depth) => {
|
|
2182
|
+
const list = nodes.filter(matches);
|
|
2183
|
+
const limit = query ? list.length : Math.min(list.length, limitOf(key));
|
|
2184
|
+
for (const node of list.slice(0, limit)) {
|
|
1953
2185
|
out.push(node);
|
|
1954
|
-
if (node.is_dir && (node.expanded || query) && node.children.length) walk(node.children);
|
|
2186
|
+
if (node.is_dir && (node.expanded || query) && node.children.length) walk(node.children, node.path, node.depth + 1);
|
|
1955
2187
|
}
|
|
2188
|
+
if (limit < list.length) out.push({
|
|
2189
|
+
more: true,
|
|
2190
|
+
key,
|
|
2191
|
+
depth,
|
|
2192
|
+
remaining: list.length - limit
|
|
2193
|
+
});
|
|
1956
2194
|
};
|
|
1957
|
-
walk(roots.value);
|
|
2195
|
+
walk(roots.value, props.sources.length ? "" : props.path, 0);
|
|
1958
2196
|
return out;
|
|
1959
2197
|
});
|
|
2198
|
+
const visible = computed(() => rows.value.filter((row) => !isMore(row)));
|
|
1960
2199
|
const stats = computed(() => folderStats(roots.value, selected.value));
|
|
1961
2200
|
const noStats = {
|
|
1962
2201
|
files: 0,
|
|
@@ -2038,29 +2277,114 @@ const _sfc_main = /*@__PURE__*/ defineComponent({
|
|
|
2038
2277
|
return;
|
|
2039
2278
|
}
|
|
2040
2279
|
try {
|
|
2041
|
-
|
|
2280
|
+
const url = await fileUrlOf(node);
|
|
2281
|
+
openUrl(url, {
|
|
2282
|
+
sameTab: api.value.isAttachmentUrl(url),
|
|
2283
|
+
name: node.name
|
|
2284
|
+
});
|
|
2285
|
+
showToast(t("downloadStarted", { name: node.name }));
|
|
2042
2286
|
} catch (error) {
|
|
2043
2287
|
showToast(t("downloadFailed", { message: errorText(error) }));
|
|
2044
2288
|
}
|
|
2045
2289
|
}
|
|
2290
|
+
function zipLimits() {
|
|
2291
|
+
const touch = typeof window !== "undefined" && !!window.matchMedia?.("(pointer: coarse)").matches;
|
|
2292
|
+
const bytes = (value, fallback) => {
|
|
2293
|
+
const mb = value ?? fallback;
|
|
2294
|
+
return mb > 0 ? mb * MB : Number.POSITIVE_INFINITY;
|
|
2295
|
+
};
|
|
2296
|
+
return {
|
|
2297
|
+
warn: bytes(props.zipWarnSize, touch ? 200 : 500),
|
|
2298
|
+
max: bytes(props.zipMaxSize, touch ? 1024 : 2048)
|
|
2299
|
+
};
|
|
2300
|
+
}
|
|
2301
|
+
const zipNotice = ref(null);
|
|
2302
|
+
/** Only desktop browsers get “use Chrome or Edge”; on iPhone every browser is Safari. */
|
|
2303
|
+
const zipTip = computed(() => typeof window !== "undefined" && !window.matchMedia?.("(pointer: coarse)").matches ? t("zipStreamTip") : "");
|
|
2304
|
+
function zipName() {
|
|
2305
|
+
return zipFileName(props.title || t("defaultZip"));
|
|
2306
|
+
}
|
|
2307
|
+
/**
|
|
2308
|
+
* Chrome / Edge stream into a file the user picks (no size limit). Other
|
|
2309
|
+
* browsers build the ZIP in memory, so large selections ask first or are refused.
|
|
2310
|
+
*/
|
|
2046
2311
|
async function batchDownload() {
|
|
2047
2312
|
const files = selectedFiles.value;
|
|
2048
|
-
if (!files.length) return;
|
|
2313
|
+
if (!files.length || batchBusy.value) return;
|
|
2049
2314
|
if (demo.value) {
|
|
2050
2315
|
showToast(t("demoBatch", { count: files.length }));
|
|
2051
2316
|
return;
|
|
2052
2317
|
}
|
|
2318
|
+
if (canStreamToDisk()) {
|
|
2319
|
+
let handle;
|
|
2320
|
+
try {
|
|
2321
|
+
handle = await pickZipFile(zipName());
|
|
2322
|
+
} catch (error) {
|
|
2323
|
+
showToast(t("batchFailed", { message: errorText(error) }));
|
|
2324
|
+
return;
|
|
2325
|
+
}
|
|
2326
|
+
if (handle) await runZip(files, (options) => zipToFile(handle, files, options), handle.name);
|
|
2327
|
+
return;
|
|
2328
|
+
}
|
|
2329
|
+
const size = totalSize(files);
|
|
2330
|
+
const { warn, max } = zipLimits();
|
|
2331
|
+
if (size > max) zipNotice.value = {
|
|
2332
|
+
kind: "block",
|
|
2333
|
+
size,
|
|
2334
|
+
limit: max,
|
|
2335
|
+
files
|
|
2336
|
+
};
|
|
2337
|
+
else if (size > warn) zipNotice.value = {
|
|
2338
|
+
kind: "warn",
|
|
2339
|
+
size,
|
|
2340
|
+
limit: warn,
|
|
2341
|
+
files
|
|
2342
|
+
};
|
|
2343
|
+
else await zipInMemory(files);
|
|
2344
|
+
}
|
|
2345
|
+
async function zipInMemory(files) {
|
|
2346
|
+
const name = zipName();
|
|
2347
|
+
await runZip(files, async (options) => saveBlob(await zipToBlob(files, options), name), name);
|
|
2348
|
+
}
|
|
2349
|
+
function confirmZip() {
|
|
2350
|
+
const notice = zipNotice.value;
|
|
2351
|
+
zipNotice.value = null;
|
|
2352
|
+
if (notice?.kind === "warn") zipInMemory(notice.files);
|
|
2353
|
+
}
|
|
2354
|
+
async function runZip(files, run, name) {
|
|
2355
|
+
const controller = new AbortController();
|
|
2356
|
+
zipAbort = controller;
|
|
2053
2357
|
batchBusy.value = true;
|
|
2054
|
-
|
|
2358
|
+
zipProgress.value = null;
|
|
2055
2359
|
try {
|
|
2056
|
-
|
|
2360
|
+
await run({
|
|
2361
|
+
urlOf: fileUrlOf,
|
|
2362
|
+
signal: controller.signal,
|
|
2363
|
+
onProgress: (progress) => zipProgress.value = progress
|
|
2364
|
+
});
|
|
2365
|
+
showToast(t("batchDone", {
|
|
2366
|
+
name,
|
|
2367
|
+
count: files.length,
|
|
2368
|
+
size: formatSize(totalSize(files))
|
|
2369
|
+
}));
|
|
2057
2370
|
selected.value = /* @__PURE__ */ new Set();
|
|
2058
2371
|
} catch (error) {
|
|
2059
|
-
showToast(t("batchFailed", { message: errorText(error) }));
|
|
2372
|
+
showToast(controller.signal.aborted ? t("batchCanceled") : t("batchFailed", { message: errorText(error) }));
|
|
2060
2373
|
} finally {
|
|
2374
|
+
zipAbort = null;
|
|
2061
2375
|
batchBusy.value = false;
|
|
2376
|
+
zipProgress.value = null;
|
|
2062
2377
|
}
|
|
2063
2378
|
}
|
|
2379
|
+
function cancelZip() {
|
|
2380
|
+
zipAbort?.abort();
|
|
2381
|
+
}
|
|
2382
|
+
const zipPercent = computed(() => {
|
|
2383
|
+
const progress = zipProgress.value;
|
|
2384
|
+
if (!progress) return 0;
|
|
2385
|
+
const ratio = progress.totalBytes ? progress.bytes / progress.totalBytes : progress.totalFiles ? progress.files / progress.totalFiles : 0;
|
|
2386
|
+
return Math.min(100, Math.floor(ratio * 100));
|
|
2387
|
+
});
|
|
2064
2388
|
/** Only types the dialog can actually render get a preview button. */
|
|
2065
2389
|
function canPreview(node) {
|
|
2066
2390
|
return !node.is_dir && previewKind(node.name) !== "none";
|
|
@@ -2132,6 +2456,7 @@ const _sfc_main = /*@__PURE__*/ defineComponent({
|
|
|
2132
2456
|
window.addEventListener("resize", measureStickyTop, { passive: true });
|
|
2133
2457
|
});
|
|
2134
2458
|
onBeforeUnmount(() => {
|
|
2459
|
+
zipAbort?.abort();
|
|
2135
2460
|
window.removeEventListener("resize", measureStickyTop);
|
|
2136
2461
|
clearTimeout(toastTimer);
|
|
2137
2462
|
});
|
|
@@ -2147,9 +2472,22 @@ const _sfc_main = /*@__PURE__*/ defineComponent({
|
|
|
2147
2472
|
"aria-busy": refreshing.value || loadingRoot.value
|
|
2148
2473
|
}, [
|
|
2149
2474
|
createElementVNode("div", _hoisted_2, [
|
|
2150
|
-
|
|
2151
|
-
|
|
2152
|
-
|
|
2475
|
+
batchBusy.value ? (openBlock(), createElementBlock("div", _hoisted_3, [
|
|
2476
|
+
createElementVNode("span", _hoisted_4, toDisplayString(t("batching", { percent: zipPercent.value })), 1),
|
|
2477
|
+
zipProgress.value ? (openBlock(), createElementBlock("span", _hoisted_5, toDisplayString(t("batchProgress", {
|
|
2478
|
+
done: unref(formatSize)(zipProgress.value.bytes),
|
|
2479
|
+
total: unref(formatSize)(zipProgress.value.totalBytes),
|
|
2480
|
+
files: zipProgress.value.files,
|
|
2481
|
+
count: zipProgress.value.totalFiles
|
|
2482
|
+
})), 1)) : createCommentVNode("v-if", true),
|
|
2483
|
+
createElementVNode("span", {
|
|
2484
|
+
class: "fl-zip-bar",
|
|
2485
|
+
style: normalizeStyle({ width: `${zipPercent.value}%` }),
|
|
2486
|
+
"aria-hidden": "true"
|
|
2487
|
+
}, null, 4)
|
|
2488
|
+
])) : selected.value.size ? (openBlock(), createElementBlock("div", _hoisted_6, [createElementVNode("span", _hoisted_7, toDisplayString(t("selected", { count: selected.value.size })), 1), createElementVNode("span", _hoisted_8, toDisplayString(t("totalSize", { size: unref(formatSize)(unref(totalSize)(selectedFiles.value)) })), 1)])) : (openBlock(), createElementBlock("div", _hoisted_9, [createElementVNode("span", _hoisted_10, toDisplayString(displayTitle.value), 1), demo.value ? (openBlock(), createElementBlock("span", _hoisted_11, toDisplayString(t("demoBadge")), 1)) : createCommentVNode("v-if", true)])),
|
|
2489
|
+
selected.value.size && !batchBusy.value ? (openBlock(), createElementBlock("button", {
|
|
2490
|
+
key: 3,
|
|
2153
2491
|
class: "fl-clear",
|
|
2154
2492
|
type: "button",
|
|
2155
2493
|
"aria-label": t("clearSelection"),
|
|
@@ -2159,8 +2497,8 @@ const _sfc_main = /*@__PURE__*/ defineComponent({
|
|
|
2159
2497
|
class: "fl-clear-icon",
|
|
2160
2498
|
name: "close",
|
|
2161
2499
|
size: 18
|
|
2162
|
-
}), createElementVNode("span",
|
|
2163
|
-
createElementVNode("div",
|
|
2500
|
+
}), createElementVNode("span", _hoisted_13, toDisplayString(t("clear")), 1)], 8, _hoisted_12)) : createCommentVNode("v-if", true),
|
|
2501
|
+
createElementVNode("div", _hoisted_14, [createElementVNode("label", _hoisted_15, [createVNode(_sfc_main$2, {
|
|
2164
2502
|
name: "search",
|
|
2165
2503
|
size: 15
|
|
2166
2504
|
}), withDirectives(createElementVNode("input", {
|
|
@@ -2168,7 +2506,7 @@ const _sfc_main = /*@__PURE__*/ defineComponent({
|
|
|
2168
2506
|
type: "text",
|
|
2169
2507
|
placeholder: t("filter"),
|
|
2170
2508
|
"aria-label": t("filter")
|
|
2171
|
-
}, null, 8,
|
|
2509
|
+
}, null, 8, _hoisted_16), [[vModelText, keyword.value]])]), createElementVNode("button", {
|
|
2172
2510
|
class: normalizeClass(["fl-icon-btn fl-refresh", { "fl-spinning": refreshing.value }]),
|
|
2173
2511
|
type: "button",
|
|
2174
2512
|
disabled: refreshing.value || loadingRoot.value,
|
|
@@ -2178,27 +2516,32 @@ const _sfc_main = /*@__PURE__*/ defineComponent({
|
|
|
2178
2516
|
}, [createVNode(_sfc_main$2, {
|
|
2179
2517
|
name: "refresh",
|
|
2180
2518
|
size: 15
|
|
2181
|
-
})], 10,
|
|
2182
|
-
|
|
2183
|
-
key:
|
|
2519
|
+
})], 10, _hoisted_17)]),
|
|
2520
|
+
batchBusy.value ? (openBlock(), createElementBlock("button", {
|
|
2521
|
+
key: 4,
|
|
2522
|
+
class: "fl-btn fl-zip-cancel",
|
|
2523
|
+
type: "button",
|
|
2524
|
+
onClick: cancelZip
|
|
2525
|
+
}, toDisplayString(t("cancel")), 1)) : selected.value.size ? (openBlock(), createElementBlock("button", {
|
|
2526
|
+
key: 5,
|
|
2184
2527
|
class: "fl-btn fl-btn-primary",
|
|
2185
2528
|
type: "button",
|
|
2186
|
-
disabled: batchBusy.value,
|
|
2187
2529
|
onClick: batchDownload
|
|
2188
2530
|
}, [createVNode(_sfc_main$2, {
|
|
2189
2531
|
name: "download",
|
|
2190
2532
|
size: 15
|
|
2191
|
-
}), createTextVNode(" " + toDisplayString(
|
|
2533
|
+
}), createTextVNode(" " + toDisplayString(t("batch")), 1)])) : createCommentVNode("v-if", true)
|
|
2192
2534
|
]),
|
|
2193
|
-
createElementVNode("div",
|
|
2194
|
-
refreshing.value ? (openBlock(), createElementBlock("span",
|
|
2195
|
-
createElementVNode("label",
|
|
2535
|
+
createElementVNode("div", _hoisted_18, [
|
|
2536
|
+
refreshing.value ? (openBlock(), createElementBlock("span", _hoisted_19)) : createCommentVNode("v-if", true),
|
|
2537
|
+
createElementVNode("label", _hoisted_20, [createElementVNode("input", {
|
|
2196
2538
|
type: "checkbox",
|
|
2197
2539
|
"aria-label": t("selectAll"),
|
|
2540
|
+
disabled: batchBusy.value,
|
|
2198
2541
|
checked: allChecked.value,
|
|
2199
2542
|
".indeterminate": someChecked.value,
|
|
2200
2543
|
onChange: toggleCheckAll
|
|
2201
|
-
}, null, 40,
|
|
2544
|
+
}, null, 40, _hoisted_21)]),
|
|
2202
2545
|
(openBlock(), createElementBlock(Fragment, null, renderList([
|
|
2203
2546
|
"name",
|
|
2204
2547
|
"size",
|
|
@@ -2212,11 +2555,11 @@ const _sfc_main = /*@__PURE__*/ defineComponent({
|
|
|
2212
2555
|
type: "button",
|
|
2213
2556
|
"aria-sort": sortKey.value === column ? sortAsc.value ? "ascending" : "descending" : void 0,
|
|
2214
2557
|
onClick: ($event) => setSort(column)
|
|
2215
|
-
}, [createTextVNode(toDisplayString(t(column === "name" ? "columnName" : column === "size" ? "columnSize" : "columnDate")), 1), createElementVNode("span",
|
|
2558
|
+
}, [createTextVNode(toDisplayString(t(column === "name" ? "columnName" : column === "size" ? "columnSize" : "columnDate")), 1), createElementVNode("span", _hoisted_23, toDisplayString(sortKey.value === column ? sortAsc.value ? "▲" : "▼" : ""), 1)], 8, _hoisted_22)], 2);
|
|
2216
2559
|
}), 64)),
|
|
2217
|
-
createElementVNode("span",
|
|
2560
|
+
createElementVNode("span", _hoisted_24, [createElementVNode("label", _hoisted_25, [
|
|
2218
2561
|
createElementVNode("span", null, toDisplayString(t("sortBy")), 1),
|
|
2219
|
-
createElementVNode("span",
|
|
2562
|
+
createElementVNode("span", _hoisted_26, toDisplayString(sortOptions.value.find((option) => option.value === sortValue.value)?.label), 1),
|
|
2220
2563
|
withDirectives(createElementVNode("select", {
|
|
2221
2564
|
"onUpdate:modelValue": _cache[1] || (_cache[1] = ($event) => sortValue.value = $event),
|
|
2222
2565
|
"aria-label": t("sortBy")
|
|
@@ -2224,11 +2567,11 @@ const _sfc_main = /*@__PURE__*/ defineComponent({
|
|
|
2224
2567
|
return openBlock(), createElementBlock("option", {
|
|
2225
2568
|
key: option.value,
|
|
2226
2569
|
value: option.value
|
|
2227
|
-
}, toDisplayString(option.label), 9,
|
|
2228
|
-
}), 128))], 8,
|
|
2570
|
+
}, toDisplayString(option.label), 9, _hoisted_28);
|
|
2571
|
+
}), 128))], 8, _hoisted_27), [[vModelSelect, sortValue.value]])
|
|
2229
2572
|
])])
|
|
2230
2573
|
]),
|
|
2231
|
-
loadingRoot.value ? (openBlock(), createElementBlock("div",
|
|
2574
|
+
loadingRoot.value ? (openBlock(), createElementBlock("div", _hoisted_29, toDisplayString(t("loading")), 1)) : rootLock.value ? (openBlock(), createElementBlock("form", {
|
|
2232
2575
|
key: 1,
|
|
2233
2576
|
class: normalizeClass(["fl-unlock-root", { "fl-unlock-error": rootLock.value.error }]),
|
|
2234
2577
|
onSubmit: withModifiers(submitRootUnlock, ["prevent"])
|
|
@@ -2240,14 +2583,14 @@ const _sfc_main = /*@__PURE__*/ defineComponent({
|
|
|
2240
2583
|
createElementVNode("label", {
|
|
2241
2584
|
class: "fl-unlock-label",
|
|
2242
2585
|
for: `${unref(uid)}-root`
|
|
2243
|
-
}, toDisplayString(t("passwordPrompt")), 9,
|
|
2586
|
+
}, toDisplayString(t("passwordPrompt")), 9, _hoisted_30),
|
|
2244
2587
|
rootLock.value.error ? (openBlock(), createElementBlock("span", {
|
|
2245
2588
|
key: 0,
|
|
2246
2589
|
id: `${unref(uid)}-root-error`,
|
|
2247
2590
|
class: "fl-unlock-message",
|
|
2248
2591
|
role: "alert"
|
|
2249
|
-
}, toDisplayString(unlockErrorText(rootLock.value.error)), 9,
|
|
2250
|
-
createElementVNode("span",
|
|
2592
|
+
}, toDisplayString(unlockErrorText(rootLock.value.error)), 9, _hoisted_31)) : createCommentVNode("v-if", true),
|
|
2593
|
+
createElementVNode("span", _hoisted_32, [
|
|
2251
2594
|
withDirectives(createElementVNode("input", {
|
|
2252
2595
|
id: `${unref(uid)}-root`,
|
|
2253
2596
|
"onUpdate:modelValue": _cache[2] || (_cache[2] = ($event) => rootLock.value.input = $event),
|
|
@@ -2257,7 +2600,7 @@ const _sfc_main = /*@__PURE__*/ defineComponent({
|
|
|
2257
2600
|
placeholder: t("passwordPlaceholder"),
|
|
2258
2601
|
"aria-invalid": !!rootLock.value.error,
|
|
2259
2602
|
"aria-describedby": rootLock.value.error ? `${unref(uid)}-root-error` : void 0
|
|
2260
|
-
}, null, 8,
|
|
2603
|
+
}, null, 8, _hoisted_33), [[vModelText, rootLock.value.input]]),
|
|
2261
2604
|
canRemember.value ? (openBlock(), createElementBlock("button", {
|
|
2262
2605
|
key: 0,
|
|
2263
2606
|
class: "fl-unlock-remember",
|
|
@@ -2266,26 +2609,50 @@ const _sfc_main = /*@__PURE__*/ defineComponent({
|
|
|
2266
2609
|
"aria-label": t("rememberPassword"),
|
|
2267
2610
|
title: t("rememberPassword"),
|
|
2268
2611
|
onClick: _cache[3] || (_cache[3] = ($event) => rootLock.value.remember = !rootLock.value.remember)
|
|
2269
|
-
}, [createVNode(_sfc_main$2, { name: "key" })], 8,
|
|
2612
|
+
}, [createVNode(_sfc_main$2, { name: "key" })], 8, _hoisted_34)) : createCommentVNode("v-if", true),
|
|
2270
2613
|
createElementVNode("button", {
|
|
2271
2614
|
class: "fl-unlock-submit",
|
|
2272
2615
|
type: "submit",
|
|
2273
2616
|
disabled: rootLock.value.busy || !rootLock.value.input
|
|
2274
|
-
}, toDisplayString(t("open")), 9,
|
|
2617
|
+
}, toDisplayString(t("open")), 9, _hoisted_35)
|
|
2275
2618
|
])
|
|
2276
|
-
], 34)) : errorMsg.value ? (openBlock(), createElementBlock("div",
|
|
2619
|
+
], 34)) : errorMsg.value ? (openBlock(), createElementBlock("div", _hoisted_36, [
|
|
2277
2620
|
createTextVNode(toDisplayString(t("loadFailed", { message: errorMsg.value })) + " ", 1),
|
|
2278
|
-
/guest/i.test(errorMsg.value) ? (openBlock(), createElementBlock("p",
|
|
2279
|
-
unref(isNetworkError)(errorMsg.value) ? (openBlock(), createElementBlock("p",
|
|
2621
|
+
/guest/i.test(errorMsg.value) ? (openBlock(), createElementBlock("p", _hoisted_37, toDisplayString(t("guestHint")), 1)) : createCommentVNode("v-if", true),
|
|
2622
|
+
unref(isNetworkError)(errorMsg.value) ? (openBlock(), createElementBlock("p", _hoisted_38, toDisplayString(t("corsHint")), 1)) : createCommentVNode("v-if", true),
|
|
2280
2623
|
createElementVNode("button", {
|
|
2281
2624
|
class: "fl-btn",
|
|
2282
2625
|
type: "button",
|
|
2283
2626
|
onClick: loadRoot
|
|
2284
2627
|
}, toDisplayString(t("retry")), 1)
|
|
2285
|
-
])) : visible.value.length === 0 ? (openBlock(), createElementBlock("div",
|
|
2286
|
-
(openBlock(true), createElementBlock(Fragment, null, renderList(
|
|
2287
|
-
return openBlock(), createElementBlock("div", {
|
|
2288
|
-
key:
|
|
2628
|
+
])) : visible.value.length === 0 ? (openBlock(), createElementBlock("div", _hoisted_39, toDisplayString(t("empty")), 1)) : createCommentVNode("v-if", true),
|
|
2629
|
+
(openBlock(true), createElementBlock(Fragment, null, renderList(rows.value, (node, index) => {
|
|
2630
|
+
return openBlock(), createElementBlock(Fragment, { key: isMore(node) ? `more:${node.key}` : node.path }, [isMore(node) ? (openBlock(), createElementBlock("div", {
|
|
2631
|
+
key: 0,
|
|
2632
|
+
class: "fl-row fl-more",
|
|
2633
|
+
style: normalizeStyle({ "--fl-depth": node.depth })
|
|
2634
|
+
}, [_cache[9] || (_cache[9] = createElementVNode("span", { class: "fl-cell fl-cell-check" }, null, -1)), createElementVNode("span", _hoisted_40, [
|
|
2635
|
+
_cache[8] || (_cache[8] = createElementVNode("span", {
|
|
2636
|
+
class: "fl-indent",
|
|
2637
|
+
"aria-hidden": "true"
|
|
2638
|
+
}, null, -1)),
|
|
2639
|
+
createElementVNode("span", _hoisted_41, toDisplayString(t("moreRemaining", { count: node.remaining })), 1),
|
|
2640
|
+
node.remaining > (__props.pageSize || 0) ? (openBlock(), createElementBlock(Fragment, { key: 0 }, [createElementVNode("button", {
|
|
2641
|
+
class: "fl-more-btn",
|
|
2642
|
+
type: "button",
|
|
2643
|
+
onClick: ($event) => showMore(node, false)
|
|
2644
|
+
}, [createTextVNode(toDisplayString(t("showMore")), 1), createElementVNode("span", _hoisted_43, toDisplayString(` ${t("folderItems", { count: __props.pageSize })}`), 1)], 8, _hoisted_42), createElementVNode("button", {
|
|
2645
|
+
class: "fl-more-btn fl-more-all",
|
|
2646
|
+
type: "button",
|
|
2647
|
+
onClick: ($event) => showMore(node, true)
|
|
2648
|
+
}, toDisplayString(t("showAll")), 9, _hoisted_44)], 64)) : (openBlock(), createElementBlock("button", {
|
|
2649
|
+
key: 1,
|
|
2650
|
+
class: "fl-more-btn",
|
|
2651
|
+
type: "button",
|
|
2652
|
+
onClick: ($event) => showMore(node, true)
|
|
2653
|
+
}, toDisplayString(t("showRest", { count: node.remaining })), 9, _hoisted_45))
|
|
2654
|
+
])], 4)) : (openBlock(), createElementBlock("div", {
|
|
2655
|
+
key: 1,
|
|
2289
2656
|
class: normalizeClass(["fl-row", {
|
|
2290
2657
|
"fl-row-dir": node.is_dir,
|
|
2291
2658
|
"fl-row-root": node.isRoot,
|
|
@@ -2296,19 +2663,19 @@ const _sfc_main = /*@__PURE__*/ defineComponent({
|
|
|
2296
2663
|
}]),
|
|
2297
2664
|
style: normalizeStyle({ "--fl-depth": node.depth })
|
|
2298
2665
|
}, [
|
|
2299
|
-
createElementVNode("label",
|
|
2666
|
+
createElementVNode("label", _hoisted_46, [createElementVNode("input", {
|
|
2300
2667
|
type: "checkbox",
|
|
2301
|
-
disabled: !!node.lock,
|
|
2668
|
+
disabled: !!node.lock || batchBusy.value,
|
|
2302
2669
|
"aria-label": t("selectItem", { name: node.name }),
|
|
2303
2670
|
checked: isChecked(node),
|
|
2304
2671
|
".indeterminate": isIndeterminate(node),
|
|
2305
2672
|
onChange: ($event) => toggleCheck(node, $event)
|
|
2306
|
-
}, null, 40,
|
|
2673
|
+
}, null, 40, _hoisted_47)]),
|
|
2307
2674
|
createElementVNode("span", {
|
|
2308
2675
|
class: "fl-cell fl-cell-name",
|
|
2309
2676
|
title: node.isRoot ? node.path : void 0
|
|
2310
2677
|
}, [
|
|
2311
|
-
_cache[
|
|
2678
|
+
_cache[11] || (_cache[11] = createElementVNode("span", {
|
|
2312
2679
|
class: "fl-indent",
|
|
2313
2680
|
"aria-hidden": "true"
|
|
2314
2681
|
}, null, -1)),
|
|
@@ -2322,7 +2689,7 @@ const _sfc_main = /*@__PURE__*/ defineComponent({
|
|
|
2322
2689
|
}, [createVNode(_sfc_main$2, {
|
|
2323
2690
|
name: "lock",
|
|
2324
2691
|
size: 14
|
|
2325
|
-
})], 8,
|
|
2692
|
+
})], 8, _hoisted_49)) : node.is_dir ? (openBlock(), createElementBlock("button", {
|
|
2326
2693
|
key: 1,
|
|
2327
2694
|
class: normalizeClass(["fl-arrow", { "fl-arrow-open": node.expanded }]),
|
|
2328
2695
|
type: "button",
|
|
@@ -2332,24 +2699,24 @@ const _sfc_main = /*@__PURE__*/ defineComponent({
|
|
|
2332
2699
|
}, [createVNode(_sfc_main$2, {
|
|
2333
2700
|
name: "next",
|
|
2334
2701
|
size: 14
|
|
2335
|
-
})], 10,
|
|
2336
|
-
node.is_dir ? (openBlock(), createElementBlock("svg",
|
|
2702
|
+
})], 10, _hoisted_50)) : (openBlock(), createElementBlock("span", _hoisted_51)),
|
|
2703
|
+
node.is_dir ? (openBlock(), createElementBlock("svg", _hoisted_52, [..._cache[10] || (_cache[10] = [createElementVNode("path", { d: "M3 7a2 2 0 0 1 2-2h4l2 2h8a2 2 0 0 1 2 2v8a2 2 0 0 1-2 2H5a2 2 0 0 1-2-2z" }, null, -1)])])) : (openBlock(), createElementBlock("span", {
|
|
2337
2704
|
key: 4,
|
|
2338
2705
|
class: "fl-type",
|
|
2339
2706
|
"data-kind": unref(fileKind)(node.name),
|
|
2340
2707
|
"aria-hidden": "true"
|
|
2341
|
-
}, toDisplayString(unref(extOf)(node.name) || "FILE"), 9,
|
|
2342
|
-
createElementVNode("span",
|
|
2708
|
+
}, toDisplayString(unref(extOf)(node.name) || "FILE"), 9, _hoisted_53)),
|
|
2709
|
+
createElementVNode("span", _hoisted_54, [createElementVNode("span", {
|
|
2343
2710
|
class: normalizeClass(["fl-name", { "fl-name-dir": node.is_dir }]),
|
|
2344
2711
|
onClick: ($event) => node.lock || node.is_dir ? toggleExpand(node) : download(node)
|
|
2345
|
-
}, toDisplayString(node.name), 11,
|
|
2346
|
-
node.is_dir && node.loaded ? (openBlock(), createElementBlock("span",
|
|
2712
|
+
}, toDisplayString(node.name), 11, _hoisted_55), createElementVNode("span", _hoisted_56, [!node.is_dir ? (openBlock(), createElementBlock(Fragment, { key: 0 }, [createTextVNode(toDisplayString(unref(formatSize)(node.size)) + " · " + toDisplayString(unref(formatDate)(node.modified)), 1)], 64)) : node.loaded ? (openBlock(), createElementBlock(Fragment, { key: 1 }, [createTextVNode(toDisplayString(t("folderItems", { count: statsOf(node).files })) + " · " + toDisplayString(unref(formatSize)(statsOf(node).bytes)), 1)], 64)) : createCommentVNode("v-if", true)])]),
|
|
2713
|
+
node.is_dir && node.loaded ? (openBlock(), createElementBlock("span", _hoisted_57, toDisplayString(t("folderItems", { count: statsOf(node).files })), 1)) : createCommentVNode("v-if", true),
|
|
2347
2714
|
node.lock?.prompting && node.lock.error ? (openBlock(), createElementBlock("span", {
|
|
2348
2715
|
key: 6,
|
|
2349
2716
|
id: `${unref(uid)}-error-${index}`,
|
|
2350
2717
|
class: "fl-unlock-message",
|
|
2351
2718
|
role: "alert"
|
|
2352
|
-
}, toDisplayString(unlockErrorText(node.lock.error)), 9,
|
|
2719
|
+
}, toDisplayString(unlockErrorText(node.lock.error)), 9, _hoisted_58)) : createCommentVNode("v-if", true),
|
|
2353
2720
|
!node.lock && unref(remembered).has(node.path) ? (openBlock(), createElementBlock("button", {
|
|
2354
2721
|
key: 7,
|
|
2355
2722
|
class: "fl-remembered",
|
|
@@ -2360,9 +2727,9 @@ const _sfc_main = /*@__PURE__*/ defineComponent({
|
|
|
2360
2727
|
}, [createVNode(_sfc_main$2, {
|
|
2361
2728
|
name: "key",
|
|
2362
2729
|
size: 11
|
|
2363
|
-
}), createTextVNode(" " + toDisplayString(t("remembered")) + " · " + toDisplayString(t("forgetPassword")), 1)], 8,
|
|
2364
|
-
node.loading ? (openBlock(), createElementBlock("span",
|
|
2365
|
-
], 8,
|
|
2730
|
+
}), createTextVNode(" " + toDisplayString(t("remembered")) + " · " + toDisplayString(t("forgetPassword")), 1)], 8, _hoisted_59)) : createCommentVNode("v-if", true),
|
|
2731
|
+
node.loading ? (openBlock(), createElementBlock("span", _hoisted_60, "…")) : createCommentVNode("v-if", true)
|
|
2732
|
+
], 8, _hoisted_48),
|
|
2366
2733
|
node.lock?.prompting ? (openBlock(), createElementBlock("form", {
|
|
2367
2734
|
key: 0,
|
|
2368
2735
|
class: "fl-unlock fl-unlock-row",
|
|
@@ -2383,7 +2750,7 @@ const _sfc_main = /*@__PURE__*/ defineComponent({
|
|
|
2383
2750
|
"aria-label": t("passwordFor", { name: node.name }),
|
|
2384
2751
|
"aria-invalid": !!node.lock.error,
|
|
2385
2752
|
"aria-describedby": node.lock.error ? `${unref(uid)}-error-${index}` : void 0
|
|
2386
|
-
}, null, 8,
|
|
2753
|
+
}, null, 8, _hoisted_62), [[vModelText, node.lock.input]]),
|
|
2387
2754
|
canRemember.value ? (openBlock(), createElementBlock("button", {
|
|
2388
2755
|
key: 0,
|
|
2389
2756
|
class: "fl-unlock-remember",
|
|
@@ -2392,12 +2759,12 @@ const _sfc_main = /*@__PURE__*/ defineComponent({
|
|
|
2392
2759
|
"aria-label": t("rememberPassword"),
|
|
2393
2760
|
title: t("rememberPassword"),
|
|
2394
2761
|
onClick: ($event) => node.lock.remember = !node.lock.remember
|
|
2395
|
-
}, [createVNode(_sfc_main$2, { name: "key" })], 8,
|
|
2762
|
+
}, [createVNode(_sfc_main$2, { name: "key" })], 8, _hoisted_63)) : createCommentVNode("v-if", true),
|
|
2396
2763
|
createElementVNode("button", {
|
|
2397
2764
|
class: "fl-unlock-submit",
|
|
2398
2765
|
type: "submit",
|
|
2399
2766
|
disabled: node.lock.busy || !node.lock.input
|
|
2400
|
-
}, toDisplayString(t("open")), 9,
|
|
2767
|
+
}, toDisplayString(t("open")), 9, _hoisted_64),
|
|
2401
2768
|
createElementVNode("button", {
|
|
2402
2769
|
class: "fl-unlock-cancel",
|
|
2403
2770
|
type: "button",
|
|
@@ -2407,11 +2774,11 @@ const _sfc_main = /*@__PURE__*/ defineComponent({
|
|
|
2407
2774
|
}, [createVNode(_sfc_main$2, {
|
|
2408
2775
|
name: "close",
|
|
2409
2776
|
size: 14
|
|
2410
|
-
})], 8,
|
|
2411
|
-
], 40,
|
|
2412
|
-
createElementVNode("span",
|
|
2413
|
-
createElementVNode("span",
|
|
2414
|
-
createElementVNode("span",
|
|
2777
|
+
})], 8, _hoisted_65)
|
|
2778
|
+
], 40, _hoisted_61)) : (openBlock(), createElementBlock(Fragment, { key: 1 }, [
|
|
2779
|
+
createElementVNode("span", _hoisted_66, toDisplayString(node.is_dir ? "—" : unref(formatSize)(node.size)), 1),
|
|
2780
|
+
createElementVNode("span", _hoisted_67, toDisplayString(unref(formatDate)(node.modified)), 1),
|
|
2781
|
+
createElementVNode("span", _hoisted_68, [node.lock ? (openBlock(), createElementBlock("button", {
|
|
2415
2782
|
key: 0,
|
|
2416
2783
|
class: "fl-action fl-arrow-end fl-lock",
|
|
2417
2784
|
type: "button",
|
|
@@ -2420,7 +2787,7 @@ const _sfc_main = /*@__PURE__*/ defineComponent({
|
|
|
2420
2787
|
}, [createVNode(_sfc_main$2, {
|
|
2421
2788
|
name: "lock",
|
|
2422
2789
|
size: 18
|
|
2423
|
-
})], 8,
|
|
2790
|
+
})], 8, _hoisted_69)) : node.is_dir ? (openBlock(), createElementBlock("button", {
|
|
2424
2791
|
key: 1,
|
|
2425
2792
|
class: normalizeClass(["fl-action fl-arrow-end", { "fl-arrow-open": node.expanded }]),
|
|
2426
2793
|
type: "button",
|
|
@@ -2430,25 +2797,42 @@ const _sfc_main = /*@__PURE__*/ defineComponent({
|
|
|
2430
2797
|
}, [createVNode(_sfc_main$2, {
|
|
2431
2798
|
name: "next",
|
|
2432
2799
|
size: 18
|
|
2433
|
-
})], 10,
|
|
2800
|
+
})], 10, _hoisted_70)) : (openBlock(), createElementBlock(Fragment, { key: 2 }, [canPreview(node) ? (openBlock(), createElementBlock("button", {
|
|
2434
2801
|
key: 0,
|
|
2435
2802
|
class: "fl-action fl-preview-btn",
|
|
2436
2803
|
type: "button",
|
|
2437
2804
|
"aria-label": `${t("preview")} ${node.name}`,
|
|
2438
2805
|
title: t("preview"),
|
|
2439
2806
|
onClick: ($event) => preview(node)
|
|
2440
|
-
}, [createVNode(_sfc_main$2, { name: "eye" })], 8,
|
|
2807
|
+
}, [createVNode(_sfc_main$2, { name: "eye" })], 8, _hoisted_71)) : createCommentVNode("v-if", true), createElementVNode("button", {
|
|
2441
2808
|
class: "fl-action fl-download",
|
|
2442
2809
|
type: "button",
|
|
2443
2810
|
"aria-label": `${t("download")} ${node.name}`,
|
|
2444
2811
|
title: t("download"),
|
|
2445
2812
|
onClick: ($event) => download(node)
|
|
2446
|
-
}, [createVNode(_sfc_main$2, { name: "download" })], 8,
|
|
2813
|
+
}, [createVNode(_sfc_main$2, { name: "download" })], 8, _hoisted_72)], 64))])
|
|
2447
2814
|
], 64))
|
|
2448
|
-
], 6);
|
|
2815
|
+
], 6))], 64);
|
|
2449
2816
|
}), 128)),
|
|
2450
|
-
createElementVNode("div",
|
|
2451
|
-
toast.value ? (openBlock(), createElementBlock("div",
|
|
2817
|
+
createElementVNode("div", _hoisted_73, [createElementVNode("span", null, toDisplayString(t("loaded", { count: allFiles.value.length })) + " · " + toDisplayString(t("totalSize", { size: unref(formatSize)(unref(totalSize)(allFiles.value)) })), 1)]),
|
|
2818
|
+
toast.value ? (openBlock(), createElementBlock("div", _hoisted_74, toDisplayString(toast.value), 1)) : createCommentVNode("v-if", true),
|
|
2819
|
+
createVNode(_sfc_main$3, {
|
|
2820
|
+
open: !!zipNotice.value,
|
|
2821
|
+
title: zipNotice.value ? t(zipNotice.value.kind === "warn" ? "zipWarnTitle" : "zipBlockTitle", { size: unref(formatSize)(zipNotice.value.size) }) : "",
|
|
2822
|
+
text: zipNotice.value ? t(zipNotice.value.kind === "warn" ? "zipWarnText" : "zipBlockText", { limit: unref(formatSize)(zipNotice.value.limit) }) : "",
|
|
2823
|
+
tip: zipTip.value,
|
|
2824
|
+
"confirm-label": zipNotice.value?.kind === "warn" ? t("zipContinue") : void 0,
|
|
2825
|
+
"cancel-label": zipNotice.value?.kind === "warn" ? t("cancel") : t("gotIt"),
|
|
2826
|
+
onConfirm: confirmZip,
|
|
2827
|
+
onClose: _cache[4] || (_cache[4] = ($event) => zipNotice.value = null)
|
|
2828
|
+
}, null, 8, [
|
|
2829
|
+
"open",
|
|
2830
|
+
"title",
|
|
2831
|
+
"text",
|
|
2832
|
+
"tip",
|
|
2833
|
+
"confirm-label",
|
|
2834
|
+
"cancel-label"
|
|
2835
|
+
]),
|
|
2452
2836
|
createVNode(_sfc_main$1, {
|
|
2453
2837
|
open: !!previewNode.value,
|
|
2454
2838
|
file: previewNode.value,
|
|
@@ -2461,9 +2845,9 @@ const _sfc_main = /*@__PURE__*/ defineComponent({
|
|
|
2461
2845
|
position: previewPosition.value,
|
|
2462
2846
|
total: previewPosition.value ? previewList.value.length : 0,
|
|
2463
2847
|
onClose: closePreview,
|
|
2464
|
-
onPrev: _cache[
|
|
2465
|
-
onNext: _cache[
|
|
2466
|
-
onDownload: _cache[
|
|
2848
|
+
onPrev: _cache[5] || (_cache[5] = ($event) => stepPreview(-1)),
|
|
2849
|
+
onNext: _cache[6] || (_cache[6] = ($event) => stepPreview(1)),
|
|
2850
|
+
onDownload: _cache[7] || (_cache[7] = ($event) => previewNode.value && download(previewNode.value))
|
|
2467
2851
|
}, null, 8, [
|
|
2468
2852
|
"open",
|
|
2469
2853
|
"file",
|