0

项目是 vue 单页应用

具体来说就是后台会返回给我一个 script 地址,我用 js 创建 script 标签然后插入到 head 中,这个 script 会生成一个 flash 插入到 html 底部,这个时候插入的位置是和 vue 中的 app 同级的,所以 vue 的生命周期 mounted 监控不到。

我怎么做才能完美的知道 dom 已插入完毕,方便我移动这个 dom 的位置,太早执行函数会获取不到dom,太晚用户会看到位置不对。

我目前是用定时器,插入 script 1s 后执行 dom 操作。

有没有更优雅的办法呢?

clipboard.png

clipboard.png

2019-06-19 提问

查看全部 3 个回答

1

已采纳
<!DOCTYPE html>
<html lang="en">
<head>
  <meta charset="UTF-8">
  <meta name="viewport" content="width=device-width, initial-scale=1.0">
  <meta http-equiv="X-UA-Compatible" content="ie=edge">
  <title>Demo</title>
</head>
<body>
  <div id="app">
    <p>{{text}}</p>
  </div>
  <script src="https://cdn.staticfile.org/vue/2.6.10/vue.js"></script>
  <script>
    (function() {
      new Vue({
        el: '#app',
        data: {
          text: 'this is app text',
        }
      })
      const observer = new MutationObserver(mutations => {
        mutations.forEach(({type, addedNodes}) => {
          if(type === 'childList' && addedNodes.length && addedNodes[0].id === 'flash') console.log('flashDOM插入完毕');
        })
      });
      observer.observe(document.body,{ childList: true, attributes: false,subtree: false, });
      
      const script = document.createElement('script');
      script.src = 'index.js';
      // 如果脚本里的DOM是立即插入的话,在onload里就可以获取到了。
      // 反之,如果DOM是延迟插入的话,如在setTimeout(() => document.body.appendChild(flash), 1000);
      // 那么就用MutationObserve去检测
      script.onload = () => console.log(document.querySelector('#flash'))
      document.head.appendChild(script);
    })();
  </script>
</body>
</html>
// index.js
(() => {
  const flash = document.createElement('div');
  flash.id = 'flash';
  flash.innerHTML = '<p>this is flash content</p>';
  document.body.appendChild(flash);
})();

推广链接