@xyne/workflow-ui 0.11.0 → 0.13.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/components/execution/ApprovalReviewDisplay.d.ts +28 -0
- package/dist/components/execution/ApprovalReviewDisplay.d.ts.map +1 -0
- package/dist/components/execution/ApprovalReviewDisplay.js +98 -0
- package/dist/components/execution/ApprovalReviewDisplay.js.map +1 -0
- package/dist/components/execution/ApprovalsView.js +3 -5
- package/dist/components/execution/ApprovalsView.js.map +1 -1
- package/dist/components/execution/PauseFormRenderer.d.ts +1 -1
- package/dist/components/execution/PauseFormRenderer.d.ts.map +1 -1
- package/dist/components/execution/PauseFormRenderer.js +20 -4
- package/dist/components/execution/PauseFormRenderer.js.map +1 -1
- package/dist/components/shared/AttachmentCard.d.ts +3 -2
- package/dist/components/shared/AttachmentCard.d.ts.map +1 -1
- package/dist/components/shared/AttachmentCard.js +22 -3
- package/dist/components/shared/AttachmentCard.js.map +1 -1
- package/dist/components/shared/DocumentViewer.d.ts +7 -0
- package/dist/components/shared/DocumentViewer.d.ts.map +1 -0
- package/dist/components/shared/DocumentViewer.js +71 -0
- package/dist/components/shared/DocumentViewer.js.map +1 -0
- package/dist/components/shared/MarkdownEditor.d.ts +24 -0
- package/dist/components/shared/MarkdownEditor.d.ts.map +1 -0
- package/dist/components/shared/MarkdownEditor.js +90 -0
- package/dist/components/shared/MarkdownEditor.js.map +1 -0
- package/dist/components/shared/viewers/CsvView.d.ts +4 -0
- package/dist/components/shared/viewers/CsvView.d.ts.map +1 -0
- package/dist/components/shared/viewers/CsvView.js +39 -0
- package/dist/components/shared/viewers/CsvView.js.map +1 -0
- package/dist/components/shared/viewers/DocxView.d.ts +4 -0
- package/dist/components/shared/viewers/DocxView.d.ts.map +1 -0
- package/dist/components/shared/viewers/DocxView.js +41 -0
- package/dist/components/shared/viewers/DocxView.js.map +1 -0
- package/dist/components/shared/viewers/ImageView.d.ts +5 -0
- package/dist/components/shared/viewers/ImageView.d.ts.map +1 -0
- package/dist/components/shared/viewers/ImageView.js +92 -0
- package/dist/components/shared/viewers/ImageView.js.map +1 -0
- package/dist/components/shared/viewers/SheetView.d.ts +4 -0
- package/dist/components/shared/viewers/SheetView.d.ts.map +1 -0
- package/dist/components/shared/viewers/SheetView.js +48 -0
- package/dist/components/shared/viewers/SheetView.js.map +1 -0
- package/dist/components/shared/viewers/TextView.d.ts +5 -0
- package/dist/components/shared/viewers/TextView.d.ts.map +1 -0
- package/dist/components/shared/viewers/TextView.js +45 -0
- package/dist/components/shared/viewers/TextView.js.map +1 -0
- package/dist/components/shared/viewers/chrome.d.ts +2 -0
- package/dist/components/shared/viewers/chrome.d.ts.map +1 -0
- package/dist/components/shared/viewers/chrome.js +7 -0
- package/dist/components/shared/viewers/chrome.js.map +1 -0
- package/dist/styles.css +1 -1
- package/package.json +11 -2
|
@@ -0,0 +1,71 @@
|
|
|
1
|
+
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
|
|
2
|
+
import { Component, lazy, Suspense } from 'react';
|
|
3
|
+
import { FileText } from 'lucide-react';
|
|
4
|
+
import { ViewerLoading } from './viewers/chrome.js';
|
|
5
|
+
import ImageView from './viewers/ImageView.js';
|
|
6
|
+
// Heavy renderers are code-split: their dependency (papaparse / SheetJS /
|
|
7
|
+
// docx-preview) only loads when a file of that type is actually opened.
|
|
8
|
+
const CsvView = lazy(() => import('./viewers/CsvView.js'));
|
|
9
|
+
const SheetView = lazy(() => import('./viewers/SheetView.js'));
|
|
10
|
+
const DocxView = lazy(() => import('./viewers/DocxView.js'));
|
|
11
|
+
const TextView = lazy(() => import('./viewers/TextView.js'));
|
|
12
|
+
// Resolve a renderer kind from the MIME type, falling back to the file
|
|
13
|
+
// extension (extraction/upload sources aren't always reliable about MIME).
|
|
14
|
+
function kindOf(mimeType, name) {
|
|
15
|
+
const m = (mimeType || '').toLowerCase();
|
|
16
|
+
const ext = (name.split('.').pop() ?? '').toLowerCase();
|
|
17
|
+
if (m === 'application/pdf' || ext === 'pdf')
|
|
18
|
+
return 'pdf';
|
|
19
|
+
if (m.startsWith('image/'))
|
|
20
|
+
return 'image';
|
|
21
|
+
if (m === 'text/markdown' || ext === 'md' || ext === 'markdown')
|
|
22
|
+
return 'markdown';
|
|
23
|
+
if (m === 'application/json' || ext === 'json')
|
|
24
|
+
return 'json';
|
|
25
|
+
if (m === 'text/csv' || ext === 'csv' || ext === 'tsv')
|
|
26
|
+
return 'csv';
|
|
27
|
+
if (ext === 'docx' ||
|
|
28
|
+
m === 'application/vnd.openxmlformats-officedocument.wordprocessingml.document')
|
|
29
|
+
return 'docx';
|
|
30
|
+
if (ext === 'xlsx' ||
|
|
31
|
+
ext === 'xls' ||
|
|
32
|
+
m.includes('spreadsheetml') ||
|
|
33
|
+
m === 'application/vnd.ms-excel')
|
|
34
|
+
return 'sheet';
|
|
35
|
+
if (m.startsWith('text/') || ext === 'txt' || ext === 'log')
|
|
36
|
+
return 'text';
|
|
37
|
+
return 'unsupported';
|
|
38
|
+
}
|
|
39
|
+
// Generic, themeable document preview. Renders PDF (native iframe, #page
|
|
40
|
+
// deep-link) and images inline; lazy-loads CSV / XLSX / DOCX / text / json /
|
|
41
|
+
// markdown renderers; everything else (and any renderer failure) degrades to a
|
|
42
|
+
// download link. `url` is the raw same-origin attachment URL (cookie auth).
|
|
43
|
+
export function DocumentViewer({ url, mimeType, name, page, }) {
|
|
44
|
+
const kind = kindOf(mimeType, name);
|
|
45
|
+
if (kind === 'pdf') {
|
|
46
|
+
return (_jsx("iframe", { src: `${url}${page ? `#page=${String(page)}` : ''}`, title: name, className: "h-[72vh] w-full border-0" }));
|
|
47
|
+
}
|
|
48
|
+
if (kind === 'image') {
|
|
49
|
+
return _jsx(ImageView, { url: url, name: name });
|
|
50
|
+
}
|
|
51
|
+
const view = kind === 'csv' ? (_jsx(CsvView, { url: url })) : kind === 'sheet' ? (_jsx(SheetView, { url: url })) : kind === 'docx' ? (_jsx(DocxView, { url: url })) : kind === 'markdown' ? (_jsx(TextView, { url: url, mode: "markdown" })) : kind === 'json' ? (_jsx(TextView, { url: url, mode: "json" })) : kind === 'text' ? (_jsx(TextView, { url: url, mode: "text" })) : null;
|
|
52
|
+
if (!view)
|
|
53
|
+
return _jsx(DownloadFallback, { url: url, name: name });
|
|
54
|
+
return (_jsx(ViewerBoundary, { fallback: _jsx(DownloadFallback, { url: url, name: name }), children: _jsx(Suspense, { fallback: _jsx(ViewerLoading, {}), children: view }) }, `${kind}:${url}`));
|
|
55
|
+
}
|
|
56
|
+
function DownloadFallback({ url, name }) {
|
|
57
|
+
return (_jsx("div", { className: "grid min-h-[30vh] place-items-center p-8 text-center", children: _jsxs("div", { className: "flex flex-col items-center gap-3 text-[var(--wui-fg-muted)]", children: [_jsx(FileText, { className: "size-8" }), _jsx("p", { className: "text-[13px]", children: "No inline preview for this file type." }), _jsxs("a", { href: url, download: name, className: "rounded-lg bg-[var(--wui-primary)] px-4 py-2 text-[13px] font-semibold text-[var(--wui-primary-fg)] transition-opacity hover:opacity-90", children: ["Download ", name] })] }) }));
|
|
58
|
+
}
|
|
59
|
+
// Catches both lazy-chunk load failures (e.g. a missing optional dep) and
|
|
60
|
+
// in-viewer parse/fetch errors (viewers throw during render on failure) →
|
|
61
|
+
// shows the download fallback instead of a blank/broken pane.
|
|
62
|
+
class ViewerBoundary extends Component {
|
|
63
|
+
state = { failed: false };
|
|
64
|
+
static getDerivedStateFromError() {
|
|
65
|
+
return { failed: true };
|
|
66
|
+
}
|
|
67
|
+
render() {
|
|
68
|
+
return this.state.failed ? this.props.fallback : this.props.children;
|
|
69
|
+
}
|
|
70
|
+
}
|
|
71
|
+
//# sourceMappingURL=DocumentViewer.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"DocumentViewer.js","sourceRoot":"","sources":["../../../src/components/shared/DocumentViewer.tsx"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
export interface MarkdownEditorProps {
|
|
2
|
+
/** Current value as a markdown string. */
|
|
3
|
+
value: string;
|
|
4
|
+
/** Called with the new markdown string on every edit. */
|
|
5
|
+
onChange: (markdown: string) => void;
|
|
6
|
+
disabled?: boolean | undefined;
|
|
7
|
+
className?: string | undefined;
|
|
8
|
+
/** Drop the outer border/background so it sits flush inside a card body. */
|
|
9
|
+
bare?: boolean | undefined;
|
|
10
|
+
}
|
|
11
|
+
/**
|
|
12
|
+
* WYSIWYG markdown editor for runtime reviewer input (approval-form text fields).
|
|
13
|
+
* You edit the rendered view directly; the stored value is markdown, so it
|
|
14
|
+
* renders identically via {@link MarkdownView} wherever it's shown later.
|
|
15
|
+
*
|
|
16
|
+
* Formatting parity with the renderer: headings, bold, italic, strikethrough,
|
|
17
|
+
* lists, links, inline code, code block, quote, divider. (Tables/images still
|
|
18
|
+
* render if present in the value, but aren't authored here.)
|
|
19
|
+
*
|
|
20
|
+
* Builder/config fields deliberately do NOT use this — those carry typed values
|
|
21
|
+
* and `{{variable}}` refs that markdown would mangle.
|
|
22
|
+
*/
|
|
23
|
+
export declare function MarkdownEditor({ value, onChange, disabled, className, bare }: MarkdownEditorProps): import("react").JSX.Element;
|
|
24
|
+
//# sourceMappingURL=MarkdownEditor.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"MarkdownEditor.d.ts","sourceRoot":"","sources":["../../../src/components/shared/MarkdownEditor.tsx"],"names":[],"mappings":"AAOA,MAAM,WAAW,mBAAmB;IAClC,0CAA0C;IAC1C,KAAK,EAAE,MAAM,CAAC;IACd,yDAAyD;IACzD,QAAQ,EAAE,CAAC,QAAQ,EAAE,MAAM,KAAK,IAAI,CAAC;IACrC,QAAQ,CAAC,EAAE,OAAO,GAAG,SAAS,CAAC;IAC/B,SAAS,CAAC,EAAE,MAAM,GAAG,SAAS,CAAC;IAC/B,4EAA4E;IAC5E,IAAI,CAAC,EAAE,OAAO,GAAG,SAAS,CAAC;CAC5B;AAED;;;;;;;;;;;GAWG;AACH,wBAAgB,cAAc,CAAC,EAAE,KAAK,EAAE,QAAQ,EAAE,QAAQ,EAAE,SAAS,EAAE,IAAI,EAAE,EAAE,mBAAmB,+BAwDjG"}
|
|
@@ -0,0 +1,90 @@
|
|
|
1
|
+
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
|
|
2
|
+
import { useEffect } from 'react';
|
|
3
|
+
import { useEditor, EditorContent } from '@tiptap/react';
|
|
4
|
+
import StarterKit from '@tiptap/starter-kit';
|
|
5
|
+
import Link from '@tiptap/extension-link';
|
|
6
|
+
import { Markdown } from 'tiptap-markdown';
|
|
7
|
+
import { cn } from './cn.js';
|
|
8
|
+
/**
|
|
9
|
+
* WYSIWYG markdown editor for runtime reviewer input (approval-form text fields).
|
|
10
|
+
* You edit the rendered view directly; the stored value is markdown, so it
|
|
11
|
+
* renders identically via {@link MarkdownView} wherever it's shown later.
|
|
12
|
+
*
|
|
13
|
+
* Formatting parity with the renderer: headings, bold, italic, strikethrough,
|
|
14
|
+
* lists, links, inline code, code block, quote, divider. (Tables/images still
|
|
15
|
+
* render if present in the value, but aren't authored here.)
|
|
16
|
+
*
|
|
17
|
+
* Builder/config fields deliberately do NOT use this — those carry typed values
|
|
18
|
+
* and `{{variable}}` refs that markdown would mangle.
|
|
19
|
+
*/
|
|
20
|
+
export function MarkdownEditor({ value, onChange, disabled, className, bare }) {
|
|
21
|
+
const editor = useEditor({
|
|
22
|
+
extensions: [
|
|
23
|
+
StarterKit.configure({ heading: { levels: [1, 2, 3] } }),
|
|
24
|
+
Link.configure({ openOnClick: false, autolink: true, linkOnPaste: true }),
|
|
25
|
+
Markdown.configure({ html: false, linkify: true, breaks: true, transformPastedText: true }),
|
|
26
|
+
],
|
|
27
|
+
content: value || '',
|
|
28
|
+
editable: !disabled,
|
|
29
|
+
onUpdate: ({ editor }) => {
|
|
30
|
+
const md = editor.storage.markdown?.getMarkdown() ?? '';
|
|
31
|
+
onChange(md);
|
|
32
|
+
},
|
|
33
|
+
editorProps: {
|
|
34
|
+
attributes: { class: 'min-h-[2.5rem] max-h-40 overflow-y-auto px-2.5 py-2 outline-none' },
|
|
35
|
+
},
|
|
36
|
+
});
|
|
37
|
+
// Sync external value changes (e.g. AI form-fill) without clobbering the
|
|
38
|
+
// user's caret while they type — only when the value truly differs.
|
|
39
|
+
useEffect(() => {
|
|
40
|
+
if (!editor)
|
|
41
|
+
return;
|
|
42
|
+
const current = editor.storage.markdown?.getMarkdown() ?? '';
|
|
43
|
+
if (value !== current)
|
|
44
|
+
editor.commands.setContent(value || '', false);
|
|
45
|
+
}, [value, editor]);
|
|
46
|
+
useEffect(() => {
|
|
47
|
+
editor?.setEditable(!disabled);
|
|
48
|
+
}, [disabled, editor]);
|
|
49
|
+
return (_jsxs("div", { className: cn(!bare && 'rounded-[var(--wui-radius-sm)] border border-[var(--wui-border)] bg-[var(--wui-bg)] focus-within:border-[var(--wui-primary)] focus-within:ring-1 focus-within:ring-[var(--wui-primary)]', disabled && 'opacity-60',
|
|
50
|
+
// WYSIWYG content styling — mirrors MarkdownView so editing matches the render.
|
|
51
|
+
'text-[13px] text-[var(--wui-fg)]', '[&_.ProseMirror]:leading-relaxed', '[&_h1]:text-base [&_h1]:font-bold [&_h1]:my-2', '[&_h2]:text-sm [&_h2]:font-bold [&_h2]:my-1.5', '[&_h3]:text-[13px] [&_h3]:font-bold [&_h3]:my-1', '[&_p]:my-1.5', '[&_ul]:my-1.5 [&_ul]:list-disc [&_ul]:pl-5', '[&_ol]:my-1.5 [&_ol]:list-decimal [&_ol]:pl-5', '[&_blockquote]:border-l-2 [&_blockquote]:border-slate-300 [&_blockquote]:pl-3 [&_blockquote]:italic [&_blockquote]:text-slate-500', '[&_code]:rounded [&_code]:bg-slate-100 [&_code]:px-1 [&_code]:py-0.5 [&_code]:font-mono [&_code]:text-[12px]', '[&_pre]:my-2 [&_pre]:rounded-md [&_pre]:bg-slate-900 [&_pre]:p-3 [&_pre]:text-[12px] [&_pre]:text-slate-100 [&_pre_code]:bg-transparent [&_pre_code]:p-0 [&_pre_code]:text-inherit', '[&_hr]:my-3 [&_hr]:border-[var(--wui-border)]', '[&_a]:text-indigo-600 [&_a]:underline', className), children: [_jsx(MarkdownToolbar, { editor: editor, disabled: disabled }), _jsx(EditorContent, { editor: editor })] }));
|
|
52
|
+
}
|
|
53
|
+
const ICON = { width: 15, height: 15, viewBox: '0 0 24 24', fill: 'none', stroke: 'currentColor', strokeWidth: 2, strokeLinecap: 'round', strokeLinejoin: 'round' };
|
|
54
|
+
function headingValue(editor) {
|
|
55
|
+
if (editor.isActive('heading', { level: 1 }))
|
|
56
|
+
return 'h1';
|
|
57
|
+
if (editor.isActive('heading', { level: 2 }))
|
|
58
|
+
return 'h2';
|
|
59
|
+
if (editor.isActive('heading', { level: 3 }))
|
|
60
|
+
return 'h3';
|
|
61
|
+
return 'p';
|
|
62
|
+
}
|
|
63
|
+
function MarkdownToolbar({ editor, disabled }) {
|
|
64
|
+
if (!editor)
|
|
65
|
+
return null;
|
|
66
|
+
const Item = ({ on, active, title, children }) => (_jsx("button", { type: "button", disabled: disabled, title: title, "aria-label": title, onMouseDown: (e) => { e.preventDefault(); on(); }, className: cn('grid h-7 w-7 place-items-center rounded transition-colors', active
|
|
67
|
+
? 'bg-[var(--wui-primary)]/15 text-[var(--wui-primary)]'
|
|
68
|
+
: 'text-[var(--wui-fg-muted)] hover:bg-[var(--wui-bg-subtle)] hover:text-[var(--wui-fg)]'), children: children }));
|
|
69
|
+
const Divider = () => _jsx("span", { className: "mx-0.5 h-4 w-px bg-[var(--wui-border)]" });
|
|
70
|
+
const setLink = () => {
|
|
71
|
+
const prev = editor.getAttributes('link')['href'] ?? '';
|
|
72
|
+
const url = window.prompt('Link URL', prev);
|
|
73
|
+
if (url === null)
|
|
74
|
+
return;
|
|
75
|
+
const chain = editor.chain().focus().extendMarkRange('link');
|
|
76
|
+
if (url === '')
|
|
77
|
+
chain.unsetLink().run();
|
|
78
|
+
else
|
|
79
|
+
chain.setLink({ href: url }).run();
|
|
80
|
+
};
|
|
81
|
+
return (_jsxs("div", { className: "flex flex-wrap items-center gap-0.5 border-b border-[var(--wui-border)] px-1.5 py-1", children: [_jsxs("select", { value: headingValue(editor), disabled: disabled, onChange: (e) => {
|
|
82
|
+
const v = e.target.value;
|
|
83
|
+
const c = editor.chain().focus();
|
|
84
|
+
if (v === 'p')
|
|
85
|
+
c.setParagraph().run();
|
|
86
|
+
else
|
|
87
|
+
c.setHeading({ level: Number(v.slice(1)) }).run();
|
|
88
|
+
}, title: "Text style", className: "mr-0.5 h-7 rounded border border-[var(--wui-border)] bg-[var(--wui-bg)] px-1.5 text-[11px] text-[var(--wui-fg)] outline-none", children: [_jsx("option", { value: "p", children: "Normal" }), _jsx("option", { value: "h1", children: "Heading 1" }), _jsx("option", { value: "h2", children: "Heading 2" }), _jsx("option", { value: "h3", children: "Heading 3" })] }), _jsx(Divider, {}), _jsx(Item, { on: () => editor.chain().focus().toggleBold().run(), active: editor.isActive('bold'), title: "Bold", children: _jsx("span", { className: "text-[13px] font-bold leading-none", children: "B" }) }), _jsx(Item, { on: () => editor.chain().focus().toggleItalic().run(), active: editor.isActive('italic'), title: "Italic", children: _jsx("span", { className: "text-[13px] italic leading-none", style: { fontFamily: 'Georgia, serif' }, children: "I" }) }), _jsx(Item, { on: () => editor.chain().focus().toggleStrike().run(), active: editor.isActive('strike'), title: "Strikethrough", children: _jsx("span", { className: "text-[13px] leading-none line-through", children: "S" }) }), _jsx(Divider, {}), _jsx(Item, { on: () => editor.chain().focus().toggleBulletList().run(), active: editor.isActive('bulletList'), title: "Bulleted list", children: _jsxs("svg", { ...ICON, children: [_jsx("line", { x1: "9", y1: "6", x2: "20", y2: "6" }), _jsx("line", { x1: "9", y1: "12", x2: "20", y2: "12" }), _jsx("line", { x1: "9", y1: "18", x2: "20", y2: "18" }), _jsx("circle", { cx: "4.5", cy: "6", r: "1.2", fill: "currentColor", stroke: "none" }), _jsx("circle", { cx: "4.5", cy: "12", r: "1.2", fill: "currentColor", stroke: "none" }), _jsx("circle", { cx: "4.5", cy: "18", r: "1.2", fill: "currentColor", stroke: "none" })] }) }), _jsx(Item, { on: () => editor.chain().focus().toggleOrderedList().run(), active: editor.isActive('orderedList'), title: "Numbered list", children: _jsxs("svg", { ...ICON, children: [_jsx("line", { x1: "10", y1: "6", x2: "20", y2: "6" }), _jsx("line", { x1: "10", y1: "12", x2: "20", y2: "12" }), _jsx("line", { x1: "10", y1: "18", x2: "20", y2: "18" }), _jsx("path", { d: "M4 4.5h1V8", strokeWidth: "1.6" }), _jsx("path", { d: "M3.6 14.2c0-.6.5-1 1-1s1 .4 1 .9c0 .9-1.6 1.2-1.9 2.4H5.8", strokeWidth: "1.6" })] }) }), _jsx(Divider, {}), _jsx(Item, { on: setLink, active: editor.isActive('link'), title: "Link", children: _jsxs("svg", { ...ICON, children: [_jsx("path", { d: "M10 13a5 5 0 0 0 7.54.54l3-3a5 5 0 0 0-7.07-7.07l-1.72 1.71" }), _jsx("path", { d: "M14 11a5 5 0 0 0-7.54-.54l-3 3a5 5 0 0 0 7.07 7.07l1.71-1.71" })] }) }), _jsx(Item, { on: () => editor.chain().focus().toggleCode().run(), active: editor.isActive('code'), title: "Inline code", children: _jsxs("svg", { ...ICON, children: [_jsx("polyline", { points: "16 18 22 12 16 6" }), _jsx("polyline", { points: "8 6 2 12 8 18" })] }) }), _jsx(Item, { on: () => editor.chain().focus().toggleCodeBlock().run(), active: editor.isActive('codeBlock'), title: "Code block", children: _jsxs("svg", { ...ICON, children: [_jsx("rect", { x: "3", y: "4", width: "18", height: "16", rx: "2" }), _jsx("polyline", { points: "9 9.5 7.5 12 9 14.5" }), _jsx("polyline", { points: "15 9.5 16.5 12 15 14.5" })] }) }), _jsx(Divider, {}), _jsx(Item, { on: () => editor.chain().focus().toggleBlockquote().run(), active: editor.isActive('blockquote'), title: "Quote", children: _jsx("svg", { ...ICON, children: _jsx("path", { d: "M7 7H4v6h3l-1 4M17 7h-3v6h3l-1 4" }) }) }), _jsx(Item, { on: () => editor.chain().focus().setHorizontalRule().run(), title: "Divider", children: _jsx("svg", { ...ICON, children: _jsx("line", { x1: "4", y1: "12", x2: "20", y2: "12" }) }) })] }));
|
|
89
|
+
}
|
|
90
|
+
//# sourceMappingURL=MarkdownEditor.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"MarkdownEditor.js","sourceRoot":"","sources":["../../../src/components/shared/MarkdownEditor.tsx"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"CsvView.d.ts","sourceRoot":"","sources":["../../../../src/components/shared/viewers/CsvView.tsx"],"names":[],"mappings":"AAOA,MAAM,CAAC,OAAO,UAAU,OAAO,CAAC,EAAE,GAAG,EAAE,EAAE;IAAE,GAAG,EAAE,MAAM,CAAA;CAAE,+BAkDvD"}
|
|
@@ -0,0 +1,39 @@
|
|
|
1
|
+
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
|
|
2
|
+
import { useEffect, useState } from 'react';
|
|
3
|
+
import Papa from 'papaparse';
|
|
4
|
+
import { ViewerLoading } from './chrome.js';
|
|
5
|
+
const MAX_ROWS = 1000;
|
|
6
|
+
// CSV/TSV renderer — parses with papaparse and renders a themed table.
|
|
7
|
+
export default function CsvView({ url }) {
|
|
8
|
+
const [rows, setRows] = useState(null);
|
|
9
|
+
const [failed, setFailed] = useState(false);
|
|
10
|
+
useEffect(() => {
|
|
11
|
+
let cancelled = false;
|
|
12
|
+
setRows(null);
|
|
13
|
+
setFailed(false);
|
|
14
|
+
void fetch(url)
|
|
15
|
+
.then((r) => {
|
|
16
|
+
if (!r.ok)
|
|
17
|
+
throw new Error(String(r.status));
|
|
18
|
+
return r.text();
|
|
19
|
+
})
|
|
20
|
+
.then((t) => {
|
|
21
|
+
const res = Papa.parse(t, { skipEmptyLines: true });
|
|
22
|
+
if (!cancelled)
|
|
23
|
+
setRows(res.data);
|
|
24
|
+
})
|
|
25
|
+
.catch(() => { if (!cancelled)
|
|
26
|
+
setFailed(true); });
|
|
27
|
+
return () => { cancelled = true; };
|
|
28
|
+
}, [url]);
|
|
29
|
+
if (failed)
|
|
30
|
+
throw new Error('csv load failed');
|
|
31
|
+
if (rows === null)
|
|
32
|
+
return _jsx(ViewerLoading, {});
|
|
33
|
+
const [head, ...body] = rows;
|
|
34
|
+
const capped = body.slice(0, MAX_ROWS);
|
|
35
|
+
const th = 'sticky top-0 border border-[var(--wui-border)] bg-[var(--wui-bg-subtle)] px-2.5 py-1.5 text-left font-semibold text-[var(--wui-fg)]';
|
|
36
|
+
const td = 'border border-[var(--wui-border)] px-2.5 py-1.5 align-top text-[var(--wui-fg-muted)]';
|
|
37
|
+
return (_jsxs("div", { className: "overflow-auto px-5 py-4", children: [_jsxs("table", { className: "w-full border-collapse text-[12.5px] tabular-nums", children: [head && (_jsx("thead", { children: _jsx("tr", { children: head.map((c, i) => _jsx("th", { className: th, children: c }, i)) }) })), _jsx("tbody", { children: capped.map((row, ri) => (_jsx("tr", { children: row.map((c, ci) => _jsx("td", { className: td, children: c }, ci)) }, ri))) })] }), body.length > capped.length && (_jsxs("p", { className: "mt-2 text-[12px] text-[var(--wui-fg-muted)]", children: ["Showing first ", String(capped.length), " of ", String(body.length), " rows."] }))] }));
|
|
38
|
+
}
|
|
39
|
+
//# sourceMappingURL=CsvView.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"CsvView.js","sourceRoot":"","sources":["../../../../src/components/shared/viewers/CsvView.tsx"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"DocxView.d.ts","sourceRoot":"","sources":["../../../../src/components/shared/viewers/DocxView.tsx"],"names":[],"mappings":"AAOA,MAAM,CAAC,OAAO,UAAU,QAAQ,CAAC,EAAE,GAAG,EAAE,EAAE;IAAE,GAAG,EAAE,MAAM,CAAA;CAAE,+BAsCxD"}
|
|
@@ -0,0 +1,41 @@
|
|
|
1
|
+
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
|
|
2
|
+
import { useEffect, useRef, useState } from 'react';
|
|
3
|
+
import { renderAsync } from 'docx-preview';
|
|
4
|
+
import { ViewerLoading } from './chrome.js';
|
|
5
|
+
// DOCX renderer — docx-preview parses the file into a styled DOM mounted into a
|
|
6
|
+
// ref'd container (it needs a real mounted node, so render the container always
|
|
7
|
+
// and overlay the spinner while it works).
|
|
8
|
+
export default function DocxView({ url }) {
|
|
9
|
+
const ref = useRef(null);
|
|
10
|
+
const [loading, setLoading] = useState(true);
|
|
11
|
+
const [failed, setFailed] = useState(false);
|
|
12
|
+
useEffect(() => {
|
|
13
|
+
let cancelled = false;
|
|
14
|
+
setLoading(true);
|
|
15
|
+
setFailed(false);
|
|
16
|
+
void fetch(url)
|
|
17
|
+
.then((r) => {
|
|
18
|
+
if (!r.ok)
|
|
19
|
+
throw new Error(String(r.status));
|
|
20
|
+
return r.blob();
|
|
21
|
+
})
|
|
22
|
+
.then(async (blob) => {
|
|
23
|
+
if (cancelled || !ref.current)
|
|
24
|
+
return;
|
|
25
|
+
await renderAsync(blob, ref.current, undefined, {
|
|
26
|
+
className: 'wui-docx',
|
|
27
|
+
inWrapper: true,
|
|
28
|
+
ignoreWidth: true,
|
|
29
|
+
});
|
|
30
|
+
if (!cancelled)
|
|
31
|
+
setLoading(false);
|
|
32
|
+
})
|
|
33
|
+
.catch(() => { if (!cancelled)
|
|
34
|
+
setFailed(true); });
|
|
35
|
+
return () => { cancelled = true; };
|
|
36
|
+
}, [url]);
|
|
37
|
+
if (failed)
|
|
38
|
+
throw new Error('docx load failed');
|
|
39
|
+
return (_jsxs("div", { className: "px-5 py-4", children: [loading && _jsx(ViewerLoading, {}), _jsx("div", { ref: ref, className: "[&_.wui-docx]:!w-full [&_.wui-docx_section]:!w-full [&_.wui-docx_section]:!max-w-none [&_.wui-docx_section]:!p-0" })] }));
|
|
40
|
+
}
|
|
41
|
+
//# sourceMappingURL=DocxView.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"DocxView.js","sourceRoot":"","sources":["../../../../src/components/shared/viewers/DocxView.tsx"],"names":[],"mappings":";AAAA,OAAO,EAAE,SAAS,EAAE,MAAM,EAAE,QAAQ,EAAE,MAAM,OAAO,CAAC;AACpD,OAAO,EAAE,WAAW,EAAE,MAAM,cAAc,CAAC;AAC3C,OAAO,EAAE,aAAa,EAAE,MAAM,aAAa,CAAC;AAE5C,gFAAgF;AAChF,gFAAgF;AAChF,2CAA2C;AAC3C,MAAM,CAAC,OAAO,UAAU,QAAQ,CAAC,EAAE,GAAG,EAAmB;IACvD,MAAM,GAAG,GAAG,MAAM,CAAiB,IAAI,CAAC,CAAC;IACzC,MAAM,CAAC,OAAO,EAAE,UAAU,CAAC,GAAG,QAAQ,CAAC,IAAI,CAAC,CAAC;IAC7C,MAAM,CAAC,MAAM,EAAE,SAAS,CAAC,GAAG,QAAQ,CAAC,KAAK,CAAC,CAAC;IAE5C,SAAS,CAAC,GAAG,EAAE;QACb,IAAI,SAAS,GAAG,KAAK,CAAC;QACtB,UAAU,CAAC,IAAI,CAAC,CAAC;QACjB,SAAS,CAAC,KAAK,CAAC,CAAC;QACjB,KAAK,KAAK,CAAC,GAAG,CAAC;aACZ,IAAI,CAAC,CAAC,CAAC,EAAE,EAAE;YACV,IAAI,CAAC,CAAC,CAAC,EAAE;gBAAE,MAAM,IAAI,KAAK,CAAC,MAAM,CAAC,CAAC,CAAC,MAAM,CAAC,CAAC,CAAC;YAC7C,OAAO,CAAC,CAAC,IAAI,EAAE,CAAC;QAClB,CAAC,CAAC;aACD,IAAI,CAAC,KAAK,EAAE,IAAI,EAAE,EAAE;YACnB,IAAI,SAAS,IAAI,CAAC,GAAG,CAAC,OAAO;gBAAE,OAAO;YACtC,MAAM,WAAW,CAAC,IAAI,EAAE,GAAG,CAAC,OAAO,EAAE,SAAS,EAAE;gBAC9C,SAAS,EAAE,UAAU;gBACrB,SAAS,EAAE,IAAI;gBACf,WAAW,EAAE,IAAI;aAClB,CAAC,CAAC;YACH,IAAI,CAAC,SAAS;gBAAE,UAAU,CAAC,KAAK,CAAC,CAAC;QACpC,CAAC,CAAC;aACD,KAAK,CAAC,GAAG,EAAE,GAAG,IAAI,CAAC,SAAS;YAAE,SAAS,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;QACrD,OAAO,GAAG,EAAE,GAAG,SAAS,GAAG,IAAI,CAAC,CAAC,CAAC,CAAC;IACrC,CAAC,EAAE,CAAC,GAAG,CAAC,CAAC,CAAC;IAEV,IAAI,MAAM;QAAE,MAAM,IAAI,KAAK,CAAC,kBAAkB,CAAC,CAAC;IAEhD,OAAO,CACL,eAAK,SAAS,EAAC,WAAW,aACvB,OAAO,IAAI,KAAC,aAAa,KAAG,EAC7B,cACE,GAAG,EAAE,GAAG,EACR,SAAS,EAAC,kHAAkH,GAC5H,IACE,CACP,CAAC;AACJ,CAAC"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"ImageView.d.ts","sourceRoot":"","sources":["../../../../src/components/shared/viewers/ImageView.tsx"],"names":[],"mappings":"AAYA,MAAM,CAAC,OAAO,UAAU,SAAS,CAAC,EAAE,GAAG,EAAE,IAAI,EAAE,EAAE;IAAE,GAAG,EAAE,MAAM,CAAC;IAAC,IAAI,EAAE,MAAM,CAAA;CAAE,+BA6H7E"}
|
|
@@ -0,0 +1,92 @@
|
|
|
1
|
+
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
|
|
2
|
+
import { useEffect, useLayoutEffect, useRef, useState } from 'react';
|
|
3
|
+
import { RotateCcw, RotateCw, ZoomIn, ZoomOut, Maximize2, ExternalLink, Download } from 'lucide-react';
|
|
4
|
+
const MIN_ZOOM = 0.1;
|
|
5
|
+
const MAX_ZOOM = 8;
|
|
6
|
+
const clampZoom = (z) => Math.min(MAX_ZOOM, Math.max(MIN_ZOOM, Math.round(z * 100) / 100));
|
|
7
|
+
// Inline image preview. Zoom is applied as real layout size (fit-to-view × zoom)
|
|
8
|
+
// inside an overflow-auto container, so a zoomed image gets native scrollbars +
|
|
9
|
+
// wheel-scroll + grab-to-pan — not just a CSS transform. Rotation (90° steps)
|
|
10
|
+
// swaps the bounding box so scrolling stays correct. Plus a typeable zoom %,
|
|
11
|
+
// fit-to-view, open-in-new-tab and download. Original bytes are never re-encoded.
|
|
12
|
+
export default function ImageView({ url, name }) {
|
|
13
|
+
const [deg, setDeg] = useState(0);
|
|
14
|
+
const [zoom, setZoom] = useState(1);
|
|
15
|
+
const [zoomText, setZoomText] = useState('100');
|
|
16
|
+
const [nat, setNat] = useState(null);
|
|
17
|
+
const [box, setBox] = useState(null);
|
|
18
|
+
const [panning, setPanning] = useState(false);
|
|
19
|
+
const scrollRef = useRef(null);
|
|
20
|
+
const pan = useRef(null);
|
|
21
|
+
// Track the scroll viewport's size so "fit" is always relative to it.
|
|
22
|
+
useLayoutEffect(() => {
|
|
23
|
+
const el = scrollRef.current;
|
|
24
|
+
if (!el)
|
|
25
|
+
return;
|
|
26
|
+
const measure = () => { setBox({ w: el.clientWidth, h: el.clientHeight }); };
|
|
27
|
+
measure();
|
|
28
|
+
const ro = new ResizeObserver(measure);
|
|
29
|
+
ro.observe(el);
|
|
30
|
+
return () => { ro.disconnect(); };
|
|
31
|
+
}, []);
|
|
32
|
+
useEffect(() => { setZoomText(String(Math.round(zoom * 100))); }, [zoom]);
|
|
33
|
+
const rotated = deg === 90 || deg === 270;
|
|
34
|
+
const ready = !!(nat && box && box.w > 0 && box.h > 0);
|
|
35
|
+
const fitScale = ready ? Math.min(box.w / nat.w, box.h / nat.h) : 1;
|
|
36
|
+
const imgW = nat ? nat.w * fitScale * zoom : 0; // image's own (unrotated) display size
|
|
37
|
+
const imgH = nat ? nat.h * fitScale * zoom : 0;
|
|
38
|
+
const boxW = rotated ? imgH : imgW; // rotated bounding box = the scroll area
|
|
39
|
+
const boxH = rotated ? imgW : imgH;
|
|
40
|
+
const canPan = ready && !!box && (boxW > box.w + 1 || boxH > box.h + 1);
|
|
41
|
+
const applyZoom = (z) => { setZoom(clampZoom(z)); };
|
|
42
|
+
const rotate = (d) => { setDeg((v) => (v + d + 360) % 360); };
|
|
43
|
+
// Fit the CURRENT orientation's bounding box to the viewport (only on demand).
|
|
44
|
+
const fit = () => {
|
|
45
|
+
if (!ready) {
|
|
46
|
+
setZoom(1);
|
|
47
|
+
return;
|
|
48
|
+
}
|
|
49
|
+
const baseW = rotated ? nat.h : nat.w; // bbox dims at zoom 1, in screen space
|
|
50
|
+
const baseH = rotated ? nat.w : nat.h;
|
|
51
|
+
setZoom(clampZoom(Math.min(box.w / (baseW * fitScale), box.h / (baseH * fitScale))));
|
|
52
|
+
};
|
|
53
|
+
const commitText = () => {
|
|
54
|
+
const n = Number.parseFloat(zoomText);
|
|
55
|
+
if (Number.isFinite(n) && n > 0)
|
|
56
|
+
applyZoom(n / 100);
|
|
57
|
+
else
|
|
58
|
+
setZoomText(String(Math.round(zoom * 100)));
|
|
59
|
+
};
|
|
60
|
+
return (_jsxs("div", { className: "flex h-[72vh] flex-col", children: [_jsxs("div", { className: "flex shrink-0 flex-wrap items-center justify-center gap-0.5 border-b border-[var(--wui-border)] bg-[var(--wui-bg)] px-2 py-1.5", children: [_jsx(ToolBtn, { title: "Rotate left", onClick: () => { rotate(-90); }, children: _jsx(RotateCcw, { className: "size-4" }) }), _jsx(ToolBtn, { title: "Rotate right", onClick: () => { rotate(90); }, children: _jsx(RotateCw, { className: "size-4" }) }), _jsx(Divider, {}), _jsx(ToolBtn, { title: "Zoom out", onClick: () => { applyZoom(zoom - 0.25); }, children: _jsx(ZoomOut, { className: "size-4" }) }), _jsxs("span", { className: "flex items-center rounded-md px-1 text-[12px] tabular-nums text-[var(--wui-fg-muted)]", children: [_jsx("input", { value: zoomText, onChange: (e) => { setZoomText(e.target.value.replace(/[^\d]/g, '').slice(0, 4)); }, onBlur: commitText, onKeyDown: (e) => { if (e.key === 'Enter')
|
|
61
|
+
e.currentTarget.blur(); }, inputMode: "numeric", "aria-label": "Zoom percent", className: "w-9 bg-transparent text-right text-[var(--wui-fg)] outline-none" }), "%"] }), _jsx(ToolBtn, { title: "Zoom in", onClick: () => { applyZoom(zoom + 0.25); }, children: _jsx(ZoomIn, { className: "size-4" }) }), _jsx(Divider, {}), _jsx(ToolBtn, { title: "Fit to view", onClick: fit, children: _jsx(Maximize2, { className: "size-4" }) }), _jsx(Divider, {}), _jsx(ToolLink, { href: url, target: "_blank", rel: "noopener noreferrer", title: "Open in new tab", children: _jsx(ExternalLink, { className: "size-4" }) }), _jsx(ToolLink, { href: url, download: name, title: "Download", children: _jsx(Download, { className: "size-4" }) })] }), _jsx("div", { ref: scrollRef, className: "flex flex-1 overflow-auto p-4", style: { cursor: canPan ? (panning ? 'grabbing' : 'grab') : 'default' }, onMouseDown: (e) => {
|
|
62
|
+
if (!canPan || !scrollRef.current)
|
|
63
|
+
return;
|
|
64
|
+
pan.current = { x: e.clientX, y: e.clientY, left: scrollRef.current.scrollLeft, top: scrollRef.current.scrollTop };
|
|
65
|
+
setPanning(true);
|
|
66
|
+
}, onMouseMove: (e) => {
|
|
67
|
+
const el = scrollRef.current;
|
|
68
|
+
if (!pan.current || !el)
|
|
69
|
+
return;
|
|
70
|
+
el.scrollLeft = pan.current.left - (e.clientX - pan.current.x);
|
|
71
|
+
el.scrollTop = pan.current.top - (e.clientY - pan.current.y);
|
|
72
|
+
}, onMouseUp: () => { pan.current = null; setPanning(false); }, onMouseLeave: () => { pan.current = null; setPanning(false); }, onDoubleClick: () => { applyZoom(zoom === 1 ? 2 : 1); }, children: ready ? (_jsx("div", { className: "relative m-auto shrink-0", style: { width: boxW, height: boxH }, children: _jsx("img", { src: url, alt: name, draggable: false, onLoad: (e) => { setNat({ w: e.currentTarget.naturalWidth, h: e.currentTarget.naturalHeight }); }, style: {
|
|
73
|
+
position: 'absolute',
|
|
74
|
+
top: '50%',
|
|
75
|
+
left: '50%',
|
|
76
|
+
width: imgW,
|
|
77
|
+
height: imgH,
|
|
78
|
+
maxWidth: 'none', // override Tailwind preflight `img{max-width:100%}`,
|
|
79
|
+
maxHeight: 'none', // which would clamp (and squash) the rotated image
|
|
80
|
+
transform: `translate(-50%, -50%) rotate(${String(deg)}deg)`,
|
|
81
|
+
}, className: "select-none rounded-lg" }) })) : (_jsx("img", { src: url, alt: name, draggable: false, onLoad: (e) => { setNat({ w: e.currentTarget.naturalWidth, h: e.currentTarget.naturalHeight }); }, className: "m-auto max-h-full max-w-full select-none rounded-lg object-contain" })) })] }));
|
|
82
|
+
}
|
|
83
|
+
function Divider() {
|
|
84
|
+
return _jsx("span", { className: "mx-1 h-4 w-px bg-[var(--wui-border)]" });
|
|
85
|
+
}
|
|
86
|
+
function ToolBtn({ title, onClick, children }) {
|
|
87
|
+
return (_jsx("button", { type: "button", onClick: onClick, title: title, className: "grid size-8 place-items-center rounded-lg text-[var(--wui-fg-muted)] transition-colors hover:bg-[var(--wui-bg-subtle)] hover:text-[var(--wui-fg)]", children: children }));
|
|
88
|
+
}
|
|
89
|
+
function ToolLink({ href, title, children, ...rest }) {
|
|
90
|
+
return (_jsx("a", { href: href, title: title, ...rest, className: "grid size-8 place-items-center rounded-lg text-[var(--wui-fg-muted)] transition-colors hover:bg-[var(--wui-bg-subtle)] hover:text-[var(--wui-fg)]", children: children }));
|
|
91
|
+
}
|
|
92
|
+
//# sourceMappingURL=ImageView.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"ImageView.js","sourceRoot":"","sources":["../../../../src/components/shared/viewers/ImageView.tsx"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"SheetView.d.ts","sourceRoot":"","sources":["../../../../src/components/shared/viewers/SheetView.tsx"],"names":[],"mappings":"AAUA,MAAM,CAAC,OAAO,UAAU,SAAS,CAAC,EAAE,GAAG,EAAE,EAAE;IAAE,GAAG,EAAE,MAAM,CAAA;CAAE,+BA6EzD"}
|
|
@@ -0,0 +1,48 @@
|
|
|
1
|
+
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
|
|
2
|
+
import { useEffect, useState } from 'react';
|
|
3
|
+
import readXlsxFile, { readSheetNames } from 'read-excel-file';
|
|
4
|
+
import { cn } from '../cn.js';
|
|
5
|
+
import { ViewerLoading } from './chrome.js';
|
|
6
|
+
const MAX_ROWS = 1000;
|
|
7
|
+
// XLSX/XLS renderer — parses with SheetJS, renders each sheet as a themed table
|
|
8
|
+
// with tabs when there is more than one sheet.
|
|
9
|
+
export default function SheetView({ url }) {
|
|
10
|
+
const [sheets, setSheets] = useState(null);
|
|
11
|
+
const [active, setActive] = useState(0);
|
|
12
|
+
const [failed, setFailed] = useState(false);
|
|
13
|
+
useEffect(() => {
|
|
14
|
+
let cancelled = false;
|
|
15
|
+
setSheets(null);
|
|
16
|
+
setFailed(false);
|
|
17
|
+
void fetch(url)
|
|
18
|
+
.then((r) => {
|
|
19
|
+
if (!r.ok)
|
|
20
|
+
throw new Error(String(r.status));
|
|
21
|
+
return r.arrayBuffer();
|
|
22
|
+
})
|
|
23
|
+
.then(async (buf) => {
|
|
24
|
+
const names = await readSheetNames(buf);
|
|
25
|
+
const parsed = await Promise.all(names.map(async (name) => ({ name, rows: await readXlsxFile(buf, { sheet: name }) })));
|
|
26
|
+
if (!cancelled)
|
|
27
|
+
setSheets(parsed);
|
|
28
|
+
})
|
|
29
|
+
.catch(() => { if (!cancelled)
|
|
30
|
+
setFailed(true); });
|
|
31
|
+
return () => { cancelled = true; };
|
|
32
|
+
}, [url]);
|
|
33
|
+
if (failed)
|
|
34
|
+
throw new Error('sheet load failed');
|
|
35
|
+
if (sheets === null)
|
|
36
|
+
return _jsx(ViewerLoading, {});
|
|
37
|
+
const sheet = sheets[active] ?? sheets[0];
|
|
38
|
+
if (!sheet)
|
|
39
|
+
return _jsx(ViewerLoading, {});
|
|
40
|
+
const [head, ...body] = sheet.rows;
|
|
41
|
+
const capped = body.slice(0, MAX_ROWS);
|
|
42
|
+
const th = 'sticky top-0 border border-[var(--wui-border)] bg-[var(--wui-bg-subtle)] px-2.5 py-1.5 text-left font-semibold text-[var(--wui-fg)]';
|
|
43
|
+
const td = 'border border-[var(--wui-border)] px-2.5 py-1.5 align-top text-[var(--wui-fg-muted)]';
|
|
44
|
+
return (_jsxs("div", { className: "flex h-full flex-col", children: [sheets.length > 1 && (_jsx("div", { className: "flex shrink-0 gap-1 overflow-x-auto border-b border-[var(--wui-border)] px-3 py-2", children: sheets.map((s, i) => (_jsx("button", { type: "button", onClick: () => setActive(i), className: cn('shrink-0 rounded px-2.5 py-1 text-[12px] transition-colors', i === active
|
|
45
|
+
? 'bg-[var(--wui-bg-subtle)] font-semibold text-[var(--wui-fg)]'
|
|
46
|
+
: 'text-[var(--wui-fg-muted)] hover:bg-[var(--wui-bg-subtle)]'), children: s.name }, s.name))) })), _jsxs("div", { className: "overflow-auto px-5 py-4", children: [_jsxs("table", { className: "w-full border-collapse text-[12.5px] tabular-nums", children: [head && (_jsx("thead", { children: _jsx("tr", { children: head.map((c, i) => _jsx("th", { className: th, children: String(c ?? '') }, i)) }) })), _jsx("tbody", { children: capped.map((row, ri) => (_jsx("tr", { children: row.map((c, ci) => _jsx("td", { className: td, children: String(c ?? '') }, ci)) }, ri))) })] }), body.length > capped.length && (_jsxs("p", { className: "mt-2 text-[12px] text-[var(--wui-fg-muted)]", children: ["Showing first ", String(capped.length), " of ", String(body.length), " rows."] }))] })] }));
|
|
47
|
+
}
|
|
48
|
+
//# sourceMappingURL=SheetView.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"SheetView.js","sourceRoot":"","sources":["../../../../src/components/shared/viewers/SheetView.tsx"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"TextView.d.ts","sourceRoot":"","sources":["../../../../src/components/shared/viewers/TextView.tsx"],"names":[],"mappings":"AAOA,MAAM,CAAC,OAAO,UAAU,QAAQ,CAAC,EAAE,GAAG,EAAE,IAAI,EAAE,EAAE;IAAE,GAAG,EAAE,MAAM,CAAC;IAAC,IAAI,EAAE,MAAM,GAAG,MAAM,GAAG,UAAU,CAAA;CAAE,+BAmClG"}
|
|
@@ -0,0 +1,45 @@
|
|
|
1
|
+
import { jsx as _jsx } from "react/jsx-runtime";
|
|
2
|
+
import { useEffect, useState } from 'react';
|
|
3
|
+
import { MarkdownView } from '../MarkdownView.js';
|
|
4
|
+
import { ViewerLoading } from './chrome.js';
|
|
5
|
+
// Plain-text / JSON / Markdown renderer. Fetches the file as text (same-origin,
|
|
6
|
+
// so the auth cookie rides along) and renders by mode. On load failure it
|
|
7
|
+
// throws during render so the parent ViewerBoundary shows the download fallback.
|
|
8
|
+
export default function TextView({ url, mode }) {
|
|
9
|
+
const [text, setText] = useState(null);
|
|
10
|
+
const [failed, setFailed] = useState(false);
|
|
11
|
+
useEffect(() => {
|
|
12
|
+
let cancelled = false;
|
|
13
|
+
setText(null);
|
|
14
|
+
setFailed(false);
|
|
15
|
+
void fetch(url)
|
|
16
|
+
.then((r) => {
|
|
17
|
+
if (!r.ok)
|
|
18
|
+
throw new Error(String(r.status));
|
|
19
|
+
return r.text();
|
|
20
|
+
})
|
|
21
|
+
.then((t) => { if (!cancelled)
|
|
22
|
+
setText(t); })
|
|
23
|
+
.catch(() => { if (!cancelled)
|
|
24
|
+
setFailed(true); });
|
|
25
|
+
return () => { cancelled = true; };
|
|
26
|
+
}, [url]);
|
|
27
|
+
if (failed)
|
|
28
|
+
throw new Error('text load failed');
|
|
29
|
+
if (text === null)
|
|
30
|
+
return _jsx(ViewerLoading, {});
|
|
31
|
+
if (mode === 'markdown') {
|
|
32
|
+
return (_jsx("div", { className: "px-5 py-4 text-[14px] text-[var(--wui-fg)]", children: _jsx(MarkdownView, { children: text }) }));
|
|
33
|
+
}
|
|
34
|
+
const body = mode === 'json' ? prettyJson(text) : text;
|
|
35
|
+
return (_jsx("pre", { className: "whitespace-pre-wrap break-words px-5 py-4 font-mono text-[12.5px] leading-relaxed text-[var(--wui-fg)]", children: body }));
|
|
36
|
+
}
|
|
37
|
+
function prettyJson(t) {
|
|
38
|
+
try {
|
|
39
|
+
return JSON.stringify(JSON.parse(t), null, 2);
|
|
40
|
+
}
|
|
41
|
+
catch {
|
|
42
|
+
return t;
|
|
43
|
+
}
|
|
44
|
+
}
|
|
45
|
+
//# sourceMappingURL=TextView.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"TextView.js","sourceRoot":"","sources":["../../../../src/components/shared/viewers/TextView.tsx"],"names":[],"mappings":";AAAA,OAAO,EAAE,SAAS,EAAE,QAAQ,EAAE,MAAM,OAAO,CAAC;AAC5C,OAAO,EAAE,YAAY,EAAE,MAAM,oBAAoB,CAAC;AAClD,OAAO,EAAE,aAAa,EAAE,MAAM,aAAa,CAAC;AAE5C,gFAAgF;AAChF,0EAA0E;AAC1E,iFAAiF;AACjF,MAAM,CAAC,OAAO,UAAU,QAAQ,CAAC,EAAE,GAAG,EAAE,IAAI,EAAuD;IACjG,MAAM,CAAC,IAAI,EAAE,OAAO,CAAC,GAAG,QAAQ,CAAgB,IAAI,CAAC,CAAC;IACtD,MAAM,CAAC,MAAM,EAAE,SAAS,CAAC,GAAG,QAAQ,CAAC,KAAK,CAAC,CAAC;IAE5C,SAAS,CAAC,GAAG,EAAE;QACb,IAAI,SAAS,GAAG,KAAK,CAAC;QACtB,OAAO,CAAC,IAAI,CAAC,CAAC;QACd,SAAS,CAAC,KAAK,CAAC,CAAC;QACjB,KAAK,KAAK,CAAC,GAAG,CAAC;aACZ,IAAI,CAAC,CAAC,CAAC,EAAE,EAAE;YACV,IAAI,CAAC,CAAC,CAAC,EAAE;gBAAE,MAAM,IAAI,KAAK,CAAC,MAAM,CAAC,CAAC,CAAC,MAAM,CAAC,CAAC,CAAC;YAC7C,OAAO,CAAC,CAAC,IAAI,EAAE,CAAC;QAClB,CAAC,CAAC;aACD,IAAI,CAAC,CAAC,CAAC,EAAE,EAAE,GAAG,IAAI,CAAC,SAAS;YAAE,OAAO,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;aAC5C,KAAK,CAAC,GAAG,EAAE,GAAG,IAAI,CAAC,SAAS;YAAE,SAAS,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;QACrD,OAAO,GAAG,EAAE,GAAG,SAAS,GAAG,IAAI,CAAC,CAAC,CAAC,CAAC;IACrC,CAAC,EAAE,CAAC,GAAG,CAAC,CAAC,CAAC;IAEV,IAAI,MAAM;QAAE,MAAM,IAAI,KAAK,CAAC,kBAAkB,CAAC,CAAC;IAChD,IAAI,IAAI,KAAK,IAAI;QAAE,OAAO,KAAC,aAAa,KAAG,CAAC;IAE5C,IAAI,IAAI,KAAK,UAAU,EAAE,CAAC;QACxB,OAAO,CACL,cAAK,SAAS,EAAC,4CAA4C,YACzD,KAAC,YAAY,cAAE,IAAI,GAAgB,GAC/B,CACP,CAAC;IACJ,CAAC;IAED,MAAM,IAAI,GAAG,IAAI,KAAK,MAAM,CAAC,CAAC,CAAC,UAAU,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC,IAAI,CAAC;IACvD,OAAO,CACL,cAAK,SAAS,EAAC,wGAAwG,YACpH,IAAI,GACD,CACP,CAAC;AACJ,CAAC;AAED,SAAS,UAAU,CAAC,CAAS;IAC3B,IAAI,CAAC;QACH,OAAO,IAAI,CAAC,SAAS,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC,CAAC,EAAE,IAAI,EAAE,CAAC,CAAC,CAAC;IAChD,CAAC;IAAC,MAAM,CAAC;QACP,OAAO,CAAC,CAAC;IACX,CAAC;AACH,CAAC"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"chrome.d.ts","sourceRoot":"","sources":["../../../../src/components/shared/viewers/chrome.tsx"],"names":[],"mappings":"AAGA,wBAAgB,aAAa,gCAM5B"}
|