Svelte 在操作样式类方面与 Vue 较为接近,是直接内置了对样式类操作的支持,不过没有 Vue 支持得那么强大。
样式类
<!-- 设置样式类和其他属性一样 -->
{#each ['foo', 'baz', 'bar'] as value}
<button
class="{current === value ? 'selected' : ''}"
on:click="{() => current = value}"
>
{value}
</button>
{/each}
<!-- 上述的书写方式有一种简写方式 -->
{#each ['foo', 'baz', 'bar'] as value}
<button
class:selected="{current === value}"
on:click="{() => current = value}"
>
{value}
</button>
{/each}
<script>
let value = 0
</script>
<!-- 简写方式不仅仅局限于selected,checked属性, 别的属性也可以使用 -->
今天收入:<input bind:value class:error={isNaN(Number(value))} />
<style>
.error { border: 1px solid red; }
input { outline: 0 none; }
</style>
class 简写
<!-- 原始写法 -->
<div class:big={big}>
<!-- ... -->
</div>
<!-- 如果样式名和变量名同名,可以简写 -->
<div class:big>
<!-- ... -->
</div>
CSS自定义属性
也就是在css中使用变量,在一定程度上实现了css in js, 这在一键给网页换肤的时候十分有用
这是 v3.38.0 新增的功能
<script>
let color = 'red';
</script>
<style>
.btn {
color: var(--color); /* 使用变量值 */
border: 1px solid var(--color);
padding: 3px;
}
.button {
color: var(--color);
border: 1px solid #ccc;
padding: 3px;
}
</style>
<!--
定义局部变量值
这个变量`--color`只能在`class`为`btn`的`span`标签的样式设置中使用
-->
<span class="btn" style="--color: {color}">按钮</span>
<!-- 在这个span中,是没有--color这个变量的,所以color样式并不会生效 -->
<span class="button">button</span>
<!-- 父组件 -->
<script>
import Btn from './Btn.svelte'
let color = 'blue'
</script>
<!-- 将样式变量传递给子组件 -->
<Btn --color={color} />
<!-- 子组件 -->
<style>
.btn {
/*
对于样式变量(所有以--开头的变量)
svelte的子组件可以直接使用,而不用使用export关键字接收
如果父组件并没有传递过来这个样式变量,那么这个样式不会生效,但不会报错
*/
color: var(--color);
border: 1px solid var(--color);
padding: 3px;
}
</style>
<span class="btn">按钮</span>
<!-- 父组件 -->
<script>
import Btn from './Btn.svelte'
let color = 'red';
</script>
<style>
.btn {
color: var(--color);
border: 1px solid var(--color);
padding: 3px;
}
</style>
<div class="btn" style="--color: {color}">
<Btn />
</div>
<!----------------------------------------------->
<!--
父组件中定义的变量--color会一直往下传,包括子组件和孙子组件
所以CSS 变量会破坏 Svelte 组件局部作用域的特性,使用需要谨慎
-->
<!-- 中间组件 Btn.svelte -->
<span class="btn">
<Button />
</span>
<script>
import Button from './Button.svelte'
</script>
<style>
.btn {
color: var(--color);
border: 1px solid var(--color);
padding: 3px;
}
</style>
<!----------------------------------------------->
<!-- 子组件 Button.svelte -->
<style>
.btn {
color: var(--color);
border: 1px solid var(--color);
padding: 3px;
}
</style>
<span class="btn">按钮</span>
全局样式
<style> 块中的 CSS,其作用域受限于该组件。
这是通过向元素添加一个类来实现的,该类基于组件样式的哈希值而生成的(例如 svelte-123xyz)。
也就是如果多个组件内容是类似的时候,生成的样式的哈希值可能会是一致的
<style>
p {
/* 这仅对本组件的 <p> 元素有效果 */
color: blue;
}
</style>
<style>
:global(body) {
/* 这个样式就是全局的 */
margin: 0;
}
div :global(strong) {
/* 这将适用于任何组件中属于该组件的<div>元素内的所有<strong>元素 */
color: goldenrod;
}
</style>
<style>
/*
要使 @keyframes 可以被全局访问,则需要在关键帧名称前添加 -global- 前缀。
编译时,将自动移除 -global- 部分,然后仅使用代码的其他部分的 my-animation-name 来引用关键帧。
*/
@keyframes -global-my-animation-name {...}
</style>