mirror of https://github.com/fantasticit/think.git
support multi bubble-menu
This commit is contained in:
parent
5a1a5c7c1a
commit
d25ad50117
|
@ -27,6 +27,8 @@ export type BubbleMenuViewProps = BubbleMenuPluginProps & {
|
||||||
view: EditorView;
|
view: EditorView;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
const ACTIVE_BUBBLE_MENUS: Instance[] = [];
|
||||||
|
|
||||||
export class BubbleMenuView {
|
export class BubbleMenuView {
|
||||||
public editor: Editor;
|
public editor: Editor;
|
||||||
|
|
||||||
|
@ -178,7 +180,11 @@ export class BubbleMenuView {
|
||||||
const cursorAt = selection.$anchor.pos;
|
const cursorAt = selection.$anchor.pos;
|
||||||
const from = Math.min(...ranges.map((range) => range.$from.pos));
|
const from = Math.min(...ranges.map((range) => range.$from.pos));
|
||||||
const to = Math.max(...ranges.map((range) => range.$to.pos));
|
const to = Math.max(...ranges.map((range) => range.$to.pos));
|
||||||
const placement = Math.abs(cursorAt - to) <= Math.abs(cursorAt - from) ? 'bottom' : 'top';
|
const placement = isNodeSelection(selection)
|
||||||
|
? 'top'
|
||||||
|
: Math.abs(cursorAt - to) <= Math.abs(cursorAt - from)
|
||||||
|
? 'bottom-start'
|
||||||
|
: 'top-start';
|
||||||
const domAtPos = view.domAtPos(from).node as HTMLElement;
|
const domAtPos = view.domAtPos(from).node as HTMLElement;
|
||||||
const nodeDOM = view.nodeDOM(from) as HTMLElement;
|
const nodeDOM = view.nodeDOM(from) as HTMLElement;
|
||||||
const node = nodeDOM || domAtPos;
|
const node = nodeDOM || domAtPos;
|
||||||
|
@ -200,7 +206,28 @@ export class BubbleMenuView {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
const otherBubbleMenus = ACTIVE_BUBBLE_MENUS.filter(
|
||||||
|
(instance) => instance.id !== this.tippy?.id && instance.popperInstance && instance.popperInstance.state
|
||||||
|
);
|
||||||
|
const offsetX = this.tippyOptions?.offset?.[0] ?? 0;
|
||||||
|
const offsetY = otherBubbleMenus.length
|
||||||
|
? otherBubbleMenus.reduce((prev, instance, currentIndex, array) => {
|
||||||
|
const prevY = array[currentIndex - 1]
|
||||||
|
? array[currentIndex - 1]?.popperInstance?.state?.modifiersData?.popperOffsets?.y ?? 0
|
||||||
|
: 0;
|
||||||
|
const currentY = instance?.popperInstance?.state?.modifiersData?.popperOffsets?.y ?? 0;
|
||||||
|
const currentHeight = instance?.popperInstance?.state?.rects?.popper?.height ?? 40;
|
||||||
|
|
||||||
|
if (Math.abs(prevY - currentY) <= currentHeight) {
|
||||||
|
prev += currentHeight;
|
||||||
|
}
|
||||||
|
|
||||||
|
return prev;
|
||||||
|
}, 0)
|
||||||
|
: this.tippyOptions?.offset?.[1] ?? 10;
|
||||||
|
|
||||||
this.tippy?.setProps({
|
this.tippy?.setProps({
|
||||||
|
offset: [offsetX, offsetY],
|
||||||
placement,
|
placement,
|
||||||
getReferenceClientRect: () => {
|
getReferenceClientRect: () => {
|
||||||
let toMountNode = null;
|
let toMountNode = null;
|
||||||
|
@ -230,15 +257,31 @@ export class BubbleMenuView {
|
||||||
this.show();
|
this.show();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
addActiveBubbleMenu = () => {
|
||||||
|
const idx = ACTIVE_BUBBLE_MENUS.findIndex((instance) => instance?.id === this.tippy?.id);
|
||||||
|
if (idx < 0) {
|
||||||
|
ACTIVE_BUBBLE_MENUS.push(this.tippy);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
removeActiveBubbleMenu = () => {
|
||||||
|
const idx = ACTIVE_BUBBLE_MENUS.findIndex((instance) => instance?.id === this.tippy?.id);
|
||||||
|
if (idx > -1) {
|
||||||
|
ACTIVE_BUBBLE_MENUS.splice(idx, 1);
|
||||||
|
}
|
||||||
|
};
|
||||||
show() {
|
show() {
|
||||||
|
this.addActiveBubbleMenu();
|
||||||
this.tippy?.show();
|
this.tippy?.show();
|
||||||
}
|
}
|
||||||
|
|
||||||
hide() {
|
hide() {
|
||||||
|
this.removeActiveBubbleMenu();
|
||||||
this.tippy?.hide();
|
this.tippy?.hide();
|
||||||
}
|
}
|
||||||
|
|
||||||
destroy() {
|
destroy() {
|
||||||
|
this.removeActiveBubbleMenu();
|
||||||
this.tippy?.destroy();
|
this.tippy?.destroy();
|
||||||
this.element.removeEventListener('mousedown', this.mousedownHandler, {
|
this.element.removeEventListener('mousedown', this.mousedownHandler, {
|
||||||
capture: true,
|
capture: true,
|
||||||
|
|
Loading…
Reference in New Issue