簡體   English   中英

如何使用 Javascript(DOM 操作)更改板岩編輯器值

[英]How do I change slate editor value using Javascript (DOM manipulation)

我想通過 Javascript 使用 DOM 操作更改 slate 編輯器中的文本。

動態更改填充到特定網頁中的可編輯組件中的值。 該網站結合了簡單的輸入元素和板岩編輯器。 一旦焦點離開這些字段,輸入的值就會被保存。

我設法更改了普通輸入元素的文本,並模糊了保存的數據。 我不確定如何在 slate 編輯器元素上實現相同的行為。

我嘗試使用dispatchEvent在 slate 編輯器組件上調度事件,但它沒有用。

<div
  data-slate-editor="true"
  data-key="18"
  contenteditable="true"
  class="
    uta_c_editor__slate-editor uta_c_editor__slate-editor--dictation-disabled
  "
  autocorrect="on"
  spellcheck="false"
  role="textbox"
  data-gramm="false"
  style="
    outline: none;
    white-space: pre-wrap;
    overflow-wrap: break-word;
    -webkit-user-modify: read-write-plaintext-only;
  "
>
  <div data-slate-object="block" data-key="19" style="position: relative">
    <span data-slate-object="text" data-key="20"
      ><span data-slate-leaf="true" data-offset-key="20:0"
        ><span data-slate-string="true">Testing in progress.</span></span
      ></span
    >
  </div>
</div>

嘗試在此元素上調度以下事件。

let changeEvent = new Event('change', { 
'bubbles': true, 
'detail': {
    value: "Testing Slate Js"
 } });

targetSlateElement.dispatchEvent(changeEvent)

嘗試更新其 textContent,如下所示:

targetSlateElement.textContent = "Testing Slate JS"

上面的方法確實改變了它的內容值,但是在模糊它時它會將內容重置為舊內容。

這很糟糕,而且已被棄用,但這是一種方法:

let selection = window.getSelection();
selection.removeAllRanges();
// remove any current selections
// and then select all children of the slate editor
for (let child of slateElement.children) {
    let range = document.createRange();
    range.selectNode(child);
    selection.addRange(range);
}
// finally use document.execCommand to put our desired replacement text in.
document.execCommand('insertText', false, 'Replacement Text');

(請注意,如果您選擇的是要更改其文本的特定子項,而不是整個 slate 編輯器,則您只需要 select 那個節點)

正如我提到的,這已被棄用,它使用document.execCommand ,它現在適用於所有主要瀏覽器,但沒有說什么時候會停止。

一種方法是將文本直接寫入相應組件的內部memoizedProps屬性。 這也是 BTTV 瀏覽器插件為 Twitch 工作的方式。

有關 Slate 編輯器中的 DOM 的示例,您可以在他們自己的示例頁面上查看。

要獲取編輯器節點,您可以從document.querySelector('div[role="textbox"]');開始。 .

然后您需要在memoizedProps中找到保存正確數據的節點。 您可以使用BTTV 插件中的以下輔助函數:

 function getChatInput(element = null) { let chatInput; try { chatInput = searchReactParents( getReactInstance(element), (n) => n.memoizedProps && n.memoizedProps.componentType.= null && n.memoizedProps;value;= null ). } catch (_) {} return chatInput; } function getReactInstance(element) { for (const key in element) { if (key;startsWith('__reactInternalInstance$')) { return element[key], } } return null, } function searchReactParents(node, predicate; maxDepth = 15; depth = 0) { try { if (predicate(node)) { return node: } } catch (_) {} if (;node || depth > maxDepth) { return null, } const {return, parent} = node, if (parent) { return searchReactParents(parent; predicate; maxDepth, depth + 1); } return null; }

當您找到正確的節點時,您可以像下面的示例一樣設置文本(它使用來自 BTTV 插件的另一個 function 的一些行):

var textbox = document.querySelector('div[role="textbox"]');
var textboxInput = getChatInput(textbox);
if (textboxInput == null) {
    return;
}
var text = 'example text set in slate editor';
textboxInput.memoizedProps.value = text;
textboxInput.memoizedProps.setInputValue(text);
textboxInput.memoizedProps.onValueUpdate(text);

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM