@abraca/nuxt 1.6.0 → 1.8.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/module.d.mts +6 -0
- package/dist/module.json +1 -1
- package/dist/module.mjs +16 -2
- package/dist/runtime/assets/sources.css +1 -0
- package/dist/runtime/components/ADocumentTree.d.vue.ts +11 -1
- package/dist/runtime/components/ADocumentTree.vue +13 -6
- package/dist/runtime/components/ADocumentTree.vue.d.ts +11 -1
- package/dist/runtime/components/renderers/AChecklistRenderer.vue +22 -4
- package/dist/runtime/components/renderers/ADashboardRenderer.vue +4 -2
- package/dist/runtime/components/renderers/AGalleryRenderer.vue +97 -70
- package/dist/runtime/components/renderers/AGraphRenderer.vue +209 -58
- package/dist/runtime/components/renderers/AKanbanRenderer.vue +145 -34
- package/dist/runtime/components/renderers/AMediaRenderer.vue +27 -17
- package/dist/runtime/components/renderers/AOutlineRenderer.vue +38 -23
- package/dist/runtime/components/renderers/ASlidesRenderer.d.vue.ts +21 -0
- package/dist/runtime/components/renderers/ASlidesRenderer.vue +591 -0
- package/dist/runtime/components/renderers/ASlidesRenderer.vue.d.ts +21 -0
- package/dist/runtime/components/renderers/ASpatialRenderer.vue +23 -0
- package/dist/runtime/components/renderers/ATableRenderer.vue +20 -391
- package/dist/runtime/components/renderers/gallery/AGalleryItemCard.d.vue.ts +40 -0
- package/dist/runtime/components/renderers/gallery/AGalleryItemCard.vue +227 -0
- package/dist/runtime/components/renderers/gallery/AGalleryItemCard.vue.d.ts +40 -0
- package/dist/runtime/components/renderers/spatial/SpatialTransformInputs.d.vue.ts +16 -0
- package/dist/runtime/components/renderers/spatial/SpatialTransformInputs.vue +66 -0
- package/dist/runtime/components/renderers/spatial/SpatialTransformInputs.vue.d.ts +16 -0
- package/dist/runtime/components/renderers/table/ATableFlatMode.d.vue.ts +2 -0
- package/dist/runtime/components/renderers/table/ATableFlatMode.vue +184 -21
- package/dist/runtime/components/renderers/table/ATableFlatMode.vue.d.ts +2 -0
- package/dist/runtime/components/renderers/table/ATableHierarchyMode.d.vue.ts +26 -0
- package/dist/runtime/components/renderers/table/ATableHierarchyMode.vue +662 -0
- package/dist/runtime/components/renderers/table/ATableHierarchyMode.vue.d.ts +26 -0
- package/dist/runtime/composables/useAwareness.js +14 -3
- package/dist/runtime/composables/useBackgroundSync.js +19 -1
- package/dist/runtime/composables/useFileIndex.js +38 -17
- package/dist/runtime/composables/useSearchIndex.js +41 -16
- package/dist/runtime/composables/useSlidesNavigation.d.ts +45 -0
- package/dist/runtime/composables/useSlidesNavigation.js +185 -0
- package/dist/runtime/composables/useYDoc.d.ts +1 -1
- package/dist/runtime/composables/useYDoc.js +47 -9
- package/dist/runtime/locale.d.ts +38 -0
- package/dist/runtime/locale.js +41 -3
- package/dist/runtime/utils/docTypes.js +17 -0
- package/package.json +3 -3
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
import { type RendererBaseProps } from '../../composables/useRendererBase.js';
|
|
2
|
+
import type { AbracadabraLocale } from '../../locale.js';
|
|
3
|
+
type __VLS_Props = RendererBaseProps & {
|
|
4
|
+
labels?: Partial<AbracadabraLocale['renderers']['slides']>;
|
|
5
|
+
editable?: boolean;
|
|
6
|
+
followingUser?: string | null;
|
|
7
|
+
};
|
|
8
|
+
declare const __VLS_export: import("vue").DefineComponent<__VLS_Props, {
|
|
9
|
+
connectedUsers: import("vue").ComputedRef<{
|
|
10
|
+
clientId: number;
|
|
11
|
+
name: string;
|
|
12
|
+
color: string;
|
|
13
|
+
avatar: string | undefined;
|
|
14
|
+
publicKey: any;
|
|
15
|
+
}[]>;
|
|
16
|
+
}, {}, {}, {}, import("vue").ComponentOptionsMixin, import("vue").ComponentOptionsMixin, {}, string, import("vue").PublicProps, Readonly<__VLS_Props> & Readonly<{}>, {
|
|
17
|
+
editable: boolean;
|
|
18
|
+
followingUser: string | null;
|
|
19
|
+
}, {}, {}, {}, string, import("vue").ComponentProvideOptions, false, {}, any>;
|
|
20
|
+
declare const _default: typeof __VLS_export;
|
|
21
|
+
export default _default;
|
|
@@ -5,6 +5,7 @@ import { useRendererBase } from "../../composables/useRendererBase";
|
|
|
5
5
|
import { useNodePanel } from "../../composables/useNodePanel";
|
|
6
6
|
import { useSpatialCamera } from "../../composables/useSpatialCamera";
|
|
7
7
|
import { useSpatialDrag } from "../../composables/useSpatialDrag";
|
|
8
|
+
import SpatialTransformInputs from "./spatial/SpatialTransformInputs.vue";
|
|
8
9
|
const props = defineProps({
|
|
9
10
|
docId: { type: String, required: true },
|
|
10
11
|
childProvider: { type: null, required: true },
|
|
@@ -371,6 +372,21 @@ defineExpose({ connectedUsers });
|
|
|
371
372
|
/>
|
|
372
373
|
</div>
|
|
373
374
|
|
|
375
|
+
<!-- Shape selector (hide for GLB — shape comes from the file) -->
|
|
376
|
+
<div
|
|
377
|
+
v-if="editable && selectedEntry.meta?.spShape !== 'glb'"
|
|
378
|
+
class="sp-prop-row"
|
|
379
|
+
>
|
|
380
|
+
<span class="sp-prop-label">Shape</span>
|
|
381
|
+
<USelectMenu
|
|
382
|
+
:model-value="selectedEntry.meta?.spShape ?? 'box'"
|
|
383
|
+
:items="shapes"
|
|
384
|
+
size="xs"
|
|
385
|
+
class="flex-1"
|
|
386
|
+
@update:model-value="tree.updateMeta(selectedEntry.id, { spShape: $event })"
|
|
387
|
+
/>
|
|
388
|
+
</div>
|
|
389
|
+
|
|
374
390
|
<div
|
|
375
391
|
v-if="editable && selectedEntry.meta?.spShape !== 'glb'"
|
|
376
392
|
class="sp-prop-row"
|
|
@@ -403,6 +419,13 @@ defineExpose({ connectedUsers });
|
|
|
403
419
|
>
|
|
404
420
|
<span class="text-[10px] w-7 text-right text-(--ui-text-dimmed)">{{ selectedEntry.meta?.spOpacity ?? 100 }}%</span>
|
|
405
421
|
</div>
|
|
422
|
+
|
|
423
|
+
<!-- Transform inputs (Pos / Rot / Scale) -->
|
|
424
|
+
<SpatialTransformInputs
|
|
425
|
+
v-if="editable"
|
|
426
|
+
:entry="selectedEntry"
|
|
427
|
+
:tree="tree"
|
|
428
|
+
/>
|
|
406
429
|
</div>
|
|
407
430
|
|
|
408
431
|
<!-- Connected users -->
|
|
@@ -2,12 +2,12 @@
|
|
|
2
2
|
import { ref, computed, watch, onBeforeUnmount } from "vue";
|
|
3
3
|
import { useRuntimeConfig } from "#imports";
|
|
4
4
|
import { useRendererBase } from "../../composables/useRendererBase";
|
|
5
|
-
import { useTouchDrag } from "../../composables/useTouchDrag";
|
|
6
5
|
import { useNodePanel } from "../../composables/useNodePanel";
|
|
7
6
|
import { useTableView } from "../../composables/useTableView";
|
|
8
7
|
import { DEFAULT_LOCALE } from "../../locale";
|
|
9
8
|
import ATableToolbar from "./table/ATableToolbar.vue";
|
|
10
9
|
import ATableFlatMode from "./table/ATableFlatMode.vue";
|
|
10
|
+
import ATableHierarchyMode from "./table/ATableHierarchyMode.vue";
|
|
11
11
|
const props = defineProps({
|
|
12
12
|
docId: { type: String, required: true },
|
|
13
13
|
childProvider: { type: null, required: true },
|
|
@@ -36,215 +36,25 @@ const rowCount = computed(() => {
|
|
|
36
36
|
if (tableView.effectiveMode.value === "flat") {
|
|
37
37
|
return tree.childrenOf(null).length;
|
|
38
38
|
}
|
|
39
|
-
const
|
|
40
|
-
return Math.max(0, ...
|
|
39
|
+
const columns = tree.childrenOf(null);
|
|
40
|
+
return Math.max(0, ...columns.map((c) => tree.childrenOf(c.id).length));
|
|
41
41
|
});
|
|
42
42
|
const flatRef = ref(null);
|
|
43
|
+
const hierarchyRef = ref(null);
|
|
43
44
|
function handleAddColumn() {
|
|
44
45
|
if (tableView.effectiveMode.value === "hierarchy") {
|
|
45
|
-
|
|
46
|
+
hierarchyRef.value?.addColumn();
|
|
46
47
|
} else {
|
|
47
48
|
flatRef.value?.addMetaColumn();
|
|
48
49
|
}
|
|
49
50
|
}
|
|
50
51
|
function handleAddRow() {
|
|
51
52
|
if (tableView.effectiveMode.value === "hierarchy") {
|
|
52
|
-
|
|
53
|
+
hierarchyRef.value?.addRow();
|
|
53
54
|
} else {
|
|
54
55
|
flatRef.value?.addRow();
|
|
55
56
|
}
|
|
56
57
|
}
|
|
57
|
-
const INTERNAL_META_KEYS = /* @__PURE__ */ new Set([
|
|
58
|
-
"_metaFields",
|
|
59
|
-
"_metaInitialized",
|
|
60
|
-
"coverUploadId",
|
|
61
|
-
"coverDocId",
|
|
62
|
-
"coverMimeType",
|
|
63
|
-
"geoType",
|
|
64
|
-
"geoLat",
|
|
65
|
-
"geoLng",
|
|
66
|
-
"icon",
|
|
67
|
-
"color",
|
|
68
|
-
"geoDescription"
|
|
69
|
-
]);
|
|
70
|
-
const UUID_RE = /^[0-9a-f]{8}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{12}$/i;
|
|
71
|
-
function camelToTitle(s) {
|
|
72
|
-
return s.replace(/([a-z])([A-Z])/g, "$1 $2").replace(/([A-Z]+)([A-Z][a-z])/g, "$1 $2").replace(/^./, (c) => c.toUpperCase());
|
|
73
|
-
}
|
|
74
|
-
const columns = computed(
|
|
75
|
-
() => tree.childrenOf(null).sort((a, b) => (a.order ?? 0) - (b.order ?? 0))
|
|
76
|
-
);
|
|
77
|
-
const colChildren = computed(() => {
|
|
78
|
-
const map = /* @__PURE__ */ new Map();
|
|
79
|
-
for (const col of columns.value) {
|
|
80
|
-
map.set(col.id, tree.childrenOf(col.id).sort((a, b) => (a.order ?? 0) - (b.order ?? 0)));
|
|
81
|
-
}
|
|
82
|
-
return map;
|
|
83
|
-
});
|
|
84
|
-
const hierarchyRowCount = computed(
|
|
85
|
-
() => Math.max(0, ...columns.value.map((c) => colChildren.value.get(c.id)?.length ?? 0))
|
|
86
|
-
);
|
|
87
|
-
function getCellEntry(colId, rowIdx) {
|
|
88
|
-
return colChildren.value.get(colId)?.[rowIdx];
|
|
89
|
-
}
|
|
90
|
-
function getRowRep(rowIdx) {
|
|
91
|
-
for (const col of columns.value) {
|
|
92
|
-
const entry = getCellEntry(col.id, rowIdx);
|
|
93
|
-
if (entry) return entry;
|
|
94
|
-
}
|
|
95
|
-
return void 0;
|
|
96
|
-
}
|
|
97
|
-
const metaColumns = computed(() => {
|
|
98
|
-
const colIds = new Set(columns.value.map((c) => c.id));
|
|
99
|
-
const keys = /* @__PURE__ */ new Set();
|
|
100
|
-
for (const col of columns.value) {
|
|
101
|
-
const children = colChildren.value.get(col.id) ?? [];
|
|
102
|
-
for (const cell of children) {
|
|
103
|
-
if (!cell.meta) continue;
|
|
104
|
-
for (const key of Object.keys(cell.meta)) {
|
|
105
|
-
if (INTERNAL_META_KEYS.has(key)) continue;
|
|
106
|
-
if (UUID_RE.test(key)) continue;
|
|
107
|
-
if (colIds.has(key)) continue;
|
|
108
|
-
keys.add(key);
|
|
109
|
-
}
|
|
110
|
-
}
|
|
111
|
-
}
|
|
112
|
-
return [...keys].sort().map((key) => ({
|
|
113
|
-
id: `__meta_${key}`,
|
|
114
|
-
label: camelToTitle(key),
|
|
115
|
-
metaKey: key
|
|
116
|
-
}));
|
|
117
|
-
});
|
|
118
|
-
function getCellValue(colId, rowIdx) {
|
|
119
|
-
const entry = getCellEntry(colId, rowIdx);
|
|
120
|
-
return entry?.label && entry.label !== "Untitled" ? entry.label : "";
|
|
121
|
-
}
|
|
122
|
-
function getMetaCellValue(rowIdx, metaKey) {
|
|
123
|
-
for (const col of columns.value) {
|
|
124
|
-
const entry = getCellEntry(col.id, rowIdx);
|
|
125
|
-
if (entry?.meta?.[metaKey] !== void 0) return String(entry.meta[metaKey]);
|
|
126
|
-
}
|
|
127
|
-
return "";
|
|
128
|
-
}
|
|
129
|
-
function setCellValue(colId, rowIdx, value) {
|
|
130
|
-
if (!props.editable) return;
|
|
131
|
-
const entry = getCellEntry(colId, rowIdx);
|
|
132
|
-
if (entry) {
|
|
133
|
-
tree.renameEntry(entry.id, value.trim() || "Untitled");
|
|
134
|
-
} else {
|
|
135
|
-
tree.createChild(colId, value.trim() || "Untitled");
|
|
136
|
-
}
|
|
137
|
-
}
|
|
138
|
-
function setMetaCellValue(rowIdx, metaKey, value) {
|
|
139
|
-
if (!props.editable) return;
|
|
140
|
-
const rep = getRowRep(rowIdx);
|
|
141
|
-
if (rep) tree.updateMeta(rep.id, { [metaKey]: value });
|
|
142
|
-
}
|
|
143
|
-
function addHierarchyColumn() {
|
|
144
|
-
if (!props.editable) return;
|
|
145
|
-
tree.createChild(null, "New Column");
|
|
146
|
-
}
|
|
147
|
-
function addHierarchyRow() {
|
|
148
|
-
if (!props.editable) return;
|
|
149
|
-
if (!columns.value[0]) return;
|
|
150
|
-
tree.createChild(columns.value[0].id, "");
|
|
151
|
-
}
|
|
152
|
-
function deleteColumn(col) {
|
|
153
|
-
if (!props.editable) return;
|
|
154
|
-
tree.deleteEntry(col.id);
|
|
155
|
-
}
|
|
156
|
-
function deleteMetaColumn(metaKey) {
|
|
157
|
-
if (!props.editable) return;
|
|
158
|
-
for (const col of columns.value) {
|
|
159
|
-
const children = colChildren.value.get(col.id) ?? [];
|
|
160
|
-
for (const cell of children) {
|
|
161
|
-
if (cell.meta?.[metaKey] !== void 0) {
|
|
162
|
-
const newMeta = { ...cell.meta };
|
|
163
|
-
delete newMeta[metaKey];
|
|
164
|
-
tree.treeMap.set(cell.id, { ...tree.treeMap.get(cell.id), meta: newMeta });
|
|
165
|
-
}
|
|
166
|
-
}
|
|
167
|
-
}
|
|
168
|
-
}
|
|
169
|
-
function deleteRow(rowIdx) {
|
|
170
|
-
if (!props.editable) return;
|
|
171
|
-
for (const col of columns.value) {
|
|
172
|
-
const entry = getCellEntry(col.id, rowIdx);
|
|
173
|
-
if (entry) tree.deleteEntry(entry.id);
|
|
174
|
-
}
|
|
175
|
-
}
|
|
176
|
-
const editingCell = ref(null);
|
|
177
|
-
const editingValue = ref("");
|
|
178
|
-
function startEditDocCol(rowIdx, col) {
|
|
179
|
-
if (!props.editable) return;
|
|
180
|
-
editingCell.value = { rowIdx, colId: col.id };
|
|
181
|
-
editingValue.value = getCellValue(col.id, rowIdx);
|
|
182
|
-
setLocalState({ "table:editing": { rowIdx, fieldId: col.id } });
|
|
183
|
-
}
|
|
184
|
-
function startEditMetaCol(rowIdx, mc) {
|
|
185
|
-
if (!props.editable) return;
|
|
186
|
-
editingCell.value = { rowIdx, colId: mc.id, metaKey: mc.metaKey };
|
|
187
|
-
editingValue.value = getMetaCellValue(rowIdx, mc.metaKey);
|
|
188
|
-
setLocalState({ "table:editing": { rowIdx, fieldId: mc.id } });
|
|
189
|
-
}
|
|
190
|
-
function commitEdit() {
|
|
191
|
-
if (!editingCell.value) return;
|
|
192
|
-
if (editingCell.value.metaKey) {
|
|
193
|
-
setMetaCellValue(editingCell.value.rowIdx, editingCell.value.metaKey, editingValue.value);
|
|
194
|
-
} else {
|
|
195
|
-
setCellValue(editingCell.value.colId, editingCell.value.rowIdx, editingValue.value);
|
|
196
|
-
}
|
|
197
|
-
editingCell.value = null;
|
|
198
|
-
setLocalState({ "table:editing": null });
|
|
199
|
-
}
|
|
200
|
-
const editingColId = ref(null);
|
|
201
|
-
const editingColValue = ref("");
|
|
202
|
-
function startRenameCol(col) {
|
|
203
|
-
if (!props.editable) return;
|
|
204
|
-
editingColId.value = col.id;
|
|
205
|
-
editingColValue.value = col.label;
|
|
206
|
-
}
|
|
207
|
-
function commitRenameCol() {
|
|
208
|
-
if (!props.editable) return;
|
|
209
|
-
if (editingColId.value && editingColValue.value.trim()) {
|
|
210
|
-
tree.renameEntry(editingColId.value, editingColValue.value.trim());
|
|
211
|
-
}
|
|
212
|
-
editingColId.value = null;
|
|
213
|
-
}
|
|
214
|
-
function rowIdxFromDragId(id) {
|
|
215
|
-
return Number.parseInt(id.replace("row-", ""), 10);
|
|
216
|
-
}
|
|
217
|
-
const {
|
|
218
|
-
dragId: rowDragId,
|
|
219
|
-
dragOverId: rowDragOverId,
|
|
220
|
-
handlePointerDown: handleRowPointerDown
|
|
221
|
-
} = useTouchDrag({
|
|
222
|
-
idAttr: "data-drag-id",
|
|
223
|
-
onDrop: (srcDragId, targetDragId) => {
|
|
224
|
-
if (!props.editable) return;
|
|
225
|
-
const srcIdx = rowIdxFromDragId(srcDragId);
|
|
226
|
-
const targetIdx = rowIdxFromDragId(targetDragId);
|
|
227
|
-
if (srcIdx === targetIdx) return;
|
|
228
|
-
for (const col of columns.value) {
|
|
229
|
-
const children = colChildren.value.get(col.id) ?? [];
|
|
230
|
-
const srcEntry = children[srcIdx];
|
|
231
|
-
if (!srcEntry) continue;
|
|
232
|
-
const prev = children[targetIdx - (targetIdx > srcIdx ? 0 : 1)];
|
|
233
|
-
const next = children[targetIdx + (targetIdx > srcIdx ? 1 : 0)];
|
|
234
|
-
let newOrder;
|
|
235
|
-
if (!prev && !next) newOrder = Date.now();
|
|
236
|
-
else if (!prev) newOrder = next.order - 1e3;
|
|
237
|
-
else if (!next) newOrder = prev.order + 1e3;
|
|
238
|
-
else newOrder = (prev.order + next.order) / 2;
|
|
239
|
-
tree.moveEntry(srcEntry.id, col.id, newOrder);
|
|
240
|
-
}
|
|
241
|
-
}
|
|
242
|
-
});
|
|
243
|
-
function cellEditor(rowIdx, fieldId) {
|
|
244
|
-
return states.value.filter((s) => s.clientId !== myClientId.value).find(
|
|
245
|
-
(s) => s["table:editing"]?.rowIdx === rowIdx && s["table:editing"]?.fieldId === fieldId
|
|
246
|
-
);
|
|
247
|
-
}
|
|
248
58
|
function ensureTableStructure() {
|
|
249
59
|
if (!childDoc.value) return;
|
|
250
60
|
if (tableView.effectiveMode.value !== "hierarchy") return;
|
|
@@ -272,7 +82,7 @@ defineExpose({ connectedUsers });
|
|
|
272
82
|
<!-- Toolbar -->
|
|
273
83
|
<ATableToolbar
|
|
274
84
|
:table-view="tableView"
|
|
275
|
-
:row-count="
|
|
85
|
+
:row-count="rowCount"
|
|
276
86
|
:editable="editable"
|
|
277
87
|
:labels="locale"
|
|
278
88
|
@add-column="handleAddColumn"
|
|
@@ -289,204 +99,23 @@ defineExpose({ connectedUsers });
|
|
|
289
99
|
:my-client-id="myClientId"
|
|
290
100
|
:set-local-state="setLocalState"
|
|
291
101
|
:editable="editable"
|
|
102
|
+
:labels="locale"
|
|
292
103
|
@open-node="(id, label) => openNode(id, label)"
|
|
293
104
|
/>
|
|
294
105
|
|
|
295
|
-
<!-- Hierarchy mode
|
|
296
|
-
<
|
|
106
|
+
<!-- Hierarchy mode -->
|
|
107
|
+
<ATableHierarchyMode
|
|
297
108
|
v-else
|
|
298
|
-
|
|
299
|
-
|
|
300
|
-
|
|
301
|
-
|
|
302
|
-
|
|
303
|
-
|
|
304
|
-
|
|
305
|
-
|
|
306
|
-
|
|
307
|
-
|
|
308
|
-
<p class="text-sm text-(--ui-text-muted)">
|
|
309
|
-
{{ locale.noRows }}
|
|
310
|
-
</p>
|
|
311
|
-
<UButton
|
|
312
|
-
v-if="editable"
|
|
313
|
-
icon="i-lucide-plus"
|
|
314
|
-
:label="locale.addColumn"
|
|
315
|
-
size="sm"
|
|
316
|
-
@click="addHierarchyColumn"
|
|
317
|
-
/>
|
|
318
|
-
</div>
|
|
319
|
-
|
|
320
|
-
<template v-else>
|
|
321
|
-
<table class="w-full text-sm border-collapse">
|
|
322
|
-
<thead class="sticky top-0 bg-(--ui-bg) z-10">
|
|
323
|
-
<tr class="border-b border-(--ui-border)">
|
|
324
|
-
<th class="w-6 px-1" />
|
|
325
|
-
<th class="text-left px-3 py-2 text-xs font-medium text-(--ui-text-muted) w-8">
|
|
326
|
-
#
|
|
327
|
-
</th>
|
|
328
|
-
<th
|
|
329
|
-
v-for="col in columns"
|
|
330
|
-
:key="col.id"
|
|
331
|
-
class="text-left px-3 py-2 text-xs font-medium text-(--ui-text-muted) min-w-32"
|
|
332
|
-
>
|
|
333
|
-
<div class="group flex items-center gap-1">
|
|
334
|
-
<input
|
|
335
|
-
v-if="editingColId === col.id"
|
|
336
|
-
v-model="editingColValue"
|
|
337
|
-
class="bg-transparent outline-none text-xs font-medium w-full"
|
|
338
|
-
autofocus
|
|
339
|
-
@keydown.enter="commitRenameCol"
|
|
340
|
-
@keydown.escape="editingColId = null"
|
|
341
|
-
@blur="commitRenameCol"
|
|
342
|
-
>
|
|
343
|
-
<span
|
|
344
|
-
v-else
|
|
345
|
-
class="cursor-text"
|
|
346
|
-
@dblclick="startRenameCol(col)"
|
|
347
|
-
>
|
|
348
|
-
{{ col.label }}
|
|
349
|
-
</span>
|
|
350
|
-
<UButton
|
|
351
|
-
v-if="editable"
|
|
352
|
-
icon="i-lucide-x"
|
|
353
|
-
size="xs"
|
|
354
|
-
variant="ghost"
|
|
355
|
-
color="neutral"
|
|
356
|
-
class="opacity-0 group-hover:opacity-100"
|
|
357
|
-
@click="deleteColumn(col)"
|
|
358
|
-
/>
|
|
359
|
-
</div>
|
|
360
|
-
</th>
|
|
361
|
-
<th
|
|
362
|
-
v-for="mc in metaColumns"
|
|
363
|
-
:key="mc.id"
|
|
364
|
-
class="text-left px-3 py-2 text-xs font-medium text-(--ui-text-muted) min-w-32"
|
|
365
|
-
>
|
|
366
|
-
<div class="group flex items-center gap-1">
|
|
367
|
-
<span class="cursor-default">{{ mc.label }}</span>
|
|
368
|
-
<UButton
|
|
369
|
-
v-if="editable"
|
|
370
|
-
icon="i-lucide-x"
|
|
371
|
-
size="xs"
|
|
372
|
-
variant="ghost"
|
|
373
|
-
color="neutral"
|
|
374
|
-
class="opacity-0 group-hover:opacity-100"
|
|
375
|
-
@click="deleteMetaColumn(mc.metaKey)"
|
|
376
|
-
/>
|
|
377
|
-
</div>
|
|
378
|
-
</th>
|
|
379
|
-
</tr>
|
|
380
|
-
</thead>
|
|
381
|
-
<TransitionGroup
|
|
382
|
-
name="trow"
|
|
383
|
-
tag="tbody"
|
|
384
|
-
>
|
|
385
|
-
<tr
|
|
386
|
-
v-for="idx in hierarchyRowCount"
|
|
387
|
-
:key="getRowRep(idx - 1)?.id ?? `row-${idx}`"
|
|
388
|
-
:data-drag-id="`row-${idx - 1}`"
|
|
389
|
-
class="hover:bg-(--ui-bg-elevated) group"
|
|
390
|
-
:class="[
|
|
391
|
-
rowDragOverId === `row-${idx - 1}` ? 'border-t-2 border-(--ui-primary)' : 'border-b border-(--ui-border)',
|
|
392
|
-
rowDragId === `row-${idx - 1}` ? 'opacity-30' : ''
|
|
393
|
-
]"
|
|
394
|
-
>
|
|
395
|
-
<td
|
|
396
|
-
class="px-1 py-1.5 text-(--ui-text-dimmed) w-6"
|
|
397
|
-
:class="editable ? 'opacity-0 group-hover:opacity-60 cursor-grab touch-none' : 'opacity-0'"
|
|
398
|
-
v-on="editable ? { pointerdown: ($event) => handleRowPointerDown($event, `row-${idx - 1}`) } : {}"
|
|
399
|
-
>
|
|
400
|
-
<UIcon
|
|
401
|
-
v-if="editable"
|
|
402
|
-
name="i-lucide-grip-vertical"
|
|
403
|
-
class="size-4"
|
|
404
|
-
/>
|
|
405
|
-
</td>
|
|
406
|
-
<td class="px-3 py-1.5 text-xs text-(--ui-text-dimmed) select-none">
|
|
407
|
-
<div class="flex items-center gap-0.5">
|
|
408
|
-
<span class="w-4 text-center">{{ idx }}</span>
|
|
409
|
-
<UButton
|
|
410
|
-
v-if="getRowRep(idx - 1)"
|
|
411
|
-
icon="i-lucide-external-link"
|
|
412
|
-
size="xs"
|
|
413
|
-
variant="ghost"
|
|
414
|
-
color="neutral"
|
|
415
|
-
class="opacity-0 group-hover:opacity-100"
|
|
416
|
-
@click="openNode(getRowRep(idx - 1).id, getRowRep(idx - 1).label)"
|
|
417
|
-
/>
|
|
418
|
-
<UButton
|
|
419
|
-
v-if="editable"
|
|
420
|
-
icon="i-lucide-trash-2"
|
|
421
|
-
size="xs"
|
|
422
|
-
variant="ghost"
|
|
423
|
-
color="error"
|
|
424
|
-
class="opacity-0 group-hover:opacity-100"
|
|
425
|
-
@click="deleteRow(idx - 1)"
|
|
426
|
-
/>
|
|
427
|
-
</div>
|
|
428
|
-
</td>
|
|
429
|
-
<td
|
|
430
|
-
v-for="col in columns"
|
|
431
|
-
:key="col.id"
|
|
432
|
-
class="px-3 py-1.5 cursor-text"
|
|
433
|
-
:style="cellEditor(idx - 1, col.id) ? { outline: `2px solid ${cellEditor(idx - 1, col.id).user?.color}` } : {}"
|
|
434
|
-
@click="startEditDocCol(idx - 1, col)"
|
|
435
|
-
>
|
|
436
|
-
<input
|
|
437
|
-
v-if="editingCell?.rowIdx === idx - 1 && editingCell?.colId === col.id"
|
|
438
|
-
v-model="editingValue"
|
|
439
|
-
class="w-full bg-transparent outline-none text-sm"
|
|
440
|
-
autofocus
|
|
441
|
-
@blur="commitEdit"
|
|
442
|
-
@keydown.enter="commitEdit"
|
|
443
|
-
@keydown.escape="editingCell = null"
|
|
444
|
-
@click.stop
|
|
445
|
-
>
|
|
446
|
-
<span
|
|
447
|
-
v-else
|
|
448
|
-
class="block text-sm text-(--ui-text) min-h-5"
|
|
449
|
-
>
|
|
450
|
-
{{ getCellValue(col.id, idx - 1) }}
|
|
451
|
-
</span>
|
|
452
|
-
</td>
|
|
453
|
-
<td
|
|
454
|
-
v-for="mc in metaColumns"
|
|
455
|
-
:key="mc.id"
|
|
456
|
-
class="px-3 py-1.5 cursor-text"
|
|
457
|
-
:style="cellEditor(idx - 1, mc.id) ? { outline: `2px solid ${cellEditor(idx - 1, mc.id).user?.color}` } : {}"
|
|
458
|
-
@click="startEditMetaCol(idx - 1, mc)"
|
|
459
|
-
>
|
|
460
|
-
<input
|
|
461
|
-
v-if="editingCell?.rowIdx === idx - 1 && editingCell?.colId === mc.id"
|
|
462
|
-
v-model="editingValue"
|
|
463
|
-
class="w-full bg-transparent outline-none text-sm"
|
|
464
|
-
autofocus
|
|
465
|
-
@blur="commitEdit"
|
|
466
|
-
@keydown.enter="commitEdit"
|
|
467
|
-
@keydown.escape="editingCell = null"
|
|
468
|
-
@click.stop
|
|
469
|
-
>
|
|
470
|
-
<span
|
|
471
|
-
v-else
|
|
472
|
-
class="block text-sm text-(--ui-text) min-h-5"
|
|
473
|
-
>
|
|
474
|
-
{{ getMetaCellValue(idx - 1, mc.metaKey) }}
|
|
475
|
-
</span>
|
|
476
|
-
</td>
|
|
477
|
-
</tr>
|
|
478
|
-
</TransitionGroup>
|
|
479
|
-
</table>
|
|
480
|
-
|
|
481
|
-
<button
|
|
482
|
-
v-if="editable"
|
|
483
|
-
class="w-full text-left px-3 py-2 text-xs text-(--ui-text-dimmed) hover:bg-(--ui-bg-elevated) border-b border-(--ui-border) transition-colors"
|
|
484
|
-
@click="addHierarchyRow"
|
|
485
|
-
>
|
|
486
|
-
+ {{ locale.addRow }}
|
|
487
|
-
</button>
|
|
488
|
-
</template>
|
|
489
|
-
</div>
|
|
109
|
+
ref="hierarchyRef"
|
|
110
|
+
:tree="tree"
|
|
111
|
+
:table-view="tableView"
|
|
112
|
+
:states="states"
|
|
113
|
+
:my-client-id="myClientId"
|
|
114
|
+
:set-local-state="setLocalState"
|
|
115
|
+
:editable="editable"
|
|
116
|
+
:labels="locale"
|
|
117
|
+
@open-node="(id, label) => openNode(id, label)"
|
|
118
|
+
/>
|
|
490
119
|
|
|
491
120
|
<!-- Node panel -->
|
|
492
121
|
<ANodePanel
|
|
@@ -0,0 +1,40 @@
|
|
|
1
|
+
import type { TreeEntry } from '../../../composables/useChildTree.js';
|
|
2
|
+
type __VLS_Props = {
|
|
3
|
+
item: TreeEntry;
|
|
4
|
+
galleryAspect: string;
|
|
5
|
+
cardStyle: string;
|
|
6
|
+
showLabels: boolean;
|
|
7
|
+
isDragging: boolean;
|
|
8
|
+
isDragOver: boolean;
|
|
9
|
+
focusers: Array<{
|
|
10
|
+
clientId: number;
|
|
11
|
+
user?: {
|
|
12
|
+
name?: string;
|
|
13
|
+
color?: string;
|
|
14
|
+
};
|
|
15
|
+
}>;
|
|
16
|
+
canWrite: boolean;
|
|
17
|
+
renameId: string | null;
|
|
18
|
+
renameValue: string;
|
|
19
|
+
};
|
|
20
|
+
declare var __VLS_62: {};
|
|
21
|
+
type __VLS_Slots = {} & {
|
|
22
|
+
actions?: (props: typeof __VLS_62) => any;
|
|
23
|
+
};
|
|
24
|
+
declare const __VLS_base: import("vue").DefineComponent<__VLS_Props, {}, {}, {}, {}, import("vue").ComponentOptionsMixin, import("vue").ComponentOptionsMixin, {
|
|
25
|
+
"commit-rename": () => any;
|
|
26
|
+
"cancel-rename": () => any;
|
|
27
|
+
"update:rename-value": (value: string) => any;
|
|
28
|
+
}, string, import("vue").PublicProps, Readonly<__VLS_Props> & Readonly<{
|
|
29
|
+
"onCommit-rename"?: (() => any) | undefined;
|
|
30
|
+
"onCancel-rename"?: (() => any) | undefined;
|
|
31
|
+
"onUpdate:rename-value"?: ((value: string) => any) | undefined;
|
|
32
|
+
}>, {}, {}, {}, {}, string, import("vue").ComponentProvideOptions, false, {}, any>;
|
|
33
|
+
declare const __VLS_export: __VLS_WithSlots<typeof __VLS_base, __VLS_Slots>;
|
|
34
|
+
declare const _default: typeof __VLS_export;
|
|
35
|
+
export default _default;
|
|
36
|
+
type __VLS_WithSlots<T, S> = T & {
|
|
37
|
+
new (): {
|
|
38
|
+
$slots: S;
|
|
39
|
+
};
|
|
40
|
+
};
|