Skip to content

Commit 632ca6f

Browse files
fix: Side menu block finding logic (#814)
* Fixed logic for getting block from coords * Fixed side menu not showing when hovering other menus * Test fixes
1 parent 965579f commit 632ca6f

File tree

4 files changed

+39
-41
lines changed

4 files changed

+39
-41
lines changed

packages/core/src/extensions/SideMenu/SideMenuPlugin.ts

Lines changed: 36 additions & 33 deletions
Original file line numberDiff line numberDiff line change
@@ -26,46 +26,26 @@ export type SideMenuState<
2626
block: Block<BSchema, I, S>;
2727
};
2828

29-
export function getDraggableBlockFromCoords(
30-
coords: { left: number; top: number },
29+
export function getDraggableBlockFromElement(
30+
element: Element,
3131
view: EditorView
3232
) {
33-
if (!view.dom.isConnected) {
34-
// view is not connected to the DOM, this can cause posAtCoords to fail
35-
// (Cannot read properties of null (reading 'nearestDesc'), https://github.com/TypeCellOS/BlockNote/issues/123)
36-
return undefined;
37-
}
38-
39-
const pos = view.posAtCoords(coords);
40-
if (!pos) {
41-
return undefined;
42-
}
43-
let node = view.domAtPos(pos.pos).node as HTMLElement;
44-
45-
if (node === view.dom) {
46-
// mouse over root
47-
return undefined;
48-
}
49-
5033
while (
51-
node &&
52-
node.parentNode &&
53-
node.parentNode !== view.dom &&
54-
!node.hasAttribute?.("data-id")
34+
element &&
35+
element.parentElement &&
36+
element.parentElement !== view.dom &&
37+
!element.hasAttribute?.("data-id")
5538
) {
56-
node = node.parentNode as HTMLElement;
39+
element = element.parentElement;
5740
}
58-
if (!node) {
41+
if (!element.hasAttribute("data-id")) {
5942
return undefined;
6043
}
61-
return { node, id: node.getAttribute("data-id")! };
44+
return { node: element as HTMLElement, id: element.getAttribute("data-id")! };
6245
}
6346

64-
function blockPositionFromCoords(
65-
coords: { left: number; top: number },
66-
view: EditorView
67-
) {
68-
const block = getDraggableBlockFromCoords(coords, view);
47+
function blockPositionFromElement(element: Element, view: EditorView) {
48+
const block = getDraggableBlockFromElement(element, view);
6949

7050
if (block && block.node.nodeType === 1) {
7151
// TODO: this uses undocumented PM APIs? do we need this / let's add docs?
@@ -197,7 +177,21 @@ function dragStart<
197177
top: e.clientY,
198178
};
199179

200-
const pos = blockPositionFromCoords(coords, view);
180+
const elements = document.elementsFromPoint(coords.left, coords.top);
181+
let blockEl = undefined;
182+
183+
for (const element of elements) {
184+
if (view.dom.contains(element)) {
185+
blockEl = getDraggableBlockFromElement(element, view);
186+
break;
187+
}
188+
}
189+
190+
if (!blockEl) {
191+
return;
192+
}
193+
194+
const pos = blockPositionFromElement(blockEl.node, view);
201195
if (pos != null) {
202196
const selection = view.state.selection;
203197
const doc = view.state.doc;
@@ -327,7 +321,16 @@ export class SideMenuView<
327321
left: editorBoundingBox.left + editorBoundingBox.width / 2, // take middle of editor
328322
top: this.mousePos.y,
329323
};
330-
const block = getDraggableBlockFromCoords(coords, this.pmView);
324+
325+
const elements = document.elementsFromPoint(coords.left, coords.top);
326+
let block = undefined;
327+
328+
for (const element of elements) {
329+
if (this.pmView.dom.contains(element)) {
330+
block = getDraggableBlockFromElement(element, this.pmView);
331+
break;
332+
}
333+
}
331334

332335
// Closes the menu if the mouse cursor is beyond the editor vertically.
333336
if (!block || !this.editor.isEditable) {

packages/core/src/extensions/TableHandles/TableHandlesPlugin.ts

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -11,7 +11,7 @@ import {
1111
} from "../../schema";
1212
import { checkBlockIsDefaultType } from "../../blocks/defaultBlockTypeGuards";
1313
import { EventEmitter } from "../../util/EventEmitter";
14-
import { getDraggableBlockFromCoords } from "../SideMenu/SideMenuPlugin";
14+
import { getDraggableBlockFromElement } from "../SideMenu/SideMenuPlugin";
1515

1616
let dragImageElement: HTMLElement | undefined;
1717

@@ -146,7 +146,7 @@ export class TableHandlesView<
146146
const tableRect =
147147
target.parentElement!.parentElement!.getBoundingClientRect();
148148

149-
const blockEl = getDraggableBlockFromCoords(cellRect, this.pmView);
149+
const blockEl = getDraggableBlockFromElement(target, this.pmView);
150150
if (!blockEl) {
151151
return;
152152
}

tests/src/end-to-end/dragdrop/dragdrop.test.ts

Lines changed: 0 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -66,23 +66,18 @@ test.describe("Check Block Dragging Functionality", () => {
6666
// Dragging first heading into next nested element.
6767
let dragTarget = await page.locator(H_ONE_BLOCK_SELECTOR);
6868
let dropTarget = await page.locator(H_TWO_BLOCK_SELECTOR);
69-
await page.pause();
7069
await dragAndDropBlock(page, dragTarget, dropTarget, true);
7170

7271
// Dragging second heading into next nested element.
7372
dragTarget = await page.locator(H_TWO_BLOCK_SELECTOR);
7473
dropTarget = await page.locator(H_THREE_BLOCK_SELECTOR);
75-
await page.pause();
7674
await dragAndDropBlock(page, dragTarget, dropTarget, true);
7775

7876
// Dragging third heading into outside nesting.
7977
dragTarget = await page.locator(H_THREE_BLOCK_SELECTOR);
8078
dropTarget = await page.locator(BLOCK_CONTAINER_SELECTOR).last();
81-
await page.pause();
8279
await dragAndDropBlock(page, dragTarget, dropTarget, true);
8380

84-
await page.pause();
85-
8681
await compareDocToSnapshot(page, "dragdropnested");
8782
});
8883
});

tests/src/end-to-end/shadcn/shadcn.test.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -31,7 +31,7 @@ test.describe("Check ShadCN UI", () => {
3131
await page.keyboard.press("Shift+Home");
3232

3333
await page.waitForSelector(LINK_BUTTON_SELECTOR);
34-
await page.click(LINK_BUTTON_SELECTOR);
34+
await page.click(LINK_BUTTON_SELECTOR, { position: { x: 5, y: 5 } });
3535

3636
await page.keyboard.type("link");
3737
await page.keyboard.press("Enter");

0 commit comments

Comments
 (0)