diff --git a/app/src/boot/globalEvent/event.ts b/app/src/boot/globalEvent/event.ts index a613b975d..407898db4 100644 --- a/app/src/boot/globalEvent/event.ts +++ b/app/src/boot/globalEvent/event.ts @@ -8,7 +8,11 @@ import {Constants} from "../../constants"; import {isIPad} from "../../protyle/util/compatibility"; import {globalTouchEnd, globalTouchStart} from "./touch"; import {initDockMenu} from "../../menus/dock"; -import {hasClosestByAttribute, hasClosestByClassName, hasTopClosestByAttribute} from "../../protyle/util/hasClosest"; +import { + hasClosestByAttribute, + hasClosestByClassName, + isInEmbedBlock +} from "../../protyle/util/hasClosest"; import {initTabMenu} from "../../menus/tab"; import {getInstanceById} from "../../layout/util"; import {Tab} from "../../layout/Tab"; @@ -85,7 +89,7 @@ export const initWindowEvent = (app: App) => { } return; } - const embedBlockElement = hasTopClosestByAttribute(target, "data-type", "NodeBlockQueryEmbed"); + const embedBlockElement = isInEmbedBlock(target); if (embedBlockElement) { embedBlockElement.firstElementChild.classList.toggle("protyle-icons--show"); return; diff --git a/app/src/boot/globalEvent/touch.ts b/app/src/boot/globalEvent/touch.ts index 4ad999592..c822c6f88 100644 --- a/app/src/boot/globalEvent/touch.ts +++ b/app/src/boot/globalEvent/touch.ts @@ -1,5 +1,10 @@ import {isIPad} from "../../protyle/util/compatibility"; -import {hasClosestByAttribute, hasClosestByClassName, hasTopClosestByTag} from "../../protyle/util/hasClosest"; +import { + hasClosestByAttribute, + hasClosestByClassName, + hasTopClosestByTag, + isInEmbedBlock +} from "../../protyle/util/hasClosest"; import {initFileMenu, initNavigationMenu} from "../../menus/navigation"; import {fileAnnotationRefMenu, inlineMathMenu, linkMenu, refMenu, tagMenu} from "../../menus/protyle"; import {App} from "../../index"; @@ -80,7 +85,7 @@ export const globalTouchEnd = (event: TouchEvent, yDiff: number, time: number, a return true; } // 内元素弹出菜单 - if (target.tagName === "SPAN" && !hasClosestByAttribute(target, "data-type", "NodeBlockQueryEmbed")) { + if (target.tagName === "SPAN" && !isInEmbedBlock(target)) { let editor: Protyle; /// #if !MOBILE const tabContainerElement = hasClosestByClassName(target, "protyle", true); diff --git a/app/src/editor/util.ts b/app/src/editor/util.ts index 93184460b..37011ae5e 100644 --- a/app/src/editor/util.ts +++ b/app/src/editor/util.ts @@ -18,7 +18,12 @@ import {ipcRenderer, shell} from "electron"; import {pushBack} from "../util/backForward"; import {Asset} from "../asset"; import {Layout} from "../layout"; -import {hasClosestBlock, hasClosestByAttribute, hasClosestByClassName,} from "../protyle/util/hasClosest"; +import { + hasClosestBlock, + hasClosestByAttribute, + hasClosestByClassName, + isInEmbedBlock, +} from "../protyle/util/hasClosest"; import {zoomOut} from "../menus/protyle"; import {countBlockWord, countSelectWord} from "../layout/status"; import {showMessage} from "../dialog/message"; @@ -349,7 +354,7 @@ const switchEditor = (editor: Editor, options: IOpenFileOptions, allModels: IMod } let nodeElement: Element; Array.from(editor.editor.protyle.wysiwyg.element.querySelectorAll(`[data-node-id="${options.id}"]`)).find(item => { - if (!hasClosestByAttribute(item.parentElement, "data-type", "NodeBlockQueryEmbed")) { + if (!isInEmbedBlock(item)) { nodeElement = item; return true; } diff --git a/app/src/layout/Wnd.ts b/app/src/layout/Wnd.ts index 64d18dae6..202bbfad8 100644 --- a/app/src/layout/Wnd.ts +++ b/app/src/layout/Wnd.ts @@ -12,7 +12,12 @@ import {Tab} from "./Tab"; import {Model} from "./Model"; import {Editor} from "../editor"; import {Graph} from "./dock/Graph"; -import {hasClosestBlock, hasClosestByAttribute, hasClosestByClassName} from "../protyle/util/hasClosest"; +import { + hasClosestBlock, + hasClosestByAttribute, + hasClosestByClassName, + isInEmbedBlock +} from "../protyle/util/hasClosest"; import {Constants} from "../constants"; /// #if !BROWSER import {webFrame, ipcRenderer} from "electron"; @@ -460,7 +465,7 @@ export class Wnd { // 在新页签中打开,但不跳转到新页签,但切换到新页签时需调整滚动 let nodeElement: HTMLElement; Array.from(currentTab.model.editor.protyle.wysiwyg.element.querySelectorAll(`[data-node-id="${keepCursorId}"]`)).find((item: HTMLElement) => { - if (!hasClosestByAttribute(item, "data-type", "NodeBlockQueryEmbed", true)) { + if (!isInEmbedBlock(item)) { nodeElement = item; return true; } diff --git a/app/src/mobile/editor.ts b/app/src/mobile/editor.ts index a1e1f82bf..47ded4d99 100644 --- a/app/src/mobile/editor.ts +++ b/app/src/mobile/editor.ts @@ -6,7 +6,7 @@ import {fetchPost} from "../util/fetch"; import {onGet} from "../protyle/util/onGet"; import {addLoading} from "../protyle/ui/initUI"; import {scrollCenter} from "../util/highlightById"; -import {hasClosestByAttribute} from "../protyle/util/hasClosest"; +import {isInEmbedBlock} from "../protyle/util/hasClosest"; import {setEditMode} from "../protyle/util/setEditMode"; import {hideElements} from "../protyle/ui/hideElements"; import {pushBack} from "./util/MobileBackFoward"; @@ -34,7 +34,7 @@ export const openMobileFileById = (app: App, id: string, action = [Constants.CB_ } let blockElement; Array.from(window.siyuan.mobile.editor.protyle.wysiwyg.element.querySelectorAll(`[data-node-id="${id}"]`)).find((item: HTMLElement) => { - if (!hasClosestByAttribute(item.parentElement, "data-type", "NodeBlockQueryEmbed")) { + if (!isInEmbedBlock(item)) { blockElement = item; return true; } diff --git a/app/src/protyle/gutter/index.ts b/app/src/protyle/gutter/index.ts index 83cb2afbe..0638cf49e 100644 --- a/app/src/protyle/gutter/index.ts +++ b/app/src/protyle/gutter/index.ts @@ -1,10 +1,9 @@ import { hasClosestBlock, - hasClosestByAttribute, hasClosestByClassName, hasClosestByMatchTag, hasClosestByTag, - hasTopClosestByClassName + hasTopClosestByClassName, isInEmbedBlock } from "../util/hasClosest"; import {getIconByType} from "../../editor/getIcon"; import {enterBack, iframeMenu, setFold, tableMenu, videoMenu, zoomOut} from "../../menus/protyle"; @@ -79,7 +78,7 @@ export class Gutter { let avElement: Element; if (buttonElement.dataset.rowId) { avElement = Array.from(protyle.wysiwyg.element.querySelectorAll(`.av[data-node-id="${buttonElement.dataset.nodeId}"]`)).find((item: HTMLElement) => { - if (!hasClosestByAttribute(item, "data-type", "NodeBlockQueryEmbed")) { + if (!isInEmbedBlock(item)) { return true; } }); @@ -159,8 +158,7 @@ export class Gutter { buttonElement.setAttribute("disabled", "disabled"); let foldElement: Element; Array.from(protyle.wysiwyg.element.querySelectorAll(`[data-node-id="${(buttonElement.previousElementSibling || buttonElement.nextElementSibling).getAttribute("data-node-id")}"]`)).find(item => { - if (!hasClosestByAttribute(item.parentElement, "data-type", "NodeBlockQueryEmbed") && - this.isMatchNode(item)) { + if (!isInEmbedBlock(item) && this.isMatchNode(item)) { foldElement = item; return true; } @@ -229,7 +227,7 @@ export class Gutter { const gutterRect = buttonElement.getBoundingClientRect(); if (buttonElement.dataset.type === "NodeAttributeViewRowMenu" || buttonElement.dataset.type === "NodeAttributeViewRow") { const rowElement = Array.from(protyle.wysiwyg.element.querySelectorAll(`.av[data-node-id="${buttonElement.dataset.nodeId}"] .av__row[data-id="${buttonElement.dataset.rowId}"]`)).find((item: HTMLElement) => { - if (!hasClosestByAttribute(item, "data-type", "NodeBlockQueryEmbed")) { + if (!isInEmbedBlock(item)) { return true; } }); @@ -295,8 +293,7 @@ export class Gutter { } else if (event.altKey) { let foldElement: Element; Array.from(protyle.wysiwyg.element.querySelectorAll(`[data-node-id="${id}"]`)).find(item => { - if (!hasClosestByAttribute(item.parentElement, "data-type", "NodeBlockQueryEmbed") && - this.isMatchNode(item)) { + if (!isInEmbedBlock(item) && this.isMatchNode(item)) { foldElement = item; return true; } @@ -370,7 +367,7 @@ export class Gutter { const gutterRect = buttonElement.getBoundingClientRect(); if (buttonElement.dataset.type === "NodeAttributeViewRowMenu") { const rowElement = Array.from(protyle.wysiwyg.element.querySelectorAll(`.av[data-node-id="${buttonElement.dataset.nodeId}"] .av__row[data-id="${buttonElement.dataset.rowId}"]`)).find((item: HTMLElement) => { - if (!hasClosestByAttribute(item, "data-type", "NodeBlockQueryEmbed")) { + if (!isInEmbedBlock(item)) { return true; } }); @@ -406,7 +403,7 @@ export class Gutter { return; } Array.from(protyle.wysiwyg.element.querySelectorAll(`[data-node-id="${buttonElement.getAttribute("data-node-id")}"]`)).find(item => { - if (!hasClosestByAttribute(item.parentElement, "data-type", "NodeBlockQueryEmbed") && this.isMatchNode(item)) { + if (!isInEmbedBlock(item) && this.isMatchNode(item)) { const rowItem = item.querySelector(`.av__row[data-id="${buttonElement.dataset.rowId}"]`); Array.from(protyle.wysiwyg.element.querySelectorAll(".protyle-wysiwyg--hl, av__row--hl")).forEach(hlItem => { if (!item.isSameNode(hlItem)) { @@ -867,8 +864,7 @@ export class Gutter { let nodeElement: Element; if (buttonElement.tagName === "BUTTON") { Array.from(protyle.wysiwyg.element.querySelectorAll(`[data-node-id="${id}"]`)).find(item => { - if (!hasClosestByAttribute(item.parentElement, "data-type", "NodeBlockQueryEmbed") && - this.isMatchNode(item)) { + if (!isInEmbedBlock(item) && this.isMatchNode(item)) { nodeElement = item; return true; } @@ -1953,8 +1949,7 @@ export class Gutter { let hideParent = false; while (nodeElement) { const isShow = !hideParent || (hideParent && nodeElement.getAttribute("fold") === "1"); - const embedElement = hasClosestByAttribute(nodeElement.parentElement, "data-type", "NodeBlockQueryEmbed"); - if (!embedElement) { + if (!isInEmbedBlock(nodeElement)) { let type; if (isShow) { type = nodeElement.getAttribute("data-type"); @@ -1979,7 +1974,7 @@ export class Gutter { const topElement = getTopAloneElement(nodeElement); listItem = topElement.querySelector(".li") || topElement.querySelector(".list"); // 嵌入块中有列表时块标显示位置错误 https://github.com/siyuan-note/siyuan/issues/6254 - if (hasClosestByAttribute(listItem, "data-type", "NodeBlockQueryEmbed")) { + if (isInEmbedBlock(listItem)) { listItem = undefined; } // 标题必须显示 diff --git a/app/src/protyle/render/av/render.ts b/app/src/protyle/render/av/render.ts index 30dcfe1f3..305c47d44 100644 --- a/app/src/protyle/render/av/render.ts +++ b/app/src/protyle/render/av/render.ts @@ -4,7 +4,7 @@ import {Constants} from "../../../constants"; import {addDragFill, renderCell} from "./cell"; import {unicode2Emoji} from "../../../emoji"; import {focusBlock} from "../../util/selection"; -import {hasClosestBlock, hasClosestByAttribute, hasClosestByClassName} from "../../util/hasClosest"; +import {hasClosestBlock, hasClosestByClassName, isInEmbedBlock} from "../../util/hasClosest"; import {stickyRow, updateHeader} from "./row"; import {getCalcValue} from "./calc"; import {renderAVAttribute} from "./blockAttr"; @@ -206,7 +206,7 @@ ${cell.color ? `color:${cell.color};` : ""}">${renderCell(cell.value, rowIndex)} let avBackground = "--av-background:var(--b3-theme-background)"; if (e.style.backgroundColor) { avBackground = "--av-background:" + e.style.backgroundColor; - } else if (hasClosestByAttribute(e, "data-type", "NodeBlockQueryEmbed")) { + } else if (isInEmbedBlock(e)) { avBackground = "--av-background:var(--b3-theme-surface)"; } e.firstElementChild.outerHTML = `
diff --git a/app/src/protyle/render/blockRender.ts b/app/src/protyle/render/blockRender.ts index 8b5588eca..6eb9f88a4 100644 --- a/app/src/protyle/render/blockRender.ts +++ b/app/src/protyle/render/blockRender.ts @@ -1,4 +1,4 @@ -import {hasClosestByAttribute, hasTopClosestByClassName} from "../util/hasClosest"; +import {hasClosestByAttribute, hasTopClosestByClassName, isInEmbedBlock} from "../util/hasClosest"; import {fetchPost, fetchSyncPost} from "../../util/fetch"; import {processRender} from "../util/processCode"; import {highlightRender} from "./highlightRender"; @@ -24,7 +24,7 @@ export const blockRender = (protyle: IProtyle, element: Element, top?: number) = // 需置于请求返回前,否则快速滚动会导致重复加载 https://ld246.com/article/1666857862494?r=88250 item.setAttribute("data-render", "true"); item.style.height = (item.clientHeight - 8) + "px"; // 减少抖动 https://ld246.com/article/1668669380171 - item.innerHTML = `
+ item.innerHTML = `
diff --git a/app/src/protyle/util/editorCommonEvent.ts b/app/src/protyle/util/editorCommonEvent.ts index 2b25bbac4..65f6cfee8 100644 --- a/app/src/protyle/util/editorCommonEvent.ts +++ b/app/src/protyle/util/editorCommonEvent.ts @@ -4,7 +4,7 @@ import { hasClosestByAttribute, hasClosestByClassName, hasClosestByTag, - hasTopClosestByAttribute + hasTopClosestByAttribute, isInEmbedBlock } from "./hasClosest"; import {Constants} from "../../constants"; import {paste} from "./paste"; @@ -829,8 +829,7 @@ export const dropEvent = (protyle: IProtyle, editorElement: HTMLElement) => { }); if (window.siyuan.dragElement) { window.siyuan.dragElement.querySelectorAll(queryClass.substring(0, queryClass.length - 1)).forEach(elementItem => { - if (elementItem.getAttribute("data-type") === "NodeBlockQueryEmbed" || - !hasClosestByAttribute(elementItem, "data-type", "NodeBlockQueryEmbed")) { + if (!isInEmbedBlock(elementItem)) { sourceElements.push(elementItem); } }); @@ -838,8 +837,7 @@ export const dropEvent = (protyle: IProtyle, editorElement: HTMLElement) => { const targetProtyleElement = document.createElement("template"); targetProtyleElement.innerHTML = `
${event.dataTransfer.getData(gutterType)}
`; targetProtyleElement.content.querySelectorAll(queryClass.substring(0, queryClass.length - 1)).forEach(elementItem => { - if (elementItem.getAttribute("data-type") === "NodeBlockQueryEmbed" || - !hasClosestByAttribute(elementItem, "data-type", "NodeBlockQueryEmbed")) { + if (!isInEmbedBlock(elementItem)) { sourceElements.push(elementItem); } }); @@ -1309,7 +1307,7 @@ export const dropEvent = (protyle: IProtyle, editorElement: HTMLElement) => { if (isSelf) { return; } - if (hasClosestByAttribute(targetElement.parentElement, "data-type", "NodeBlockQueryEmbed")) { + if (isInEmbedBlock(targetElement)) { // 不允许托入嵌入块 return; } diff --git a/app/src/protyle/util/hasClosest.ts b/app/src/protyle/util/hasClosest.ts index a8b1aa760..59133d8ab 100644 --- a/app/src/protyle/util/hasClosest.ts +++ b/app/src/protyle/util/hasClosest.ts @@ -128,3 +128,16 @@ export const hasClosestByClassName = (element: Node, className: string, top = fa } return isClosest && e; }; + +export const isInEmbedBlock = (element: Element) => { + const embedElement = hasTopClosestByAttribute(element, "data-type", "NodeBlockQueryEmbed"); + if (embedElement) { + if (embedElement.isSameNode(element)) { + return false; + } else { + return embedElement; + } + } else { + return false; + } +} diff --git a/app/src/protyle/wysiwyg/getBlock.ts b/app/src/protyle/wysiwyg/getBlock.ts index 521ab96d2..c03265397 100644 --- a/app/src/protyle/wysiwyg/getBlock.ts +++ b/app/src/protyle/wysiwyg/getBlock.ts @@ -1,4 +1,4 @@ -import {hasClosestBlock, hasClosestByAttribute} from "../util/hasClosest"; +import {hasClosestBlock, isInEmbedBlock} from "../util/hasClosest"; import {Constants} from "../../constants"; export const getPreviousBlock = (element: Element) => { @@ -19,7 +19,7 @@ export const getPreviousBlock = (element: Element) => { export const getLastBlock = (element: Element) => { let lastElement; Array.from(element.querySelectorAll("[data-node-id]")).reverse().find(item => { - if (!hasClosestByAttribute(item.parentElement, "data-type", "NodeBlockQueryEmbed")) { + if (!isInEmbedBlock(item)) { lastElement = item; return true; } @@ -30,8 +30,7 @@ export const getLastBlock = (element: Element) => { export const getFirstBlock = (element: Element) => { let firstElement; Array.from(element.querySelectorAll("[data-node-id]")).find(item => { - if (!hasClosestByAttribute(item.parentElement, "data-type", "NodeBlockQueryEmbed") && - !item.classList.contains("li") && !item.classList.contains("sb")) { + if (!isInEmbedBlock(item) && !item.classList.contains("li") && !item.classList.contains("sb")) { firstElement = item; return true; } diff --git a/app/src/protyle/wysiwyg/index.ts b/app/src/protyle/wysiwyg/index.ts index 5db2c836b..245e3cfd1 100644 --- a/app/src/protyle/wysiwyg/index.ts +++ b/app/src/protyle/wysiwyg/index.ts @@ -3,8 +3,8 @@ import { hasClosestBlock, hasClosestByAttribute, hasClosestByClassName, - hasClosestByMatchTag, hasTopClosestByAttribute, - hasTopClosestByClassName, + hasClosestByMatchTag, + hasTopClosestByClassName, isInEmbedBlock, } from "../util/hasClosest"; import { focusBlock, @@ -544,7 +544,7 @@ export class WYSIWYG { } // av cell select const avCellElement = hasClosestByClassName(target, "av__cell"); - if (!protyle.disabled && avCellElement && avCellElement.dataset.id && !hasClosestByAttribute(avCellElement, "data-type", "NodeBlockQueryEmbed")) { + if (!protyle.disabled && avCellElement && avCellElement.dataset.id && !isInEmbedBlock(avCellElement)) { const nodeElement = hasClosestBlock(avCellElement); if (!nodeElement) { return; @@ -929,7 +929,7 @@ export class WYSIWYG { if (currentElement) { // 从下往上划选遇到嵌入块时,选中整个嵌入块 - const embedElement = hasClosestByAttribute(currentElement, "data-type", "NodeBlockQueryEmbed"); + const embedElement = isInEmbedBlock(currentElement); if (embedElement) { currentElement = embedElement; } @@ -1328,7 +1328,7 @@ export class WYSIWYG { return; } // https://github.com/siyuan-note/siyuan/issues/11793 - const embedElement = hasTopClosestByAttribute(nodeElement.parentElement, "data-type", "NodeBlockQueryEmbed"); + const embedElement = isInEmbedBlock(nodeElement); if (embedElement) { nodeElement = embedElement; } @@ -1549,7 +1549,7 @@ export class WYSIWYG { return; } const target = event.detail.target || event.target as HTMLElement; - const embedElement = hasClosestByAttribute(target, "data-type", "NodeBlockQueryEmbed"); + const embedElement = isInEmbedBlock(target); if (embedElement) { if (getSelection().rangeCount === 0) { focusSideBlock(embedElement); @@ -1801,7 +1801,7 @@ export class WYSIWYG { return; } if (nodeElement) { - const embedElement = hasClosestByAttribute(nodeElement, "data-type", "NodeBlockQueryEmbed"); + const embedElement = isInEmbedBlock(nodeElement); if (embedElement) { protyle.gutter.render(protyle, embedElement, this.element); } else { @@ -2306,7 +2306,7 @@ export class WYSIWYG { const reloadElement = hasClosestByClassName(event.target, "protyle-action__reload"); if (reloadElement) { - const embedReloadElement = hasClosestByAttribute(reloadElement, "data-type", "NodeBlockQueryEmbed"); + const embedReloadElement = isInEmbedBlock(reloadElement); if (embedReloadElement) { embedReloadElement.removeAttribute("data-render"); blockRender(protyle, embedReloadElement); @@ -2637,7 +2637,7 @@ export class WYSIWYG { if (ctrlIsPressed && range.toString() === "") { let ctrlElement = hasClosestBlock(event.target); if (ctrlElement) { - const embedBlockElement = hasClosestByAttribute(ctrlElement, "data-type", "NodeBlockQueryEmbed"); + const embedBlockElement = isInEmbedBlock(ctrlElement); if (embedBlockElement) { ctrlElement = embedBlockElement; } diff --git a/app/src/protyle/wysiwyg/input.ts b/app/src/protyle/wysiwyg/input.ts index 528b90eed..cde5ca807 100644 --- a/app/src/protyle/wysiwyg/input.ts +++ b/app/src/protyle/wysiwyg/input.ts @@ -9,7 +9,7 @@ import {getContenteditableElement, getNextBlock, hasNextSibling, isNotEditBlock} import {genEmptyBlock} from "../../block/util"; import {blockRender} from "../render/blockRender"; import {hideElements} from "../ui/hideElements"; -import {hasClosestByAttribute, hasClosestByClassName} from "../util/hasClosest"; +import {hasClosestByAttribute, hasClosestByClassName, isInEmbedBlock} from "../util/hasClosest"; import {fetchPost, fetchSyncPost} from "../../util/fetch"; import {headingTurnIntoList, turnIntoTaskList} from "./turnIntoList"; import {updateAVName} from "../render/av/action"; @@ -176,8 +176,7 @@ export const input = async (protyle: IProtyle, blockElement: HTMLElement, range: blockElement.outerHTML = html.replace("", "" + Constants.ZWSP + ""); } protyle.wysiwyg.element.querySelectorAll(`[data-node-id="${id}"]`).forEach((item: HTMLElement) => { - if (item.getAttribute("data-type") === "NodeBlockQueryEmbed" || - !hasClosestByAttribute(item, "data-type", "NodeBlockQueryEmbed")) { + if (!isInEmbedBlock(item)) { blockElement = item; } }); diff --git a/app/src/protyle/wysiwyg/keydown.ts b/app/src/protyle/wysiwyg/keydown.ts index 852d48155..ebfc727a5 100644 --- a/app/src/protyle/wysiwyg/keydown.ts +++ b/app/src/protyle/wysiwyg/keydown.ts @@ -15,7 +15,7 @@ import { hasClosestBlock, hasClosestByAttribute, hasClosestByMatchTag, - hasTopClosestByAttribute + hasTopClosestByAttribute, isInEmbedBlock } from "../util/hasClosest"; import {removeBlock, removeImage} from "./remove"; import { @@ -1319,8 +1319,7 @@ export const keydown = (protyle: IProtyle, editorElement: HTMLElement) => { return; } - if (!nodeElement.classList.contains("code-block") && !event.repeat && - !hasClosestByAttribute(nodeElement, "data-type", "NodeBlockQueryEmbed")) { + if (!nodeElement.classList.contains("code-block") && !event.repeat && !isInEmbedBlock(nodeElement)) { let findToolbar = false; protyle.options.toolbar.find((menuItem: IMenuItem) => { if (!menuItem.hotkey) { diff --git a/app/src/protyle/wysiwyg/transaction.ts b/app/src/protyle/wysiwyg/transaction.ts index a9c9f81cb..1a5cc3ceb 100644 --- a/app/src/protyle/wysiwyg/transaction.ts +++ b/app/src/protyle/wysiwyg/transaction.ts @@ -5,7 +5,7 @@ import {Constants} from "../../constants"; import {blockRender} from "../render/blockRender"; import {processRender} from "../util/processCode"; import {highlightRender} from "../render/highlightRender"; -import {hasClosestBlock, hasClosestByAttribute} from "../util/hasClosest"; +import {hasClosestBlock, hasClosestByAttribute, isInEmbedBlock} from "../util/hasClosest"; import {setFold, zoomOut} from "../../menus/protyle"; import {disabledProtyle, enableProtyle, onGet} from "../util/onGet"; /// #if !MOBILE @@ -94,8 +94,7 @@ const promiseTransaction = () => { if (protyle.options.backlinkData) { // 反链中有多个相同块的情况 Array.from(protyle.wysiwyg.element.querySelectorAll(`[data-node-id="${operation.id}"]`)).forEach(item => { - if (item.getAttribute("data-type") === "NodeBlockQueryEmbed" || - !hasClosestByAttribute(item, "data-type", "NodeBlockQueryEmbed")) { + if (!isInEmbedBlock(item)) { if (range && (item.isSameNode(range.startContainer) || item.contains(range.startContainer))) { // 正在编辑的块不能进行更新 } else { @@ -117,7 +116,7 @@ const promiseTransaction = () => { if (operation.action === "delete" || operation.action === "append") { if (protyle.options.backlinkData) { Array.from(protyle.wysiwyg.element.querySelectorAll(`[data-node-id="${operation.id}"]`)).forEach(item => { - if (!hasClosestByAttribute(item, "data-type", "NodeBlockQueryEmbed")) { + if (!isInEmbedBlock(item)) { item.remove(); } }); @@ -136,7 +135,7 @@ const promiseTransaction = () => { if (protyle.options.backlinkData) { const updateElements: Element[] = []; Array.from(protyle.wysiwyg.element.querySelectorAll(`[data-node-id="${operation.id}"]`)).forEach(item => { - if (item.getAttribute("data-type") === "NodeBlockQueryEmbed" || !hasClosestByAttribute(item, "data-type", "NodeBlockQueryEmbed")) { + if (!isInEmbedBlock(item)) { updateElements.push(item); return; } @@ -144,14 +143,14 @@ const promiseTransaction = () => { let hasFind = false; if (operation.previousID && updateElements.length > 0) { Array.from(protyle.wysiwyg.element.querySelectorAll(`[data-node-id="${operation.previousID}"]`)).forEach(item => { - if (item.getAttribute("data-type") === "NodeBlockQueryEmbed" || !hasClosestByAttribute(item.parentElement, "data-type", "NodeBlockQueryEmbed")) { + if (!isInEmbedBlock(item)) { item.after(processClonePHElement(updateElements[0].cloneNode(true) as Element)); hasFind = true; } }); } else if (updateElements.length > 0) { Array.from(protyle.wysiwyg.element.querySelectorAll(`[data-node-id="${operation.parentID}"]`)).forEach(item => { - if (item.getAttribute("data-type") === "NodeBlockQueryEmbed" || !hasClosestByAttribute(item.parentElement, "data-type", "NodeBlockQueryEmbed")) { + if (!isInEmbedBlock(item)) { // 列表特殊处理 if (item.firstElementChild?.classList.contains("protyle-action")) { item.firstElementChild.after(processClonePHElement(updateElements[0].cloneNode(true) as Element)); @@ -187,14 +186,14 @@ const promiseTransaction = () => { Array.from(protyle.wysiwyg.element.querySelectorAll(`[data-node-id="${operation.previousID}"]`)).forEach(item => { if (item.nextElementSibling?.getAttribute("data-node-id") !== operation.id && !hasClosestByAttribute(item, "data-node-id", operation.id) && // 段落转列表会在段落后插入新列表 - (item.getAttribute("data-type") === "NodeBlockQueryEmbed" || !hasClosestByAttribute(item.parentElement, "data-type", "NodeBlockQueryEmbed"))) { + !isInEmbedBlock(item)) { item.insertAdjacentHTML("afterend", operation.data); cursorElements.push(item.nextElementSibling); } }); } else { Array.from(protyle.wysiwyg.element.querySelectorAll(`[data-node-id="${operation.parentID}"]`)).forEach(item => { - if (item.getAttribute("data-type") === "NodeBlockQueryEmbed" || !hasClosestByAttribute(item.parentElement, "data-type", "NodeBlockQueryEmbed")) { + if (!isInEmbedBlock(item)) { // 列表特殊处理 if (item.firstElementChild && item.firstElementChild.classList.contains("protyle-action") && item.firstElementChild.nextElementSibling.getAttribute("data-node-id") !== operation.id) { @@ -301,8 +300,7 @@ const updateBlock = (updateElements: Element[], protyle: IProtyle, operation: IO } }); Array.from(protyle.wysiwyg.element.querySelectorAll(`[data-node-id="${operation.id}"]`)).find(item => { - if (item.getAttribute("data-type") === "NodeBlockQueryEmbed" // 引用转换为块嵌入,undo、redo 后也需要更新 updateElement - || !hasClosestByAttribute(item, "data-type", "NodeBlockQueryEmbed")) { + if (!isInEmbedBlock(item)) { updateElements[0] = item; return true; } @@ -332,7 +330,7 @@ const updateBlock = (updateElements: Element[], protyle: IProtyle, operation: IO export const onTransaction = (protyle: IProtyle, operation: IOperation, isUndo: boolean) => { const updateElements: Element[] = []; Array.from(protyle.wysiwyg.element.querySelectorAll(`[data-node-id="${operation.id}"]`)).forEach(item => { - if (!hasClosestByAttribute(item.parentElement, "data-type", "NodeBlockQueryEmbed")) { + if (!isInEmbedBlock(item)) { updateElements.push(item); } }); @@ -398,7 +396,7 @@ export const onTransaction = (protyle: IProtyle, operation: IOperation, isUndo: focusId: operation.id, callback() { Array.from(protyle.wysiwyg.element.querySelectorAll(`[data-node-id="${operation.id}"]`)).forEach(item => { - if (!hasClosestByAttribute(item.parentElement, "data-type", "NodeBlockQueryEmbed")) { + if (!isInEmbedBlock(item)) { updateElements.push(item); } }); @@ -419,7 +417,7 @@ export const onTransaction = (protyle: IProtyle, operation: IOperation, isUndo: focusId: operation.id, callback() { Array.from(protyle.wysiwyg.element.querySelectorAll(`[data-node-id="${operation.id}"]`)).forEach(item => { - if (!hasClosestByAttribute(item.parentElement, "data-type", "NodeBlockQueryEmbed")) { + if (!isInEmbedBlock(item)) { updateElements.push(item); } }); @@ -575,7 +573,7 @@ export const onTransaction = (protyle: IProtyle, operation: IOperation, isUndo: let hasFind = false; if (operation.previousID && updateElements.length > 0) { Array.from(protyle.wysiwyg.element.querySelectorAll(`[data-node-id="${operation.previousID}"]`)).forEach(item => { - if (!hasClosestByAttribute(item.parentElement, "data-type", "NodeBlockQueryEmbed")) { + if (!isInEmbedBlock(item)) { item.after(processClonePHElement(updateElements[0].cloneNode(true) as Element)); hasFind = true; } @@ -586,7 +584,7 @@ export const onTransaction = (protyle: IProtyle, operation: IOperation, isUndo: hasFind = true; } else { Array.from(protyle.wysiwyg.element.querySelectorAll(`[data-node-id="${operation.parentID}"]`)).forEach(item => { - if (!hasClosestByAttribute(item.parentElement, "data-type", "NodeBlockQueryEmbed")) { + if (!isInEmbedBlock(item)) { // 列表特殊处理 if (item.firstElementChild?.classList.contains("protyle-action")) { item.firstElementChild.after(processClonePHElement(updateElements[0].cloneNode(true) as Element)); @@ -609,7 +607,7 @@ export const onTransaction = (protyle: IProtyle, operation: IOperation, isUndo: if (operation.data === "focus") { // 标记需要 focus,https://ld246.com/article/1650018446988/comment/1650081404993?r=Vanessa#comments Array.from(protyle.wysiwyg.element.querySelectorAll(`[data-node-id="${operation.id}"]`)).find(item => { - if (!hasClosestByAttribute(item.parentElement, "data-type", "NodeBlockQueryEmbed")) { + if (!isInEmbedBlock(item)) { focusBlock(item); return true; } @@ -632,7 +630,7 @@ export const onTransaction = (protyle: IProtyle, operation: IOperation, isUndo: const cursorElements = []; if (operation.previousID) { Array.from(protyle.wysiwyg.element.querySelectorAll(`[data-node-id="${operation.previousID}"]`)).forEach(item => { - const embedElement = hasClosestByAttribute(item.parentElement, "data-type", "NodeBlockQueryEmbed"); + const embedElement = isInEmbedBlock(item); if (embedElement) { // https://github.com/siyuan-note/siyuan/issues/5524 embedElement.removeAttribute("data-render"); @@ -648,7 +646,7 @@ export const onTransaction = (protyle: IProtyle, operation: IOperation, isUndo: cursorElements.push(protyle.wysiwyg.element.firstElementChild); } else { Array.from(protyle.wysiwyg.element.querySelectorAll(`[data-node-id="${operation.parentID}"]`)).forEach(item => { - if (!hasClosestByAttribute(item.parentElement, "data-type", "NodeBlockQueryEmbed")) { + if (!isInEmbedBlock(item)) { // 列表特殊处理 if (item.firstElementChild?.classList.contains("protyle-action")) { item.firstElementChild.insertAdjacentHTML("afterend", operation.data); diff --git a/app/src/util/backForward.ts b/app/src/util/backForward.ts index 7a58abfe6..9009d163c 100644 --- a/app/src/util/backForward.ts +++ b/app/src/util/backForward.ts @@ -1,4 +1,4 @@ -import {hasClosestBlock, hasClosestByAttribute} from "../protyle/util/hasClosest"; +import {hasClosestBlock, isInEmbedBlock} from "../protyle/util/hasClosest"; import {getContenteditableElement} from "../protyle/wysiwyg/getBlock"; import {focusByOffset, focusByRange, getSelectionOffset} from "../protyle/util/selection"; import {hideElements} from "../protyle/ui/hideElements"; @@ -97,7 +97,7 @@ const focusStack = async (app: App, stack: IBackStack) => { focusByOffset(protyle.title.editElement, stack.position.start, stack.position.end); } else { Array.from(protyle.wysiwyg.element.querySelectorAll(`[data-node-id="${stack.id}"]`)).find((item: HTMLElement) => { - if (!hasClosestByAttribute(item, "data-type", "NodeBlockQueryEmbed")) { + if (!isInEmbedBlock(item)) { blockElement = item; return true; } @@ -122,7 +122,7 @@ const focusStack = async (app: App, stack: IBackStack) => { return true; } Array.from(stack.protyle.wysiwyg.element.querySelectorAll(`[data-node-id="${stack.id}"]`)).find((item: HTMLElement) => { - if (!hasClosestByAttribute(item, "data-type", "NodeBlockQueryEmbed")) { + if (!isInEmbedBlock(item)) { blockElement = item; return true; } @@ -165,7 +165,7 @@ const focusStack = async (app: App, stack: IBackStack) => { protyle: stack.protyle, afterCB() { Array.from(stack.protyle.wysiwyg.element.querySelectorAll(`[data-node-id="${stack.id}"]`)).find((item: HTMLElement) => { - if (!hasClosestByAttribute(item, "data-type", "NodeBlockQueryEmbed")) { + if (!isInEmbedBlock(item)) { blockElement = item; return true; } @@ -193,7 +193,7 @@ const focusStack = async (app: App, stack: IBackStack) => { isPushBack: false, callback: () => { Array.from(stack.protyle.wysiwyg.element.querySelectorAll(`[data-node-id="${stack.id}"]`)).find((item: HTMLElement) => { - if (!hasClosestByAttribute(item, "data-type", "NodeBlockQueryEmbed")) { + if (!isInEmbedBlock(item)) { blockElement = item; return true; }