@lumir-company/editor 0.4.17 → 0.4.18
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +7 -0
- package/dist/index.js +149 -0
- package/dist/index.js.map +1 -1
- package/dist/index.mjs +149 -0
- package/dist/index.mjs.map +1 -1
- package/package.json +1 -1
package/dist/index.mjs
CHANGED
|
@@ -4901,6 +4901,9 @@ function LumirTableHandlesController() {
|
|
|
4901
4901
|
const frozenRef = useRef11(false);
|
|
4902
4902
|
const menuOpenRef = useRef11(false);
|
|
4903
4903
|
const draggingRef = useRef11(false);
|
|
4904
|
+
useEffect10(() => {
|
|
4905
|
+
editor.__lumirActiveTableId = focused?.block?.id ?? null;
|
|
4906
|
+
}, [editor, focused]);
|
|
4904
4907
|
const recompute = useCallback20(() => {
|
|
4905
4908
|
if (frozenRef.current) {
|
|
4906
4909
|
return;
|
|
@@ -5443,6 +5446,140 @@ function liftFontSize(blocks) {
|
|
|
5443
5446
|
return mapPreservingRef(blocks, (b) => mapBlock(b, "lift"));
|
|
5444
5447
|
}
|
|
5445
5448
|
|
|
5449
|
+
// src/utils/table-delete.ts
|
|
5450
|
+
import { CellSelection, TableMap as TableMap2, deleteRow } from "prosemirror-tables";
|
|
5451
|
+
function measureRowHeights(view, tablePos) {
|
|
5452
|
+
try {
|
|
5453
|
+
const at = view?.domAtPos?.(tablePos + 1);
|
|
5454
|
+
let el = at?.node;
|
|
5455
|
+
if (el && el.nodeType === 3) el = el.parentElement;
|
|
5456
|
+
const tableEl = el?.closest?.("table") ?? null;
|
|
5457
|
+
const body = tableEl?.tBodies?.[0];
|
|
5458
|
+
if (!body) return null;
|
|
5459
|
+
return Array.from(body.rows).map(
|
|
5460
|
+
(tr) => Math.round(tr.getBoundingClientRect().height)
|
|
5461
|
+
);
|
|
5462
|
+
} catch {
|
|
5463
|
+
return null;
|
|
5464
|
+
}
|
|
5465
|
+
}
|
|
5466
|
+
function buildDeleteColumnTr(state, tablePos, col, rowPx) {
|
|
5467
|
+
const table = state.doc.nodeAt(tablePos);
|
|
5468
|
+
if (!table || table.type.name !== "table") return null;
|
|
5469
|
+
const map = TableMap2.get(table);
|
|
5470
|
+
const W = map.width;
|
|
5471
|
+
const H = map.height;
|
|
5472
|
+
if (col < 0 || col >= W || W <= 1) return null;
|
|
5473
|
+
const cells = [];
|
|
5474
|
+
const seen = /* @__PURE__ */ new Set();
|
|
5475
|
+
for (let r = 0; r < H; r++) {
|
|
5476
|
+
for (let c = 0; c < W; c++) {
|
|
5477
|
+
const pos = map.map[r * W + c];
|
|
5478
|
+
if (seen.has(pos)) continue;
|
|
5479
|
+
seen.add(pos);
|
|
5480
|
+
const node = table.nodeAt(pos);
|
|
5481
|
+
if (!node) continue;
|
|
5482
|
+
cells.push({
|
|
5483
|
+
node,
|
|
5484
|
+
top: r,
|
|
5485
|
+
left: c,
|
|
5486
|
+
rowspan: node.attrs.rowspan ?? 1,
|
|
5487
|
+
colspan: node.attrs.colspan ?? 1
|
|
5488
|
+
});
|
|
5489
|
+
}
|
|
5490
|
+
}
|
|
5491
|
+
const spansCol = (c) => c.left <= col && col < c.left + c.colspan;
|
|
5492
|
+
const isDropped = (c) => spansCol(c) && c.colspan === 1;
|
|
5493
|
+
const survivingByRow = new Array(H).fill(0);
|
|
5494
|
+
for (const c of cells) if (!isDropped(c)) survivingByRow[c.top]++;
|
|
5495
|
+
const rowDies = survivingByRow.map((n) => n === 0);
|
|
5496
|
+
const newRowIndex = [];
|
|
5497
|
+
let ni = 0;
|
|
5498
|
+
for (let r = 0; r < H; r++) newRowIndex[r] = rowDies[r] ? -1 : ni++;
|
|
5499
|
+
const newH = ni;
|
|
5500
|
+
if (newH === 0) return null;
|
|
5501
|
+
const newRows = Array.from({ length: newH }, () => []);
|
|
5502
|
+
for (const c of cells) {
|
|
5503
|
+
if (isDropped(c)) continue;
|
|
5504
|
+
const newColspan = c.colspan - (spansCol(c) ? 1 : 0);
|
|
5505
|
+
let dyingWithin = 0;
|
|
5506
|
+
for (let r = c.top; r < c.top + c.rowspan; r++) if (rowDies[r]) dyingWithin++;
|
|
5507
|
+
const newRowspan = Math.max(1, c.rowspan - dyingWithin);
|
|
5508
|
+
const attrs = { ...c.node.attrs, colspan: newColspan, rowspan: newRowspan };
|
|
5509
|
+
if (spansCol(c) && Array.isArray(attrs.colwidth) && attrs.colwidth.length) {
|
|
5510
|
+
const cw = attrs.colwidth.slice();
|
|
5511
|
+
cw.splice(col - c.left, 1);
|
|
5512
|
+
attrs.colwidth = cw.some((w) => w > 0) ? cw : null;
|
|
5513
|
+
}
|
|
5514
|
+
if (dyingWithin > 0 && rowPx) {
|
|
5515
|
+
let sum = 0;
|
|
5516
|
+
let ok = true;
|
|
5517
|
+
for (let r = c.top; r < c.top + c.rowspan; r++) {
|
|
5518
|
+
if (typeof rowPx[r] !== "number") {
|
|
5519
|
+
ok = false;
|
|
5520
|
+
break;
|
|
5521
|
+
}
|
|
5522
|
+
sum += rowPx[r];
|
|
5523
|
+
}
|
|
5524
|
+
if (ok && sum > 0) attrs.rowHeight = Math.round(sum);
|
|
5525
|
+
}
|
|
5526
|
+
const target = newRowIndex[c.top];
|
|
5527
|
+
if (target >= 0) newRows[target].push(c.node.type.create(attrs, c.node.content));
|
|
5528
|
+
}
|
|
5529
|
+
const rowType = table.child(0)?.type;
|
|
5530
|
+
if (!rowType) return null;
|
|
5531
|
+
const rowNodes = newRows.map((rowCells) => rowType.create(null, rowCells));
|
|
5532
|
+
const newTable = table.type.create(table.attrs, rowNodes);
|
|
5533
|
+
const tr = state.tr;
|
|
5534
|
+
tr.replaceWith(tablePos, tablePos + table.nodeSize, newTable);
|
|
5535
|
+
return tr.docChanged ? tr : null;
|
|
5536
|
+
}
|
|
5537
|
+
function removeFocusedRowOrColumn(editor, index, direction) {
|
|
5538
|
+
const tiptap = editor?._tiptapEditor;
|
|
5539
|
+
if (!tiptap) return false;
|
|
5540
|
+
const { state } = tiptap;
|
|
5541
|
+
let tablePos = -1;
|
|
5542
|
+
const activeId = editor?.__lumirActiveTableId;
|
|
5543
|
+
if (activeId) {
|
|
5544
|
+
const p = findTableNodePos(tiptap, activeId);
|
|
5545
|
+
if (p >= 0 && state.doc.nodeAt(p)?.type.name === "table") tablePos = p;
|
|
5546
|
+
}
|
|
5547
|
+
if (tablePos < 0) {
|
|
5548
|
+
const $from = state.selection.$from;
|
|
5549
|
+
for (let d = $from.depth; d > 0; d--) {
|
|
5550
|
+
if ($from.node(d).type.name === "table") {
|
|
5551
|
+
tablePos = $from.before(d);
|
|
5552
|
+
break;
|
|
5553
|
+
}
|
|
5554
|
+
}
|
|
5555
|
+
}
|
|
5556
|
+
if (tablePos < 0) {
|
|
5557
|
+
const vp = editor?.tableHandles?.view?.tablePos;
|
|
5558
|
+
if (typeof vp === "number" && state.doc.nodeAt(vp)?.type.name === "table") {
|
|
5559
|
+
tablePos = vp;
|
|
5560
|
+
}
|
|
5561
|
+
}
|
|
5562
|
+
if (tablePos < 0) return false;
|
|
5563
|
+
try {
|
|
5564
|
+
if (direction === "column") {
|
|
5565
|
+
const rowPx = measureRowHeights(tiptap.view, tablePos);
|
|
5566
|
+
const tr = buildDeleteColumnTr(state, tablePos, index, rowPx);
|
|
5567
|
+
if (!tr) return false;
|
|
5568
|
+
tiptap.view.dispatch(tr);
|
|
5569
|
+
return true;
|
|
5570
|
+
}
|
|
5571
|
+
const tableInside = state.doc.resolve(tablePos + 1);
|
|
5572
|
+
const rowStart = state.doc.resolve(tableInside.posAtIndex(index) + 1);
|
|
5573
|
+
const cellPos = state.doc.resolve(rowStart.posAtIndex(0));
|
|
5574
|
+
const selState = state.apply(
|
|
5575
|
+
state.tr.setSelection(new CellSelection(cellPos))
|
|
5576
|
+
);
|
|
5577
|
+
return deleteRow(selState, (tr) => tiptap.view.dispatch(tr));
|
|
5578
|
+
} catch {
|
|
5579
|
+
return false;
|
|
5580
|
+
}
|
|
5581
|
+
}
|
|
5582
|
+
|
|
5446
5583
|
// src/utils/excel-paste.ts
|
|
5447
5584
|
var NAMED_COLORS = {
|
|
5448
5585
|
black: "#000000",
|
|
@@ -6296,6 +6433,18 @@ function LumirEditor({
|
|
|
6296
6433
|
editor.isEditable = editable;
|
|
6297
6434
|
}
|
|
6298
6435
|
}, [editor, editable]);
|
|
6436
|
+
useEffect11(() => {
|
|
6437
|
+
if (!editor) return;
|
|
6438
|
+
const th = editor.tableHandles;
|
|
6439
|
+
if (!th || th.__lumirColDelPatched || typeof th.removeRowOrColumn !== "function")
|
|
6440
|
+
return;
|
|
6441
|
+
const orig = th.removeRowOrColumn.bind(th);
|
|
6442
|
+
th.removeRowOrColumn = (index, dir) => {
|
|
6443
|
+
if (removeFocusedRowOrColumn(editor, index, dir)) return;
|
|
6444
|
+
return orig(index, dir);
|
|
6445
|
+
};
|
|
6446
|
+
th.__lumirColDelPatched = true;
|
|
6447
|
+
}, [editor]);
|
|
6299
6448
|
useEffect11(() => {
|
|
6300
6449
|
if (!editor || !floatingMenu) return;
|
|
6301
6450
|
const ft = editor.formattingToolbar;
|