【问题标题】:Add event directive to svelte html expression?将事件指令添加到 svelte html 表达式?
【发布时间】:2020-03-10 00:54:06
【问题描述】:

我想通过 svelte 中的 html 表达式添加自定义按钮。 通过文档here,我可以使用 @html 标签来做到这一点。

{@html 
`
 <button>
   click me
 </button>
`
}

我现在想在 html 字符串中添加一个指令事件处理程序,即单击按钮时将调用的本地定义函数。到目前为止我尝试过的:

{@html 
`
 <button
   on:click="${()=>doSomething()}">
   click me
 </button>
`
}

但是,正如我所料,它不起作用。我在想可能有另一种方法,但到目前为止还想不出一个

【问题讨论】:

    标签: javascript html svelte


    【解决方案1】:

    从概念上讲,使用@html 指令等同于使用el.innerHTML = myHtmlString。

    换句话说,在您的 HTML 字符串的上下文中,您完全不在 Svelte 的领域(并且完全在本机浏览器的领域)。

    on:click 是特殊的 Svelte 语法,浏览器不会处理它。因此,如果您想要 HTML 字符串中的事件,则需要返回原始 HTML/JS。也就是说,请改用onclick。

    当然,onclick 的语义与on:click 的语义完全不同。对于onclick,您只能传递一个字符串,当事件发生时将是eval'd(而对于on:click,您传递一个函数reference,当事件发生)。

    为了清楚起见,让我们回顾一下 Svelte 的语法:

    <button on:click={doSomething}>Click me</button>
    

    相比之下,在原始 HTML 中,这看起来像:

    {@html '<button onclick="doSomething()">Click click!</button>'}
    

    看到重要的区别:使用onclick,您需要调用 doSomething() 函数,否则点击时不会发生任何事情。

    现在,更有趣的是:这个doSomething 函数需要在作用域内可用...也就是说,你必须将它附加到window:

    <script context="module">
      // note: using context=module to avoid adding this function to window
      //       multiple times
      window.doSomething = () => { ... }
    </script>
    {@html '<button onclick="doSomething()">Click click!</button>'}
    

    这很难看……你可以这样做,以避免污染全局范围:

    <script>
      import { onMount } from 'svelte'
    
        const doSomething = () => { ... }
    
        onMount(() => {
            const btn = document.querySelector('#grab-me')
            btn.addEventListener('click', doSomething)
        })
    </script>
    
    {@html '<button id="grab-me">Click click!</button>'}
    

    现在我们正在污染 DOM id...我们可以通过包装 Svelte 控制的元素来进一步避免这种情况,我们可以使用 bind:this={el} 获取对它的引用...

    总而言之,@html 字符串中的动态元素最好避免使用,因为您在其中失去了 Svelte 的所有好处。 @html 最适合呈现静态 HTML 内容。

    为什么要将按钮放在字符串中,而不是让 Svelte 管理它?

    如果你真的需要走这条路,你可能也对this dirty trick 感兴趣,我绝对不推荐使用它(我永远不会在我自己的代码中使用它)......但这可能会给你进一步了解您想要实现的目标。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2023-03-09
      • 2014-11-12
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2020-12-17
      相关资源
      最近更新 更多