基本标记
Svelte 组件中的标记可以被认为是 HTML++。
标签
小写标签,如 <div>
,表示常规 HTML 元素。大写标签或使用点表示法的标签,例如 <Widget>
或 <my.stuff>
,表示一个组件。
<script>
import Widget from './Widget.svelte';
</script>
<div>
<Widget />
</div>
元素属性
默认情况下,属性的工作方式与其 HTML 对应项完全相同。
<div class="foo">
<button disabled>can't touch this</button>
</div>
与 HTML 一样,值可以不加引号。
<input type=checkbox />
属性值可以包含 JavaScript 表达式。
<a href="page/{p}">page {p}</a>
或者它们可以是 JavaScript 表达式。
<button disabled={!clickable}>...</button>
如果布尔属性的值为真值,则将其包含在元素中;如果其值为假值,则将其排除。
除非属性值为空值(null
或 undefined
),否则将包含所有其他属性。
<input required={false} placeholder="This input field is not required" />
<div title={null}>This div has no title attribute</div>
为单个表达式加引号不会影响值的解析方式,但在 Svelte 6 中,它会导致值被强制转换为字符串。
<button disabled="{number !== 42}">...</button>
当属性名称和值匹配(name={name}
)时,它们可以替换为 {name}
。
<button {disabled}>...</button>
<!-- equivalent to
<button disabled={disabled}>...</button>
-->
组件属性
按照惯例,传递给组件的值被称为属性或prop,而不是特性,特性是 DOM 的一个功能。
与元素一样,name={name}
可以替换为 {name}
简写形式。
<Widget foo={bar} answer={42} text="hello" />
扩展属性允许一次将许多属性传递给元素或组件。
元素或组件可以有多个扩展属性,与常规属性交错。
<Widget {...things} />
事件
可以通过向元素添加以 on
开头的属性来监听 DOM 事件。例如,要监听 click
事件,请将 onclick
属性添加到按钮中。
<button onclick={() => console.log('clicked')}>click me</button>
事件属性区分大小写。onclick
监听 click
事件,onClick
监听 Click
事件,这两者是不同的。这确保您可以监听自定义事件,这些事件在其名称中包含大写字符。
因为事件只是属性,所以属性的相同规则也适用。
- 您可以使用简写形式:
<button {onclick}>点击我</button>
- 您可以扩展它们:
<button {...thisSpreadContainsEventAttributes}>点击我</button>
在时间方面,事件属性始终在来自绑定的事件之后触发(例如,oninput
始终在更新 bind:value
后触发)。在幕后,一些事件处理程序是使用 addEventListener
直接附加的,而其他事件处理程序则是委托的。
当使用 ontouchstart
和 ontouchmove
事件属性时,处理程序对于更好的性能是被动的。这通过允许浏览器立即滚动文档来极大地提高响应速度,而不是等待查看事件处理程序是否调用 event.preventDefault()
。
在您需要阻止这些事件默认行为的极少数情况下,您应该改用on
(例如在操作内部)。
事件委托
为了减少内存占用并提高性能,Svelte 使用了一种称为事件委托的技术。这意味着对于某些事件——请参见下面的列表——应用程序根目录中的单个事件侦听器负责运行事件路径上的任何处理程序。
需要注意一些问题。
- 当您使用委托侦听器手动分派事件时,请确保设置
{ bubbles: true }
选项,否则它将无法到达应用程序根目录。 - 当直接使用
addEventListener
时,避免调用stopPropagation
,否则事件将无法到达应用程序根目录,并且处理程序将不会被调用。同样,在应用程序根目录中手动添加的处理程序将在声明性地添加到 DOM 更深处的处理程序(例如使用onclick={...}
)之前运行,在捕获和冒泡阶段都是如此。由于这些原因,最好使用从svelte/events
导入的on
函数,而不是addEventListener
,因为它将确保顺序得到保留,并且stopPropagation
得到正确处理。
以下事件处理程序是委托的。
beforeinput
click
change
dblclick
contextmenu
focusin
focusout
input
keydown
keyup
mousedown
mousemove
mouseout
mouseover
mouseup
pointerdown
pointermove
pointerout
pointerover
pointerup
touchend
touchmove
touchstart
文本表达式
可以通过用花括号括起来将 JavaScript 表达式包含为文本。
{expression}
可以通过使用其HTML 实体字符串在 Svelte 模板中包含花括号:{
、{
或 {
用于 {
,以及 }
、}
或 }
用于 }
。
如果您使用的是正则表达式 (RegExp
)字面量表示法,则需要将其括在括号中。
<h1>Hello {name}!</h1>
<p>{a} + {b} = {a + b}.</p>
<div>{(/^[A-Za-z ]+$/).test(value) ? x : y}</div>
表达式将被字符串化并转义以防止代码注入。如果要呈现 HTML,请改用 {@html}
标签。
{@html potentiallyUnsafeHtmlString}
确保您要么转义传递的字符串,要么只用您控制的值填充它,以防止XSS 攻击。
注释
您可以在组件内使用 HTML 注释。
<!-- this is a comment! --><h1>Hello world</h1>
以 svelte-ignore
开头的注释会禁用下一块标记的警告。通常,这些是辅助功能警告;请确保您出于正当理由禁用它们。
<!-- svelte-ignore a11y-autofocus -->
<input bind:value={name} autofocus />
您可以添加一个以 @component
开头的特殊注释,该注释将在悬停在其他文件中的组件名称上时显示。
<!--
@component
- You can use markdown here.
- You can also use code blocks here.
- Usage:
```html
<Main name="Arethra">
```
-->
<script>
let { name } = $props();
</script>
<main>
<h1>
Hello, {name}
</h1>
</main>