@grafloria/element 0.4.33 → 0.4.34

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/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@grafloria/element",
3
- "version": "0.4.33",
3
+ "version": "0.4.34",
4
4
  "type": "module",
5
5
  "main": "./src/index.js",
6
6
  "types": "./src/index.d.ts",
@@ -1323,7 +1323,7 @@ export function createDashboardHandle(ctx) {
1323
1323
  },
1324
1324
  focusWidget(id) {
1325
1325
  var _a;
1326
- const b = binders.get((_a = viewOfWidget.get(id)) !== null && _a !== void 0 ? _a : '');
1326
+ const b = binders.get((_a = boardOfWidget(id)) !== null && _a !== void 0 ? _a : '');
1327
1327
  if (!b)
1328
1328
  return false;
1329
1329
  if (b.focusWidget(id))
@@ -1344,7 +1344,7 @@ export function createDashboardHandle(ctx) {
1344
1344
  b.selectWidget(undefined);
1345
1345
  return true;
1346
1346
  }
1347
- const b = binders.get((_a = viewOfWidget.get(id)) !== null && _a !== void 0 ? _a : '');
1347
+ const b = binders.get((_a = boardOfWidget(id)) !== null && _a !== void 0 ? _a : '');
1348
1348
  return !!b && b.selectWidget(id);
1349
1349
  },
1350
1350
  getSelectedWidget() {
@@ -1628,16 +1628,39 @@ export function createDashboardHandle(ctx) {
1628
1628
  ctx.hosts.clear();
1629
1629
  },
1630
1630
  };
1631
+ /**
1632
+ * The board that HOLDS a widget NOW — live membership, the way toJSON reads
1633
+ * it. A cross-board drag moves membership through the binder's own
1634
+ * commands, which the mount-time map never sees; a handle that kept asking
1635
+ * the widget's FIRST board answered `cell: null` for a tile that had just
1636
+ * been dropped into a page. The map is the fallback for a widget that is
1637
+ * not a member yet (an add still committing).
1638
+ */
1639
+ const boardOfWidget = (id) => {
1640
+ var _a, _b, _c, _d;
1641
+ for (const [cid, g] of ctx.boardGroups)
1642
+ if ((_a = g.members) === null || _a === void 0 ? void 0 : _a.has(id))
1643
+ return cid;
1644
+ const model = (_b = ctx.apiRef) === null || _b === void 0 ? void 0 : _b.getModel();
1645
+ if (model)
1646
+ for (const vid of binders.keys())
1647
+ if ((_d = (_c = model.getGroup(vid)) === null || _c === void 0 ? void 0 : _c.members) === null || _d === void 0 ? void 0 : _d.has(id))
1648
+ return vid;
1649
+ return viewOfWidget.get(id);
1650
+ };
1631
1651
  function makeWidgetHandle(id) {
1632
1652
  const spec = specById.get(id);
1633
- const viewId = viewOfWidget.get(id);
1634
- if (!spec || !viewId)
1653
+ if (!spec || !boardOfWidget(id))
1635
1654
  return undefined;
1636
- const binder = () => binders.get(viewId);
1655
+ const board = () => { var _a; return (_a = boardOfWidget(id)) !== null && _a !== void 0 ? _a : ''; };
1656
+ const binder = () => binders.get(board());
1637
1657
  const node = () => { var _a; return (_a = ctx.apiRef) === null || _a === void 0 ? void 0 : _a.getModel().getNode(id); };
1638
1658
  return {
1639
1659
  id,
1640
- viewId,
1660
+ get viewId() {
1661
+ var _a;
1662
+ return (_a = boardOfWidget(id)) !== null && _a !== void 0 ? _a : '';
1663
+ },
1641
1664
  get node() {
1642
1665
  return node();
1643
1666
  },
@@ -1716,8 +1739,8 @@ export function createDashboardHandle(ctx) {
1716
1739
  // the parent board and the parent's re-pack, as ONE undoable batch.
1717
1740
  // Undo restores the groups as fresh GroupModels, so the history
1718
1741
  // handler re-binds the container's grid (ctx.rebindContainer).
1719
- const parentGroup = ctx.boardGroups.get(viewId);
1720
- const parentBinder = binders.get(viewId);
1742
+ const parentGroup = ctx.boardGroups.get(board());
1743
+ const parentBinder = binders.get(board());
1721
1744
  const model = (_a = ctx.apiRef) === null || _a === void 0 ? void 0 : _a.getModel();
1722
1745
  if (!parentGroup || !parentBinder || !model)
1723
1746
  return;
@@ -1751,7 +1774,7 @@ export function createDashboardHandle(ctx) {
1751
1774
  }
1752
1775
  };
1753
1776
  removeSubtree(id);
1754
- const registry = registryOf(id, viewId, spec);
1777
+ const registry = registryOf(id, board(), spec);
1755
1778
  cmds.push(...nodeRemovals, ...unregisters, new RegisterWidgetCommand(registry, 'unregister'));
1756
1779
  (_c = binders.get(id)) === null || _c === void 0 ? void 0 : _c.dispose();
1757
1780
  binders.delete(id);
@@ -1762,7 +1785,7 @@ export function createDashboardHandle(ctx) {
1762
1785
  return;
1763
1786
  }
1764
1787
  const n = node();
1765
- const group = ctx.boardGroups.get(viewId);
1788
+ const group = ctx.boardGroups.get(board());
1766
1789
  const b = binder();
1767
1790
  if (!n || !group || !b)
1768
1791
  return;
@@ -1775,11 +1798,11 @@ export function createDashboardHandle(ctx) {
1775
1798
  // The un-registration is the LAST command so that undo — which runs
1776
1799
  // the batch in reverse — re-registers the spec BEFORE the node and its
1777
1800
  // membership come back and the painter is asked to paint it (D2).
1778
- const registry = registryOf(id, viewId, spec);
1801
+ const registry = registryOf(id, board(), spec);
1779
1802
  // …and the page it emptied, if it was one, closes with it — in which
1780
1803
  // case everything rides INSIDE one sequence, or the batch could never
1781
1804
  // undo (a membership command cannot undo once its group is gone).
1782
- const closing = (_g = (_f = ctx.closePageIfEmptied) === null || _f === void 0 ? void 0 : _f.call(ctx, viewId, id)) !== null && _g !== void 0 ? _g : [];
1805
+ const closing = (_g = (_f = ctx.closePageIfEmptied) === null || _f === void 0 ? void 0 : _f.call(ctx, board(), id)) !== null && _g !== void 0 ? _g : [];
1783
1806
  const cmds = [
1784
1807
  ...survivors,
1785
1808
  new RemoveFromGroupCommand(group.id, id),
@@ -394,7 +394,38 @@ export function bindDashboardGrid(api, group, options = {}) {
394
394
  return e;
395
395
  };
396
396
  /** The effective row bound a gesture must respect: the strip's, else the fit capacity. */
397
- const bound = () => maxRows !== null && maxRows !== void 0 ? maxRows : capacity;
397
+ const bound = () => { var _a; return (_a = squeezeRoom !== null && squeezeRoom !== void 0 ? squeezeRoom : maxRows) !== null && _a !== void 0 ? _a : capacity; };
398
+ /** Move the LIVE bound (the engine's too), the way escalation does. */
399
+ const setLiveBound = (n) => {
400
+ maxRows = n;
401
+ engine.maxRows = n;
402
+ };
403
+ /**
404
+ * Rows a SQUEEZE may use while a tile arrives by hand — the engine's bound
405
+ * only. The binder's `maxRows` also sets the GEOMETRY (`rows()`), and
406
+ * raising it to the room made every tile shrink to a 29-row grid the
407
+ * moment the ghost entered; the rows must shrink only as far as the
408
+ * content actually reaches.
409
+ */
410
+ let squeezeRoom;
411
+ const setSqueeze = (n) => {
412
+ squeezeRoom = n;
413
+ engine.maxRows = n !== null && n !== void 0 ? n : maxRows;
414
+ };
415
+ /**
416
+ * The rows a NESTED board's live frame holds at the row floor. A page's
417
+ * height is its container's and a section's is its slab's, so a full one
418
+ * cannot ask for room the way the main fit board does (`fitCapacity` reads
419
+ * the design height, which a nested board hands to its parent as 0).
420
+ */
421
+ const elasticRows = () => {
422
+ if (designRows === undefined)
423
+ return undefined;
424
+ const fh = frame().height;
425
+ if (fh <= 0)
426
+ return undefined;
427
+ return Math.max(1, Math.floor((fh - 2 * padding + gap) / (minRowHeight + gap)));
428
+ };
398
429
  /**
399
430
  * The rows the design height can hold at the row floor — what 'bounded' fit
400
431
  * enforces. A board is never bounded BELOW what it already holds: a document
@@ -2404,6 +2435,7 @@ export function bindDashboardGrid(api, group, options = {}) {
2404
2435
  const adopt = (
2405
2436
  // Only the id is used: a tab page arriving here is a GROUP, not a node.
2406
2437
  node, world, pxSize, opts = {}) => {
2438
+ var _a;
2407
2439
  if (disposed)
2408
2440
  return null;
2409
2441
  const f = frame();
@@ -2416,8 +2448,29 @@ export function bindDashboardGrid(api, group, options = {}) {
2416
2448
  if (b !== undefined)
2417
2449
  span.h = Math.max(1, Math.min(b, span.h));
2418
2450
  engine.beginGesture(); // pre-entry snapshot — abort() restores it
2419
- const entered = engine.add({ id: node.id, x: 0, y: engine.rows(), w: span.w, h: span.h });
2451
+ // A FULL nested board SQUEEZES for a tile arriving by hand, the way a fit
2452
+ // board squeezes for its own. Its bound is the design the escalation path
2453
+ // grows through the parent, and a page has no parent tile to grow (its
2454
+ // height is its container's): so the rows shrink toward the floor instead
2455
+ // of refusing the drop with no sign of why — the fluid demo's Filters page
2456
+ // took a KPI dragged onto it and showed nothing at all. abort() puts the
2457
+ // bound back; a commit keeps what the board then holds.
2458
+ const squeezeBefore = squeezeRoom;
2459
+ let entered = engine.add({ id: node.id, x: 0, y: engine.rows(), w: span.w, h: span.h });
2460
+ // Only a board with NO parent tile to grow through squeezes — a page. A
2461
+ // full SECTION keeps refusing (grid-options s05: refused, then joined once
2462
+ // a strip was removed); growing its slab for a dropped tile is the
2463
+ // escalation path's, not a squeeze's, and is not built yet.
2464
+ if (!entered && !parentPeer()) {
2465
+ const room = elasticRows();
2466
+ if (room !== undefined && room > ((_a = bound()) !== null && _a !== void 0 ? _a : 0)) {
2467
+ setSqueeze(room);
2468
+ span.h = Math.max(1, Math.min(room, span.h));
2469
+ entered = engine.add({ id: node.id, x: 0, y: engine.rows(), w: span.w, h: span.h });
2470
+ }
2471
+ }
2420
2472
  if (!entered) {
2473
+ setSqueeze(squeezeBefore);
2421
2474
  engine.endGesture();
2422
2475
  return null; // a bounded, full board refuses the adoption
2423
2476
  }
@@ -2518,6 +2571,7 @@ export function bindDashboardGrid(api, group, options = {}) {
2518
2571
  if (engine.getItem(node.id))
2519
2572
  engine.remove(node.id);
2520
2573
  engine.cancelGesture(); // pre-entry layout, memory cleared
2574
+ setSqueeze(squeezeBefore);
2521
2575
  adoptedGhostId = null;
2522
2576
  disarmGlideSoon();
2523
2577
  project();
@@ -2553,6 +2607,11 @@ export function bindDashboardGrid(api, group, options = {}) {
2553
2607
  });
2554
2608
  }
2555
2609
  engine.endGesture();
2610
+ if (squeezeRoom !== undefined) {
2611
+ // What the board now HOLDS is its bound, not the squeeze's room.
2612
+ squeezeRoom = undefined;
2613
+ setLiveBound(liveBound(engine.getItems()));
2614
+ }
2556
2615
  adoptedGhostId = null;
2557
2616
  disarmGlideSoon();
2558
2617
  syncPlaceholder();