2

考虑以下示例:

riot.mount('clock')
setTimeout(()=>{
  console.log("removing from dom")
  var el = document.getElementsByTagName("clock")[0];
  el.parentNode.removeChild(el);
  riot.update();
}, 5000)
<script src="https://cdnjs.cloudflare.com/ajax/libs/riot/2.5.0/riot+compiler.min.js">
</script>
<script type="riot/tag">
  <clock>
      <p>{ time }</p>
      
      this.time = new Date();
      tick() {
        this.update({ time: new Date() })
      }
      var timer = setInterval(this.tick, 1000)
      this.on("unmount",() => {
      	console.log("unmounted")
        clearInterval(timer)
      });
      this.on("update",() => {
        console.log("on update");
      });
      this.tick();
  </clock>
</script>

<clock></clock>

我们在其中挂载一个标签,然后使用普通的 DOM 方法将其删除。在这种情况下,可以看到虽然标签不再存在,但它并没有被卸载,因此unmount事件处理程序中的处置代码没有运行。

我可以使用 DOM MutationObserver 来处理这种情况,但我想知道我是否遗漏了什么。

4

1 回答 1

1

检查parentNodeon update 并调用unmount,如果它不存在。

riot.mount('clock')
setTimeout(()=>{
  console.log("removing from dom")
  var el = document.getElementsByTagName("clock")[0];
  el.parentNode.removeChild(el);
  riot.update();
}, 5000)
<script src="https://cdnjs.cloudflare.com/ajax/libs/riot/2.5.0/riot+compiler.min.js">
</script>
<script>
  riot.mixin("autoUnmount", {
    init: function() {
      this.on("update",() => {
        if (!this.root.parentNode) {
          this.unmount();
        }
      });
    }
  });
</script>
<script type="riot/tag">
  <clock>
      <p>{ time }</p>
      
      this.mixin("autoUnmount");
      this.time = new Date();
      tick() {
        this.update({ time: new Date() })
      }
      var timer = setInterval(this.tick, 1000)
      this.on("unmount",() => {
      	console.log("unmounted")
        clearInterval(timer)
      });
      this.on("update",() => {
        console.log("on update");
      });
      this.tick();
  </clock>
</script>

<clock></clock>

于 2016-07-06T17:34:45.307 回答