Reactjs 网络应用程序 - MutationObserver 在 Safari 浏览器中的使用不如预期

问题描述 投票:0回答:1

我有一个反应 web 应用程序,它呈现 2 个垂直调整大小的文本区域(使用 CSS)。我的要求是,当用户调整一个文本区域的大小时,代码会捕获它并将高度应用于另一个文本区域。

根据我的研究,目前没有像

textarea.onResize()
这样方便的方法。所以,我正在使用MutationObserver。 API 非常优雅,正是我所需要的。我能够正确配置它,捕获
style
属性的变化并将其应用于其他文本区域。这在 Google Chrome(版本 76.0.3809.132(官方构建)(64 位))和 Mozilla FireFox(版本 68.0.1esr(64 位))中运行良好。所有这些测试都是在 Mac OS High Sierra(版本 10.13.6)上完成的。

问题

虽然,当谈到Safari浏览器(版本12.1.2(13607.3.10))时,它似乎没有按预期工作。

在调试时,我发现当用户调整给定文本区域的大小时,

style
属性被附加到它上面,并分配了一些高度并且对于每次更改,
MutationObserver
观察到更改产生了一个
MutationRecord
,我在我的回调采取适当的行动(在这种情况下,将高度应用于其他文本区域)。虽然,当用户调整文本区域大小时,Safari 浏览器不会为
MutationRecord
属性的更改生成
style

两件事:

  1. 如果我在浏览器的开发人员模式下检查文本区域并更改元素的
    style
    属性,
    MutationRecord
    会正确生成并且我的回调确实会执行,这很奇怪。
  2. 我在 JS Fiddle 中创建了一个示例,其中在 Safari 中,如果您调整文本区域的大小,则不会生成
    MutationRecord
    并且您不会看到任何警报,但是如果您检查并手动进行更改,您将查看警报(生成适当的
    MutationRecord
    s)。在 ChromeFirefox 中,调整文本区域的大小将产生窗口警报,而无需通过检查元素进行更改。

代码

CSS

.textField textarea {
    resize: vertical;
}

componentDidMount()

componentDidMount() {
 if ('MutationObserver' in window) {
      const config =  {
        attributes: true,
        subtree: true,
        attributeFilter: ['style'],
        attributeOldValue: true
      };

      const sourceTextArea = window.getElementById('sourceTextArea');
      this.sourceObserver =  new MutationObserver(this.handleManualSourceTextAreaResize);
      this.sourceObserver.observe(sourceTextArea, config);

      const targetTextArea = window.getElementById('targetTextArea');
      this.targetObserver =  new MutationObserver(this.handleManualTargetTextAreaResize);
      this.targetObserver.observe(targetTextArea, config);
    }
}

源文本区域的回调

handleManualSourceTextAreaResize = (mutationsList, observer) => {
    const sourceTextArea = getElement('sourceTextArea');
    const targetTextArea = getElement('targetTextArea').children[0];

    if (!this.isStopPropagation) {
      targetTextArea.setAttribute('style',  'height: ' + sourceTextArea.offsetHeight + 'px');
      this.isStopPropagation = true;
    } else {
      this.isStopPropagation = false;
    }
  }

目标文本区域的回调

  handleManualTargetTextAreaResize = (mutationsList, observer) => {
    const sourceTextArea = getElement('sourceTextArea').children[0];
    const targetTextArea = getElement('targetTextArea');

    if (!this.isStopPropagation) {
      sourceTextArea.setAttribute('style',  'height: ' + targetTextArea.offsetHeight + 'px'');
      this.isStopPropagation = true;
    } else {
      this.isStopPropagation = false;
    }
  }

reactjs safari mutation-observers
1个回答
0
投票

你需要使用

WebKitMutationObserver
的 ios。所以就我而言,我有这个条件:

var observer = new MutationObserver(loopCheckSelector);
if (!observer){
  observer = new WebKitMutationObserver(loopCheckSelector);
}
observer.observe(container, observerOptions);

如果您的流量主要是 ios,您也可以切换条件。

© www.soinside.com 2019 - 2024. All rights reserved.