@ai-matrx/records-ui 0.115.38 → 0.115.40
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/CHANGELOG.md +18 -0
- package/dist/index.cjs +323 -136
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +60 -2
- package/dist/index.d.ts +60 -2
- package/dist/index.js +320 -131
- package/dist/index.js.map +1 -1
- package/dist/pickers.cjs.map +1 -1
- package/dist/pickers.js.map +1 -1
- package/package.json +3 -3
package/dist/index.js
CHANGED
|
@@ -5503,9 +5503,12 @@ function withheldNoticeOf(hidden, key) {
|
|
|
5503
5503
|
return notice && typeof notice === "object" ? notice : null;
|
|
5504
5504
|
}
|
|
5505
5505
|
function withheldSentence(field2, notice) {
|
|
5506
|
-
const
|
|
5507
|
-
if (typeof says === "string" && says.trim() !== "") return says.trim();
|
|
5506
|
+
const extra = notice;
|
|
5507
|
+
if (typeof extra.says === "string" && extra.says.trim() !== "") return extra.says.trim();
|
|
5508
5508
|
const name = fieldName(field2);
|
|
5509
|
+
if (typeof extra.part === "string" && extra.part.trim() !== "" && typeof extra.who === "string" && extra.who.trim() !== "") {
|
|
5510
|
+
return `${name} is in ${extra.part.trim()} \u2014 ${extra.who.trim()} see it.`;
|
|
5511
|
+
}
|
|
5509
5512
|
const reason = notice.reason ? ` It is ${notice.reason}` : "";
|
|
5510
5513
|
const needs = notice.needs ? `${reason ? "," : " It"} and reading it needs ${notice.needs}` : "";
|
|
5511
5514
|
const or = notice.or ? `${needs || reason ? ", or" : " It needs"} ${notice.or}` : "";
|
|
@@ -11474,6 +11477,9 @@ function useGridEditing({ tableId, fields, rows, reload, reloadAfterWrite, canWr
|
|
|
11474
11477
|
const startedFrom = useRef21(null);
|
|
11475
11478
|
const startedStored = useRef21(null);
|
|
11476
11479
|
const host = useRecordsUi();
|
|
11480
|
+
const fieldsRef = useRef21(fields);
|
|
11481
|
+
fieldsRef.current = fields;
|
|
11482
|
+
const forceNext = useRef21(/* @__PURE__ */ new Set());
|
|
11477
11483
|
const type = useCallback10((value) => {
|
|
11478
11484
|
typed2.current = value;
|
|
11479
11485
|
setDraft(value);
|
|
@@ -11630,6 +11636,47 @@ function useGridEditing({ tableId, fields, rows, reload, reloadAfterWrite, canWr
|
|
|
11630
11636
|
delete next[id];
|
|
11631
11637
|
return next;
|
|
11632
11638
|
});
|
|
11639
|
+
const syncedField = fieldsRef.current.find((f) => f.key === key);
|
|
11640
|
+
if (syncedField?.source === "synced" && host.writeSyncedCell) {
|
|
11641
|
+
const force = forceNext.current.delete(id);
|
|
11642
|
+
let outcome;
|
|
11643
|
+
try {
|
|
11644
|
+
outcome = await host.writeSyncedCell({ tableId, recordId: rowId, fieldKey: key, value: shown5, force });
|
|
11645
|
+
} catch (thrown) {
|
|
11646
|
+
outcome = { ok: false, message: thrown instanceof Error ? thrown.message : String(thrown) };
|
|
11647
|
+
}
|
|
11648
|
+
setSaving((held) => {
|
|
11649
|
+
const next = { ...held };
|
|
11650
|
+
delete next[id];
|
|
11651
|
+
return next;
|
|
11652
|
+
});
|
|
11653
|
+
if (outcome.ok && outcome.status === "written") {
|
|
11654
|
+
if (typeof outcome.version === "number") {
|
|
11655
|
+
rememberVersion(versions.current, rowId, outcome.version);
|
|
11656
|
+
source.wrote(rowId, outcome.version);
|
|
11657
|
+
}
|
|
11658
|
+
settling.current.set(id, base2);
|
|
11659
|
+
writtenRef.current?.({ rowId, key, before: base2, after: shown5 });
|
|
11660
|
+
afterWrite();
|
|
11661
|
+
return;
|
|
11662
|
+
}
|
|
11663
|
+
setOptimistic((held) => {
|
|
11664
|
+
const next = { ...held };
|
|
11665
|
+
delete next[id];
|
|
11666
|
+
return next;
|
|
11667
|
+
});
|
|
11668
|
+
const sheetValue = outcome.ok ? outcome.sheetValue : null;
|
|
11669
|
+
setRefusals((held) => ({
|
|
11670
|
+
...held,
|
|
11671
|
+
[id]: outcome.ok ? {
|
|
11672
|
+
error: { code: "stale_write", message: `The sheet now says "${sheetValue ?? ""}". Retry keeps yours.` },
|
|
11673
|
+
conflict: null,
|
|
11674
|
+
attempted: value,
|
|
11675
|
+
sheet: { value: sheetValue }
|
|
11676
|
+
} : { error: { code: "refused_by_rule", message: outcome.message }, conflict: null, attempted: value }
|
|
11677
|
+
}));
|
|
11678
|
+
return;
|
|
11679
|
+
}
|
|
11633
11680
|
let written;
|
|
11634
11681
|
try {
|
|
11635
11682
|
let version = await versionOf(source, versions.current, versionReads.current, rowId);
|
|
@@ -11789,6 +11836,7 @@ function useGridEditing({ tableId, fields, rows, reload, reloadAfterWrite, canWr
|
|
|
11789
11836
|
(rowId, key) => {
|
|
11790
11837
|
const held = refusals[cellKey(rowId, key)];
|
|
11791
11838
|
if (!held) return;
|
|
11839
|
+
if (held.sheet) forceNext.current.add(cellKey(rowId, key));
|
|
11792
11840
|
void writeCell(rowId, key, held.attempted, held.conflict?.contested_fields[key]);
|
|
11793
11841
|
},
|
|
11794
11842
|
[refusals, writeCell]
|
|
@@ -16573,6 +16621,7 @@ function useMergedGridControls(args) {
|
|
|
16573
16621
|
} = args;
|
|
16574
16622
|
const client = useRecordsClient27();
|
|
16575
16623
|
const linkRecord = useRecordsUi().linkRecord;
|
|
16624
|
+
const columnAccess = useRecordsUi().columnAccess;
|
|
16576
16625
|
const hrefForRecord = useRecordsUi().hrefForRecord;
|
|
16577
16626
|
const tableVersion = (0, recordVersions_exports.useTableVersion)(client, tableId, table);
|
|
16578
16627
|
const mutation = useFieldMutation2();
|
|
@@ -16754,6 +16803,14 @@ function useMergedGridControls(args) {
|
|
|
16754
16803
|
writeLook({ ...rest, ...next.size > 0 ? { wrapColumns: [...next] } : {} });
|
|
16755
16804
|
}
|
|
16756
16805
|
});
|
|
16806
|
+
if (columnAccess) {
|
|
16807
|
+
out.push({
|
|
16808
|
+
id: "col-access",
|
|
16809
|
+
label: "Who can see and edit\u2026",
|
|
16810
|
+
disabledReason: rights.structure ? void 0 : rights.why("structure"),
|
|
16811
|
+
onSelect: () => setDialog({ kind: "access", field: field2 })
|
|
16812
|
+
});
|
|
16813
|
+
}
|
|
16757
16814
|
out.push({
|
|
16758
16815
|
id: "col-duplicate",
|
|
16759
16816
|
label: "Duplicate property",
|
|
@@ -17035,6 +17092,7 @@ function useMergedGridControls(args) {
|
|
|
17035
17092
|
}
|
|
17036
17093
|
};
|
|
17037
17094
|
}, [
|
|
17095
|
+
columnAccess,
|
|
17038
17096
|
args,
|
|
17039
17097
|
colours,
|
|
17040
17098
|
fieldKeys,
|
|
@@ -17085,6 +17143,13 @@ function useMergedGridControls(args) {
|
|
|
17085
17143
|
const close = () => setDialog(null);
|
|
17086
17144
|
const dialogs = !enabled ? null : /* @__PURE__ */ jsxs57(Fragment17, { children: [
|
|
17087
17145
|
colours.dialogs,
|
|
17146
|
+
dialog?.kind === "access" && columnAccess ? columnAccess({
|
|
17147
|
+
tableId,
|
|
17148
|
+
fieldId: dialog.field.id,
|
|
17149
|
+
name: fieldName(dialog.field),
|
|
17150
|
+
onClose: () => setDialog(null),
|
|
17151
|
+
onChanged: () => tableShapeChanged5(tableId)
|
|
17152
|
+
}) : null,
|
|
17088
17153
|
/* @__PURE__ */ jsx63(RowActionsDialog, { tableId, open: rowActionsOpen, onOpenChange: setRowActionsOpen }),
|
|
17089
17154
|
/* @__PURE__ */ jsx63(
|
|
17090
17155
|
RowLabelPicker,
|
|
@@ -19672,6 +19737,40 @@ function columnForField(field2, editing, mayWriteRow, whyNotRow, look, onAskWhoC
|
|
|
19672
19737
|
const name = fieldName(field2);
|
|
19673
19738
|
const format = cellFormatFor(field2, look?.format);
|
|
19674
19739
|
const workedOut = workedOutFrom(field2);
|
|
19740
|
+
const syncedMark = field2.source === "synced" ? /* @__PURE__ */ jsx69(
|
|
19741
|
+
"span",
|
|
19742
|
+
{
|
|
19743
|
+
"data-records-synced": field2.key,
|
|
19744
|
+
title: `Synced from ${look?.syncedFrom || "its source"}`,
|
|
19745
|
+
"aria-label": `Synced from ${look?.syncedFrom || "its source"}`,
|
|
19746
|
+
className: "text-[10px] text-muted-foreground",
|
|
19747
|
+
children: "\u27F3"
|
|
19748
|
+
}
|
|
19749
|
+
) : null;
|
|
19750
|
+
const restricted = field2.sensitivity === "confidential" || field2.sensitivity === "restricted";
|
|
19751
|
+
const lockMark = restricted ? /* @__PURE__ */ jsx69(
|
|
19752
|
+
"span",
|
|
19753
|
+
{
|
|
19754
|
+
"data-records-restricted": field2.key,
|
|
19755
|
+
title: "Fewer people see this column",
|
|
19756
|
+
"aria-label": "Fewer people see this column",
|
|
19757
|
+
className: "inline-flex text-muted-foreground",
|
|
19758
|
+
children: /* @__PURE__ */ jsxs63("svg", { viewBox: "0 0 24 24", width: "11", height: "11", fill: "none", stroke: "currentColor", strokeWidth: "2", strokeLinecap: "round", strokeLinejoin: "round", "aria-hidden": "true", children: [
|
|
19759
|
+
/* @__PURE__ */ jsx69("rect", { x: "4", y: "11", width: "16", height: "10", rx: "2" }),
|
|
19760
|
+
/* @__PURE__ */ jsx69("path", { d: "M8 11V7a4 4 0 0 1 8 0v4" })
|
|
19761
|
+
] })
|
|
19762
|
+
}
|
|
19763
|
+
) : null;
|
|
19764
|
+
const withSynced = (inner2) => {
|
|
19765
|
+
const header = lockMark ? /* @__PURE__ */ jsxs63("span", { className: "inline-flex items-center gap-1", children: [
|
|
19766
|
+
inner2,
|
|
19767
|
+
lockMark
|
|
19768
|
+
] }) : inner2;
|
|
19769
|
+
return syncedMark ? /* @__PURE__ */ jsxs63("span", { className: "inline-flex items-center gap-1", children: [
|
|
19770
|
+
syncedMark,
|
|
19771
|
+
header
|
|
19772
|
+
] }) : header;
|
|
19773
|
+
};
|
|
19675
19774
|
return {
|
|
19676
19775
|
id: field2.key,
|
|
19677
19776
|
/*
|
|
@@ -19679,38 +19778,40 @@ function columnForField(field2, editing, mayWriteRow, whyNotRow, look, onAskWhoC
|
|
|
19679
19778
|
* (`custom.formula_eval`, on read or on write) and nobody types it — so its header carries
|
|
19680
19779
|
* the mark, and the formula it is worked out from is one hover away, in its own words.
|
|
19681
19780
|
*/
|
|
19682
|
-
header:
|
|
19683
|
-
|
|
19684
|
-
|
|
19781
|
+
header: withSynced(
|
|
19782
|
+
look?.rowLabel ? (
|
|
19783
|
+
// THE COLUMN THAT NAMES EACH RECORD says so (tranche 6i, the older grid's key marker).
|
|
19784
|
+
/* @__PURE__ */ jsxs63("span", { className: "inline-flex items-center gap-1", children: [
|
|
19785
|
+
/* @__PURE__ */ jsx69(
|
|
19786
|
+
"span",
|
|
19787
|
+
{
|
|
19788
|
+
"data-records-row-label": field2.key,
|
|
19789
|
+
title: "This column names each record",
|
|
19790
|
+
"aria-label": "Names each record",
|
|
19791
|
+
className: "text-[10px] text-muted-foreground",
|
|
19792
|
+
children: "\u26BF"
|
|
19793
|
+
}
|
|
19794
|
+
),
|
|
19795
|
+
name
|
|
19796
|
+
] })
|
|
19797
|
+
) : workedOut && stampMarkOf(field2) ? (
|
|
19798
|
+
// A STAMP OR A RECORD NUMBER (walk 2026-10-08 D7): kept by the store, but nobody wrote a formula
|
|
19799
|
+
// for it, so its header wears its own mark — a clock, a person, a number sign — never "fx".
|
|
19800
|
+
/* @__PURE__ */ jsx69("span", { className: "inline-flex items-center", title: workedOut, "data-records-stamp": stampMarkOf(field2), children: withTypeMark(field2, name) })
|
|
19801
|
+
) : workedOut ? /* @__PURE__ */ jsxs63("span", { className: "inline-flex items-center gap-1", children: [
|
|
19802
|
+
name,
|
|
19685
19803
|
/* @__PURE__ */ jsx69(
|
|
19686
19804
|
"span",
|
|
19687
19805
|
{
|
|
19688
|
-
"data-records-
|
|
19689
|
-
title:
|
|
19690
|
-
"aria-label":
|
|
19691
|
-
className: "text-[10px] text-muted-foreground",
|
|
19692
|
-
children: "
|
|
19806
|
+
"data-records-worked-out": field2.key,
|
|
19807
|
+
title: workedOut,
|
|
19808
|
+
"aria-label": workedOut,
|
|
19809
|
+
className: "rounded bg-muted px-1 font-mono text-[10px] font-normal text-muted-foreground",
|
|
19810
|
+
children: "fx"
|
|
19693
19811
|
}
|
|
19694
|
-
)
|
|
19695
|
-
|
|
19696
|
-
|
|
19697
|
-
) : workedOut && stampMarkOf(field2) ? (
|
|
19698
|
-
// A STAMP OR A RECORD NUMBER (walk 2026-10-08 D7): kept by the store, but nobody wrote a formula
|
|
19699
|
-
// for it, so its header wears its own mark — a clock, a person, a number sign — never "fx".
|
|
19700
|
-
/* @__PURE__ */ jsx69("span", { className: "inline-flex items-center", title: workedOut, "data-records-stamp": stampMarkOf(field2), children: withTypeMark(field2, name) })
|
|
19701
|
-
) : workedOut ? /* @__PURE__ */ jsxs63("span", { className: "inline-flex items-center gap-1", children: [
|
|
19702
|
-
name,
|
|
19703
|
-
/* @__PURE__ */ jsx69(
|
|
19704
|
-
"span",
|
|
19705
|
-
{
|
|
19706
|
-
"data-records-worked-out": field2.key,
|
|
19707
|
-
title: workedOut,
|
|
19708
|
-
"aria-label": workedOut,
|
|
19709
|
-
className: "rounded bg-muted px-1 font-mono text-[10px] font-normal text-muted-foreground",
|
|
19710
|
-
children: "fx"
|
|
19711
|
-
}
|
|
19712
|
-
)
|
|
19713
|
-
] }) : name,
|
|
19812
|
+
)
|
|
19813
|
+
] }) : name
|
|
19814
|
+
),
|
|
19714
19815
|
label: name,
|
|
19715
19816
|
accessorFn: (row) => row.document?.[field2.key],
|
|
19716
19817
|
// A column the store keeps no value for is not offered a sort it would refuse (`sortRefusal`).
|
|
@@ -20921,7 +21022,7 @@ function columnsSentence(mapped, total, unmapped) {
|
|
|
20921
21022
|
if (unmapped === "ignore") return `${mapped} of ${total} columns go into this table \xB7 ${rest} left out`;
|
|
20922
21023
|
return `${mapped} of ${total} go in now \xB7 ${rest} wait for approval with their values`;
|
|
20923
21024
|
}
|
|
20924
|
-
function ImportWizard({ tableId, source, onDone, onWrote, className }) {
|
|
21025
|
+
function ImportWizard({ tableId, source, onDone, onWrote, autoRun, className }) {
|
|
20925
21026
|
const client = useRecordsClient35();
|
|
20926
21027
|
const table = useTable8(tableId);
|
|
20927
21028
|
const fields = useFields10(tableId);
|
|
@@ -21543,6 +21644,13 @@ function ImportWizard({ tableId, source, onDone, onWrote, className }) {
|
|
|
21543
21644
|
const refusedByRules = ruleVerdicts.reduce((n, v) => n + v.refused, 0);
|
|
21544
21645
|
const [goAheadAnyway, setGoAheadAnyway] = useState61(false);
|
|
21545
21646
|
useEffect46(() => setGoAheadAnyway(false), [ruleVerdicts]);
|
|
21647
|
+
const [autoRan, setAutoRan] = useState61(false);
|
|
21648
|
+
useEffect46(() => {
|
|
21649
|
+
if (!autoRun || autoRan || !source || phase !== "ready" || !plan) return;
|
|
21650
|
+
if (busy || !rights.write || rows.length === 0 || titleMissing || ruleVerdicts.length > 0) return;
|
|
21651
|
+
setAutoRan(true);
|
|
21652
|
+
void run();
|
|
21653
|
+
}, [autoRun, autoRan, source, phase, plan, busy, rights.write, rows.length, titleMissing, ruleVerdicts, run]);
|
|
21546
21654
|
const afterWrite = !busy && (phase === "done" || alreadyRan !== null || ledger !== null && ledger.seen > 0);
|
|
21547
21655
|
return /* @__PURE__ */ jsxs68("div", { className: cn37("flex min-w-0 flex-col gap-2 text-xs", className), children: [
|
|
21548
21656
|
/* @__PURE__ */ jsxs68("div", { className: "flex items-center gap-2", children: [
|
|
@@ -24251,6 +24359,8 @@ import {
|
|
|
24251
24359
|
designateView,
|
|
24252
24360
|
viewPatchFor,
|
|
24253
24361
|
groupViewsBySection,
|
|
24362
|
+
planViewDrop,
|
|
24363
|
+
sectionDropId,
|
|
24254
24364
|
sectionNames,
|
|
24255
24365
|
sectionNameOk,
|
|
24256
24366
|
reassignSection
|
|
@@ -25710,7 +25820,8 @@ function GridBody({
|
|
|
25710
25820
|
...presentation.formats?.[field2.key] ? { format: presentation.formats[field2.key] } : {},
|
|
25711
25821
|
frozen: frozenKeys.has(field2.key),
|
|
25712
25822
|
// The column that names each record wears the mark (merged grid, tranche 6i).
|
|
25713
|
-
rowLabel: merged && field2.key === (table.data?.title_field ?? null)
|
|
25823
|
+
rowLabel: merged && field2.key === (table.data?.title_field ?? null),
|
|
25824
|
+
syncedFrom: syncedFromWords(table.data)
|
|
25714
25825
|
},
|
|
25715
25826
|
onAskWhoChanged,
|
|
25716
25827
|
{
|
|
@@ -26899,6 +27010,12 @@ function withHeaderMenus(columns, menuFor, filterFor) {
|
|
|
26899
27010
|
return filter ? { ...withMenu, ...filter } : withMenu;
|
|
26900
27011
|
});
|
|
26901
27012
|
}
|
|
27013
|
+
function syncedFromWords(table) {
|
|
27014
|
+
const source = table?.sync_source;
|
|
27015
|
+
if (!source?.provider) return null;
|
|
27016
|
+
const from = source.provider === "google_sheets" ? "Google Sheets" : source.provider === "csv_url" ? "a CSV link" : source.provider === "postgres" ? "an outside database" : source.provider === "matrx_view" ? "another table" : source.provider;
|
|
27017
|
+
return source.label ? `${from} \xB7 ${source.label}` : from;
|
|
27018
|
+
}
|
|
26902
27019
|
function withoutGoneColumns(query, liveKeys, openingSort) {
|
|
26903
27020
|
const sortGone = Boolean(query.sort && !liveKeys.has(query.sort.id));
|
|
26904
27021
|
const goneFilters = Object.keys(query.columnFilters ?? {}).filter((key) => !liveKeys.has(key));
|
|
@@ -28163,7 +28280,7 @@ function NewTableStart({
|
|
|
28163
28280
|
/* @__PURE__ */ jsx89(Button53, { disabled: !importReady || busy, onClick: () => void continueImport(), "data-new-table-continue": "", children: busy ? "Creating\u2026" : "Next: columns" })
|
|
28164
28281
|
] });
|
|
28165
28282
|
} else {
|
|
28166
|
-
body = /* @__PURE__ */ jsx89("div", { "data-new-table-wizard": "", children: /* @__PURE__ */ jsx89(ImportWizard, { tableId: step2.tableId, source: step2.source, onDone: () => onOpenTable?.(step2.tableId) }) });
|
|
28283
|
+
body = /* @__PURE__ */ jsx89("div", { "data-new-table-wizard": "", children: /* @__PURE__ */ jsx89(ImportWizard, { tableId: step2.tableId, source: step2.source, autoRun: step2.made, onDone: () => onOpenTable?.(step2.tableId) }) });
|
|
28167
28284
|
footer = /* @__PURE__ */ jsxs79(Fragment30, { children: [
|
|
28168
28285
|
!step2.made ? /* @__PURE__ */ jsx89(Button53, { variant: "ghost", className: "mr-auto", onClick: () => setStep({ at: "import" }), children: "Back" }) : null,
|
|
28169
28286
|
/* @__PURE__ */ jsx89(Button53, { variant: "outline", onClick: () => onOpenTable?.(step2.tableId), "data-new-table-open": "", children: "Open the table" })
|
|
@@ -35008,6 +35125,7 @@ function TimelineView({
|
|
|
35008
35125
|
const [dragging, setDragging] = useState99(null);
|
|
35009
35126
|
const [linking, setLinking] = useState99(null);
|
|
35010
35127
|
const [ganttBusy, setGanttBusy] = useState99(false);
|
|
35128
|
+
const [linkTarget, setLinkTarget] = useState99(null);
|
|
35011
35129
|
const { placed, unscheduled } = useMemo57(() => {
|
|
35012
35130
|
const out = [];
|
|
35013
35131
|
const without = [];
|
|
@@ -35176,6 +35294,18 @@ function TimelineView({
|
|
|
35176
35294
|
label: `${titleOf(target)} now waits on ${titleOf(source)}`
|
|
35177
35295
|
});
|
|
35178
35296
|
};
|
|
35297
|
+
const taskRowAt = (x, y) => {
|
|
35298
|
+
const canvas = scroller.current?.querySelector("[data-timeline-canvas]");
|
|
35299
|
+
const body2 = scroller.current;
|
|
35300
|
+
if (!canvas || !body2) return null;
|
|
35301
|
+
const box = canvas.getBoundingClientRect();
|
|
35302
|
+
const frame2 = body2.getBoundingClientRect();
|
|
35303
|
+
if (frame2.width === 0 || x < frame2.left || x > frame2.right) return null;
|
|
35304
|
+
const index = Math.floor((y - box.top - LANE_PAD / 2) / ROW_PX);
|
|
35305
|
+
if (index < 0) return null;
|
|
35306
|
+
const lane = laneRows[0];
|
|
35307
|
+
return lane?.packed.find((b) => b.row === index)?.p.row.id ?? null;
|
|
35308
|
+
};
|
|
35179
35309
|
const beginLink = (p) => (e) => {
|
|
35180
35310
|
if (e.button !== void 0 && e.button !== 0) return;
|
|
35181
35311
|
e.stopPropagation();
|
|
@@ -35184,13 +35314,21 @@ function TimelineView({
|
|
|
35184
35314
|
const x1 = box.left + box.width / 2;
|
|
35185
35315
|
const y1 = box.top + box.height / 2;
|
|
35186
35316
|
setLinking({ id: p.row.id, x1, y1, x2: e.clientX, y2: e.clientY });
|
|
35187
|
-
const onMove = (ev) =>
|
|
35317
|
+
const onMove = (ev) => {
|
|
35318
|
+
const x = ev.clientX;
|
|
35319
|
+
const y = ev.clientY;
|
|
35320
|
+
setLinking((l) => l ? { ...l, x2: x, y2: y } : l);
|
|
35321
|
+
const over = taskRowAt(x, y);
|
|
35322
|
+
setLinkTarget(over && over !== p.row.id ? over : null);
|
|
35323
|
+
};
|
|
35188
35324
|
const onUp = (ev) => {
|
|
35189
35325
|
window.removeEventListener("pointermove", onMove);
|
|
35190
35326
|
window.removeEventListener("pointerup", onUp);
|
|
35191
35327
|
setLinking(null);
|
|
35328
|
+
setLinkTarget(null);
|
|
35329
|
+
const at = ev;
|
|
35192
35330
|
const hit = ev.target?.closest?.("[data-timeline-bar]");
|
|
35193
|
-
const id = hit?.getAttribute("data-timeline-bar");
|
|
35331
|
+
const id = taskRowAt(at.clientX, at.clientY) ?? hit?.getAttribute("data-timeline-bar");
|
|
35194
35332
|
if (id && id !== p.row.id) connect(p.row.id, id);
|
|
35195
35333
|
};
|
|
35196
35334
|
window.addEventListener("pointermove", onMove);
|
|
@@ -35202,7 +35340,7 @@ function TimelineView({
|
|
|
35202
35340
|
try {
|
|
35203
35341
|
const make = async (current, key, label) => {
|
|
35204
35342
|
if (current) return current.key;
|
|
35205
|
-
const made = await knobClient.fieldDeclare({ table_id: tableId, spec: { key, label,
|
|
35343
|
+
const made = await knobClient.fieldDeclare({ table_id: tableId, spec: { key, label, parity_type: "datetime", kind: "date" } });
|
|
35206
35344
|
if (!made.ok) {
|
|
35207
35345
|
moves.say(refusalSentence(made.error));
|
|
35208
35346
|
return null;
|
|
@@ -35421,6 +35559,7 @@ function TimelineView({
|
|
|
35421
35559
|
"data-timeline-span": `${first}..${last}`,
|
|
35422
35560
|
...p.marker ? { "data-timeline-marker": "" } : {},
|
|
35423
35561
|
...milestone ? { "data-timeline-milestone": "" } : {},
|
|
35562
|
+
...linkTarget === p.row.id ? { "data-timeline-drop-target": "" } : {},
|
|
35424
35563
|
...onCritical ? { "data-timeline-critical": "" } : {},
|
|
35425
35564
|
...slip !== null ? { "data-timeline-slip": slip } : {},
|
|
35426
35565
|
...may ? {} : { "data-timeline-locked": "" },
|
|
@@ -35434,6 +35573,7 @@ function TimelineView({
|
|
|
35434
35573
|
outside ? "overflow-visible" : "overflow-hidden",
|
|
35435
35574
|
milestone ? "border-transparent bg-transparent" : color ? CHOICE_CHIP_CLASS4[color] : "bg-muted",
|
|
35436
35575
|
onCritical ? "ring-2 ring-amber-500" : void 0,
|
|
35576
|
+
linkTarget === p.row.id ? "ring-2 ring-primary" : void 0,
|
|
35437
35577
|
may ? "cursor-grab active:cursor-grabbing" : "cursor-pointer",
|
|
35438
35578
|
dragging?.id === p.row.id ? "z-20 shadow-md" : "z-10",
|
|
35439
35579
|
refused ? "ring-2 ring-destructive" : void 0
|
|
@@ -35515,7 +35655,7 @@ function TimelineView({
|
|
|
35515
35655
|
/* @__PURE__ */ jsxs109("div", { className: "ml-auto flex flex-wrap items-center gap-2", children: [
|
|
35516
35656
|
settings,
|
|
35517
35657
|
/* @__PURE__ */ jsxs109(DropdownMenu8, { children: [
|
|
35518
|
-
/* @__PURE__ */ jsx120(DropdownMenuTrigger8, { asChild: true, children: /* @__PURE__ */ jsx120(Button75, { size: "sm", variant: ganttOn ? "secondary" :
|
|
35658
|
+
/* @__PURE__ */ jsx120(DropdownMenuTrigger8, { asChild: true, children: /* @__PURE__ */ jsx120(Button75, { size: "sm", variant: "outline", className: ganttOn ? "bg-secondary" : void 0, "aria-label": "Gantt options", "data-timeline-gantt-menu": "", children: "Gantt" }) }),
|
|
35519
35659
|
/* @__PURE__ */ jsxs109(DropdownMenuContent8, { align: "end", className: "min-w-48", children: [
|
|
35520
35660
|
/* @__PURE__ */ jsx120(DropdownMenuCheckboxItem2, { checked: ganttOn, onCheckedChange: (on) => setGantt({ mode: on === true }), children: "Gantt view" }),
|
|
35521
35661
|
ganttOn ? /* @__PURE__ */ jsxs109(Fragment45, { children: [
|
|
@@ -35593,6 +35733,7 @@ function TimelineView({
|
|
|
35593
35733
|
const ghost = baselineOf(b.p.row);
|
|
35594
35734
|
const at = shown5(b.p);
|
|
35595
35735
|
return /* @__PURE__ */ jsxs109("div", { children: [
|
|
35736
|
+
linkTarget === b.p.row.id ? /* @__PURE__ */ jsx120("div", { "aria-hidden": "true", "data-timeline-drop-band": b.p.row.id, className: "pointer-events-none absolute inset-x-0 bg-primary/10", style: { top: LANE_PAD / 2 + b.row * ROW_PX, height: ROW_PX } }) : null,
|
|
35596
35737
|
ghost ? /* @__PURE__ */ jsx120(
|
|
35597
35738
|
"div",
|
|
35598
35739
|
{
|
|
@@ -38927,6 +39068,9 @@ function ArchivedPortals({
|
|
|
38927
39068
|
import { useCallback as useCallback43, useEffect as useEffect89, useRef as useRef50, useState as useState109 } from "react";
|
|
38928
39069
|
import { useRecordsClient as useRecordsClient74 } from "@ai-matrx/records/react";
|
|
38929
39070
|
import { Badge as Badge15, Button as Button80, Input as Input6, Popover as Popover16, PopoverContent as PopoverContent16, PopoverTrigger as PopoverTrigger16, Skeleton as Skeleton18, cn as cn65 } from "@ai-matrx/design-system";
|
|
39071
|
+
import { DndContext, PointerSensor, closestCenter, useDroppable, useSensor, useSensors } from "@dnd-kit/core";
|
|
39072
|
+
import { SortableContext, useSortable, verticalListSortingStrategy } from "@dnd-kit/sortable";
|
|
39073
|
+
import { CSS as CSS2 } from "@dnd-kit/utilities";
|
|
38930
39074
|
|
|
38931
39075
|
// src/seedOnce.ts
|
|
38932
39076
|
import { useCallback as useCallback42, useRef as useRef49 } from "react";
|
|
@@ -38948,7 +39092,7 @@ var NOOP3 = () => {
|
|
|
38948
39092
|
};
|
|
38949
39093
|
function viewActions(whyNot, host, locked = false, personal = false) {
|
|
38950
39094
|
const one = (base2, run) => {
|
|
38951
|
-
if (whyNot !== null) return { ...base2, disabledReason: whyNot, run: NOOP3 };
|
|
39095
|
+
if (whyNot !== null) return { ...base2, disabledReason: locked && base2.id !== "duplicate" && base2.id !== "lock" ? VIEW_LOCKED_REASON : whyNot, run: NOOP3 };
|
|
38952
39096
|
if (!run) return { ...base2, disabledReason: ACTION_NOT_HERE_REASON, run: NOOP3 };
|
|
38953
39097
|
return { ...base2, run };
|
|
38954
39098
|
};
|
|
@@ -38991,6 +39135,25 @@ function seedIsSatisfied(seed, views) {
|
|
|
38991
39135
|
if (views.some((v) => v.name === seed.name)) return true;
|
|
38992
39136
|
return seed.isDefault === true && views.some((v) => v.isDefault);
|
|
38993
39137
|
}
|
|
39138
|
+
function SectionBox({ id, children, ...rest }) {
|
|
39139
|
+
const { setNodeRef, isOver } = useDroppable({ id });
|
|
39140
|
+
return /* @__PURE__ */ jsx131("div", { ref: setNodeRef, className: cn65("rounded-sm", isOver && "bg-accent/40"), ...rest, children });
|
|
39141
|
+
}
|
|
39142
|
+
function SortableRow({ id, disabled, children }) {
|
|
39143
|
+
const { attributes, listeners: listeners2, setNodeRef, transform, transition, isDragging } = useSortable({ id, disabled });
|
|
39144
|
+
return /* @__PURE__ */ jsx131(
|
|
39145
|
+
"div",
|
|
39146
|
+
{
|
|
39147
|
+
ref: setNodeRef,
|
|
39148
|
+
style: { transform: CSS2.Transform.toString(transform), transition },
|
|
39149
|
+
className: cn65(isDragging && "relative z-10 opacity-80"),
|
|
39150
|
+
"data-view-row": id,
|
|
39151
|
+
...disabled ? {} : attributes,
|
|
39152
|
+
...disabled ? {} : listeners2,
|
|
39153
|
+
children
|
|
39154
|
+
}
|
|
39155
|
+
);
|
|
39156
|
+
}
|
|
38994
39157
|
function ViewBar({ tableId, activeViewId, onActiveView, seed, settings, onViews, initialViews, className }) {
|
|
38995
39158
|
const client = useRecordsClient74();
|
|
38996
39159
|
const claimSeed = useSeedGuard();
|
|
@@ -39022,6 +39185,26 @@ function ViewBar({ tableId, activeViewId, onActiveView, seed, settings, onViews,
|
|
|
39022
39185
|
}
|
|
39023
39186
|
});
|
|
39024
39187
|
const [renamingSection, setRenamingSection] = useState109(null);
|
|
39188
|
+
const [dragging, setDragging] = useState109(false);
|
|
39189
|
+
const justDragged = useRef50(false);
|
|
39190
|
+
const sensors = useSensors(useSensor(PointerSensor, { activationConstraint: { distance: 6 } }));
|
|
39191
|
+
async function dropped(event) {
|
|
39192
|
+
setDragging(false);
|
|
39193
|
+
justDragged.current = true;
|
|
39194
|
+
setTimeout(() => {
|
|
39195
|
+
justDragged.current = false;
|
|
39196
|
+
}, 250);
|
|
39197
|
+
if (!event.over || !views) return;
|
|
39198
|
+
const writes = planViewDrop(views, String(event.active.id), String(event.over.id));
|
|
39199
|
+
for (const w of writes) {
|
|
39200
|
+
const written = await saveViewPatch(client, tableId, w.id, { position: w.position, ..."section" in w ? { section: w.section ?? null } : {} });
|
|
39201
|
+
if (!written.ok) {
|
|
39202
|
+
setError(written.error);
|
|
39203
|
+
break;
|
|
39204
|
+
}
|
|
39205
|
+
}
|
|
39206
|
+
if (writes.length > 0) await load();
|
|
39207
|
+
}
|
|
39025
39208
|
const toggleShut = (name) => {
|
|
39026
39209
|
setShut((all) => {
|
|
39027
39210
|
const next = all.includes(name) ? all.filter((n) => n !== name) : [...all, name];
|
|
@@ -39234,83 +39417,89 @@ function ViewBar({ tableId, activeViewId, onActiveView, seed, settings, onViews,
|
|
|
39234
39417
|
) }),
|
|
39235
39418
|
/* @__PURE__ */ jsxs119(PopoverContent16, { sizing: "content", align: "start", className: "w-64 p-1", "data-view-picker-content": "", children: [
|
|
39236
39419
|
/* @__PURE__ */ jsxs119("div", { role: "group", "aria-label": "Saved views", className: "flex max-h-[50dvh] flex-col overflow-y-auto", children: [
|
|
39237
|
-
|
|
39238
|
-
|
|
39239
|
-
|
|
39240
|
-
|
|
39241
|
-
|
|
39242
|
-
|
|
39243
|
-
|
|
39244
|
-
|
|
39245
|
-
|
|
39246
|
-
|
|
39247
|
-
|
|
39248
|
-
|
|
39249
|
-
|
|
39250
|
-
|
|
39251
|
-
|
|
39252
|
-
|
|
39253
|
-
|
|
39254
|
-
|
|
39255
|
-
|
|
39256
|
-
|
|
39257
|
-
|
|
39258
|
-
|
|
39259
|
-
|
|
39260
|
-
|
|
39261
|
-
|
|
39262
|
-
|
|
39263
|
-
|
|
39264
|
-
|
|
39265
|
-
|
|
39266
|
-
|
|
39267
|
-
|
|
39268
|
-
|
|
39420
|
+
/* @__PURE__ */ jsx131(DndContext, { sensors, collisionDetection: closestCenter, onDragStart: () => setDragging(true), onDragCancel: () => setDragging(false), onDragEnd: (e) => void dropped(e), children: (() => {
|
|
39421
|
+
const groups = groupViewsBySection(views);
|
|
39422
|
+
return groups.some((g) => g.name === null) || !dragging ? groups : [{ name: null, views: [] }, ...groups];
|
|
39423
|
+
})().map((group) => /* @__PURE__ */ jsxs119(SectionBox, { id: sectionDropId(group.name), role: "group", "aria-label": group.name ?? "Views", "data-view-section": group.name ?? "", children: [
|
|
39424
|
+
group.name === null && group.views.length === 0 ? /* @__PURE__ */ jsx131("span", { className: "block px-2 py-1.5 text-[11px] text-muted-foreground", children: "No section" }) : null,
|
|
39425
|
+
/* @__PURE__ */ jsxs119(SortableContext, { items: group.views.map((v) => v.id), strategy: verticalListSortingStrategy, children: [
|
|
39426
|
+
group.name !== null ? renamingSection?.from === group.name ? /* @__PURE__ */ jsxs119(
|
|
39427
|
+
"form",
|
|
39428
|
+
{
|
|
39429
|
+
className: "flex items-center gap-1 px-1 py-1",
|
|
39430
|
+
onSubmit: (e) => {
|
|
39431
|
+
e.preventDefault();
|
|
39432
|
+
void renameSection(group.name, renamingSection.draft);
|
|
39433
|
+
},
|
|
39434
|
+
children: [
|
|
39435
|
+
/* @__PURE__ */ jsx131(
|
|
39436
|
+
Input6,
|
|
39437
|
+
{
|
|
39438
|
+
autoFocus: true,
|
|
39439
|
+
"aria-label": "New name for this section",
|
|
39440
|
+
value: renamingSection.draft,
|
|
39441
|
+
onChange: (e) => setRenamingSection({ from: group.name, draft: e.target.value }),
|
|
39442
|
+
onKeyDown: (e) => {
|
|
39443
|
+
if (e.key === "Escape") {
|
|
39444
|
+
e.preventDefault();
|
|
39445
|
+
e.stopPropagation();
|
|
39446
|
+
setRenamingSection(null);
|
|
39447
|
+
}
|
|
39448
|
+
},
|
|
39449
|
+
className: "h-7 min-w-0 flex-1 text-xs"
|
|
39450
|
+
}
|
|
39451
|
+
),
|
|
39452
|
+
/* @__PURE__ */ jsx131(Button80, { size: "sm", type: "submit", className: "h-7", children: "Save" })
|
|
39453
|
+
]
|
|
39454
|
+
}
|
|
39455
|
+
) : /* @__PURE__ */ jsxs119("div", { className: "group flex min-h-7 items-center gap-1 px-2 text-[11px] font-medium uppercase tracking-wide text-muted-foreground", children: [
|
|
39456
|
+
/* @__PURE__ */ jsxs119(
|
|
39457
|
+
"button",
|
|
39458
|
+
{
|
|
39459
|
+
type: "button",
|
|
39460
|
+
className: "flex min-w-0 flex-1 items-center gap-1 text-left",
|
|
39461
|
+
"aria-expanded": !shut.includes(group.name),
|
|
39462
|
+
"data-view-section-toggle": "",
|
|
39463
|
+
onClick: () => toggleShut(group.name),
|
|
39464
|
+
children: [
|
|
39465
|
+
/* @__PURE__ */ jsx131("svg", { viewBox: "0 0 24 24", className: cn65("h-3 w-3 shrink-0", shut.includes(group.name) && "-rotate-90"), fill: "none", stroke: "currentColor", strokeWidth: "2", strokeLinecap: "round", strokeLinejoin: "round", "aria-hidden": "true", children: /* @__PURE__ */ jsx131("path", { d: "m6 9 6 6 6-6" }) }),
|
|
39466
|
+
/* @__PURE__ */ jsx131("span", { className: "truncate", children: group.name }),
|
|
39467
|
+
/* @__PURE__ */ jsx131("span", { className: "shrink-0 font-normal normal-case", children: group.views.length })
|
|
39468
|
+
]
|
|
39469
|
+
}
|
|
39470
|
+
),
|
|
39471
|
+
rights.admin ? /* @__PURE__ */ jsxs119(Fragment49, { children: [
|
|
39472
|
+
/* @__PURE__ */ jsx131("button", { type: "button", className: "shrink-0 normal-case hover:text-foreground", "data-view-section-rename": "", onClick: () => setRenamingSection({ from: group.name, draft: group.name }), children: "Rename" }),
|
|
39473
|
+
/* @__PURE__ */ jsx131("button", { type: "button", className: "shrink-0 normal-case hover:text-destructive", "data-view-section-delete": "", title: "The views stay; they leave the section", onClick: () => void renameSection(group.name, null), children: "Delete" })
|
|
39474
|
+
] }) : null
|
|
39475
|
+
] }) : null,
|
|
39476
|
+
group.name !== null && shut.includes(group.name) && !group.views.some((v) => v.id === active) ? null : group.views.map((view) => /* @__PURE__ */ jsx131(SortableRow, { id: view.id, disabled: !(rights.admin || view.personal) || view.presentation?.locked === true, children: /* @__PURE__ */ jsxs119(
|
|
39269
39477
|
"button",
|
|
39270
39478
|
{
|
|
39271
39479
|
type: "button",
|
|
39272
|
-
|
|
39273
|
-
|
|
39274
|
-
|
|
39275
|
-
|
|
39480
|
+
"aria-pressed": view.id === active,
|
|
39481
|
+
className: cn65(
|
|
39482
|
+
"flex min-h-8 w-full items-center gap-2 rounded-sm px-2 text-left text-xs text-popover-foreground hover:bg-accent hover:text-accent-foreground",
|
|
39483
|
+
group.name !== null && "pl-4",
|
|
39484
|
+
view.id === active && "font-medium"
|
|
39485
|
+
),
|
|
39486
|
+
onClick: () => {
|
|
39487
|
+
if (justDragged.current) return;
|
|
39488
|
+
setActive(view.id);
|
|
39489
|
+
onActiveView?.(view);
|
|
39490
|
+
setOpen(false);
|
|
39491
|
+
},
|
|
39492
|
+
title: view.ruleId ? "Membership is this view's Rule" : "The whole table",
|
|
39276
39493
|
children: [
|
|
39277
|
-
/* @__PURE__ */ jsx131("
|
|
39278
|
-
/* @__PURE__ */ jsx131("
|
|
39279
|
-
/* @__PURE__ */ jsx131("
|
|
39494
|
+
/* @__PURE__ */ jsx131("span", { className: "min-w-0 flex-1 truncate", children: view.name }),
|
|
39495
|
+
view.presentation?.locked === true ? /* @__PURE__ */ jsx131(Badge15, { variant: "neutral", className: "shrink-0 px-1.5 py-0 text-[10px]", "data-view-locked": "", title: VIEW_LOCKED_REASON, children: "Locked" }) : null,
|
|
39496
|
+
view.personal ? /* @__PURE__ */ jsx131(Badge15, { variant: "neutral", className: "shrink-0 px-1.5 py-0 text-[10px]", "data-view-personal": "", title: "Only you see this view", children: "Personal" }) : null,
|
|
39497
|
+
view.isDefault ? /* @__PURE__ */ jsx131(Badge15, { variant: "neutral", className: "shrink-0 px-1.5 py-0 text-[10px]", "data-view-default": "", children: "Default" }) : null
|
|
39280
39498
|
]
|
|
39281
39499
|
}
|
|
39282
|
-
),
|
|
39283
|
-
|
|
39284
|
-
|
|
39285
|
-
/* @__PURE__ */ jsx131("button", { type: "button", className: "shrink-0 normal-case hover:text-destructive", "data-view-section-delete": "", title: "The views stay; they leave the section", onClick: () => void renameSection(group.name, null), children: "Delete" })
|
|
39286
|
-
] }) : null
|
|
39287
|
-
] }) : null,
|
|
39288
|
-
group.name !== null && shut.includes(group.name) && !group.views.some((v) => v.id === active) ? null : group.views.map((view) => /* @__PURE__ */ jsxs119(
|
|
39289
|
-
"button",
|
|
39290
|
-
{
|
|
39291
|
-
type: "button",
|
|
39292
|
-
"aria-pressed": view.id === active,
|
|
39293
|
-
className: cn65(
|
|
39294
|
-
"flex min-h-8 w-full items-center gap-2 rounded-sm px-2 text-left text-xs text-popover-foreground hover:bg-accent hover:text-accent-foreground",
|
|
39295
|
-
group.name !== null && "pl-4",
|
|
39296
|
-
view.id === active && "font-medium"
|
|
39297
|
-
),
|
|
39298
|
-
onClick: () => {
|
|
39299
|
-
setActive(view.id);
|
|
39300
|
-
onActiveView?.(view);
|
|
39301
|
-
setOpen(false);
|
|
39302
|
-
},
|
|
39303
|
-
title: view.ruleId ? "Membership is this view's Rule" : "The whole table",
|
|
39304
|
-
children: [
|
|
39305
|
-
/* @__PURE__ */ jsx131("span", { className: "min-w-0 flex-1 truncate", children: view.name }),
|
|
39306
|
-
view.presentation?.locked === true ? /* @__PURE__ */ jsx131(Badge15, { variant: "neutral", className: "shrink-0 px-1.5 py-0 text-[10px]", "data-view-locked": "", title: VIEW_LOCKED_REASON, children: "Locked" }) : null,
|
|
39307
|
-
view.personal ? /* @__PURE__ */ jsx131(Badge15, { variant: "neutral", className: "shrink-0 px-1.5 py-0 text-[10px]", "data-view-personal": "", title: "Only you see this view", children: "Personal" }) : null,
|
|
39308
|
-
view.isDefault ? /* @__PURE__ */ jsx131(Badge15, { variant: "neutral", className: "shrink-0 px-1.5 py-0 text-[10px]", "data-view-default": "", children: "Default" }) : null
|
|
39309
|
-
]
|
|
39310
|
-
},
|
|
39311
|
-
view.id
|
|
39312
|
-
))
|
|
39313
|
-
] }, group.name ?? "__loose")),
|
|
39500
|
+
) }, view.id))
|
|
39501
|
+
] })
|
|
39502
|
+
] }, group.name ?? "__loose")) }),
|
|
39314
39503
|
views.length === 0 && !rights.admin ? /* @__PURE__ */ jsx131("span", { className: "px-2 py-1 text-xs text-muted-foreground", children: rights.why("structure") }) : null
|
|
39315
39504
|
] }),
|
|
39316
39505
|
/* @__PURE__ */ jsx131("div", { className: "mt-1 border-t border-border pt-1", children: naming ? /* @__PURE__ */ jsxs119(
|
|
@@ -44610,9 +44799,9 @@ function SubscriptionsPanel({ tableId, activeRuleId, className }) {
|
|
|
44610
44799
|
import { copyText as copyText8 } from "@ai-matrx/kit/clipboard";
|
|
44611
44800
|
import { ErrorBox as ErrorBox7 } from "@ai-matrx/design-system";
|
|
44612
44801
|
import { useCallback as useCallback56, useEffect as useEffect106, useMemo as useMemo73, useRef as useRef58, useState as useState127 } from "react";
|
|
44613
|
-
import { DndContext, KeyboardSensor, PointerSensor, closestCenter, useSensor, useSensors } from "@dnd-kit/core";
|
|
44614
|
-
import { SortableContext, arrayMove, sortableKeyboardCoordinates, useSortable, verticalListSortingStrategy } from "@dnd-kit/sortable";
|
|
44615
|
-
import { CSS as
|
|
44802
|
+
import { DndContext as DndContext2, KeyboardSensor, PointerSensor as PointerSensor2, closestCenter as closestCenter2, useSensor as useSensor2, useSensors as useSensors2 } from "@dnd-kit/core";
|
|
44803
|
+
import { SortableContext as SortableContext2, arrayMove, sortableKeyboardCoordinates, useSortable as useSortable2, verticalListSortingStrategy as verticalListSortingStrategy2 } from "@dnd-kit/sortable";
|
|
44804
|
+
import { CSS as CSS3 } from "@dnd-kit/utilities";
|
|
44616
44805
|
import { useFields as useFields28, useRecordsClient as useRecordsClient89, useTable as useTable30 } from "@ai-matrx/records/react";
|
|
44617
44806
|
import { publicFormPath } from "@ai-matrx/records";
|
|
44618
44807
|
import {
|
|
@@ -46269,9 +46458,9 @@ function QuestionList({
|
|
|
46269
46458
|
onQuestions,
|
|
46270
46459
|
onQuestion
|
|
46271
46460
|
}) {
|
|
46272
|
-
const sensors =
|
|
46273
|
-
|
|
46274
|
-
|
|
46461
|
+
const sensors = useSensors2(
|
|
46462
|
+
useSensor2(PointerSensor2, { activationConstraint: { distance: 4 } }),
|
|
46463
|
+
useSensor2(KeyboardSensor, { coordinateGetter: sortableKeyboardCoordinates })
|
|
46275
46464
|
);
|
|
46276
46465
|
const askable = askableFields([...fields]);
|
|
46277
46466
|
const unasked = askable.filter((f) => !draft.questions.some((q) => q.field === f.key));
|
|
@@ -46293,7 +46482,7 @@ function QuestionList({
|
|
|
46293
46482
|
/* @__PURE__ */ jsx151("span", { className: "font-medium text-foreground", children: "Questions" }),
|
|
46294
46483
|
/* @__PURE__ */ jsx151("span", { className: "tabular-nums", children: draft.questions.length })
|
|
46295
46484
|
] }),
|
|
46296
|
-
/* @__PURE__ */ jsx151(
|
|
46485
|
+
/* @__PURE__ */ jsx151(DndContext2, { sensors, collisionDetection: closestCenter2, onDragEnd: dragEnd, children: /* @__PURE__ */ jsx151(SortableContext2, { items: draft.questions.map((q) => q.field), strategy: verticalListSortingStrategy2, children: draft.questions.map((question, index) => /* @__PURE__ */ jsx151(
|
|
46297
46486
|
QuestionRow,
|
|
46298
46487
|
{
|
|
46299
46488
|
index,
|
|
@@ -46346,14 +46535,14 @@ function QuestionRow({
|
|
|
46346
46535
|
onChange,
|
|
46347
46536
|
onRemove
|
|
46348
46537
|
}) {
|
|
46349
|
-
const sortable =
|
|
46538
|
+
const sortable = useSortable2({ id: question.field });
|
|
46350
46539
|
const [open, setOpen] = useState127(true);
|
|
46351
46540
|
const name = field2 ? fieldName(field2) : question.field;
|
|
46352
46541
|
return /* @__PURE__ */ jsxs139(
|
|
46353
46542
|
"div",
|
|
46354
46543
|
{
|
|
46355
46544
|
ref: sortable.setNodeRef,
|
|
46356
|
-
style: { transform:
|
|
46545
|
+
style: { transform: CSS3.Transform.toString(sortable.transform), transition: sortable.transition },
|
|
46357
46546
|
className: cn84("rounded border bg-background px-2 py-1.5", sortable.isDragging && "z-10 shadow-md"),
|
|
46358
46547
|
"data-records-form-question-row": question.field,
|
|
46359
46548
|
children: [
|
|
@@ -47303,20 +47492,20 @@ import {
|
|
|
47303
47492
|
|
|
47304
47493
|
// src/DashboardGrid.tsx
|
|
47305
47494
|
import {
|
|
47306
|
-
DndContext as
|
|
47495
|
+
DndContext as DndContext3,
|
|
47307
47496
|
KeyboardSensor as KeyboardSensor2,
|
|
47308
|
-
PointerSensor as
|
|
47497
|
+
PointerSensor as PointerSensor3,
|
|
47309
47498
|
pointerWithin,
|
|
47310
|
-
useSensor as
|
|
47311
|
-
useSensors as
|
|
47499
|
+
useSensor as useSensor3,
|
|
47500
|
+
useSensors as useSensors3
|
|
47312
47501
|
} from "@dnd-kit/core";
|
|
47313
47502
|
import {
|
|
47314
|
-
SortableContext as
|
|
47503
|
+
SortableContext as SortableContext3,
|
|
47315
47504
|
rectSortingStrategy,
|
|
47316
47505
|
sortableKeyboardCoordinates as sortableKeyboardCoordinates2,
|
|
47317
|
-
useSortable as
|
|
47506
|
+
useSortable as useSortable3
|
|
47318
47507
|
} from "@dnd-kit/sortable";
|
|
47319
|
-
import { CSS as
|
|
47508
|
+
import { CSS as CSS4 } from "@dnd-kit/utilities";
|
|
47320
47509
|
import { cn as cn89 } from "@ai-matrx/design-system";
|
|
47321
47510
|
|
|
47322
47511
|
// src/dashboardLayout.ts
|
|
@@ -47380,9 +47569,9 @@ var dashboardCollision = (args) => {
|
|
|
47380
47569
|
}).sort((a, b) => a.data.value - b.data.value);
|
|
47381
47570
|
};
|
|
47382
47571
|
function DashboardGrid({ items, arranging, onMove, onSpan }) {
|
|
47383
|
-
const sensors =
|
|
47384
|
-
|
|
47385
|
-
|
|
47572
|
+
const sensors = useSensors3(
|
|
47573
|
+
useSensor3(PointerSensor3, { activationConstraint: { distance: 4 } }),
|
|
47574
|
+
useSensor3(KeyboardSensor2, { coordinateGetter: sortableKeyboardCoordinates2 })
|
|
47386
47575
|
);
|
|
47387
47576
|
const ids = items.map((item) => item.id);
|
|
47388
47577
|
function dragEnd(event) {
|
|
@@ -47392,7 +47581,7 @@ function DashboardGrid({ items, arranging, onMove, onSpan }) {
|
|
|
47392
47581
|
}
|
|
47393
47582
|
const grid = /* @__PURE__ */ jsx156("div", { className: "grid grid-cols-1 gap-2 sm:grid-cols-12", children: items.map((item, index) => /* @__PURE__ */ jsx156(GridCell2, { item, index, arranging, onSpan }, item.id)) });
|
|
47394
47583
|
if (!arranging) return grid;
|
|
47395
|
-
return /* @__PURE__ */ jsx156(
|
|
47584
|
+
return /* @__PURE__ */ jsx156(DndContext3, { sensors, collisionDetection: dashboardCollision, onDragEnd: dragEnd, children: /* @__PURE__ */ jsx156(SortableContext3, { items: ids, strategy: rectSortingStrategy, children: grid }) });
|
|
47396
47585
|
}
|
|
47397
47586
|
function GridCell2({
|
|
47398
47587
|
item,
|
|
@@ -47400,8 +47589,8 @@ function GridCell2({
|
|
|
47400
47589
|
arranging,
|
|
47401
47590
|
onSpan
|
|
47402
47591
|
}) {
|
|
47403
|
-
const sortable =
|
|
47404
|
-
const style = arranging ? { transform:
|
|
47592
|
+
const sortable = useSortable3({ id: item.id, disabled: !arranging });
|
|
47593
|
+
const style = arranging ? { transform: CSS4.Transform.toString(sortable.transform), transition: sortable.transition } : void 0;
|
|
47405
47594
|
return /* @__PURE__ */ jsxs144(
|
|
47406
47595
|
"div",
|
|
47407
47596
|
{
|