You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
svelte/documentation/docs/02-template-syntax/05-styles-and-classes.md

4.9 KiB

title
Styles & Classes
  • style scoping
  • :global
  • style:
  • class:
  • --css props

Styling is a fundamental part of UI components. Svelte helps you style your components with ease, providing useful features out of the box.

Scoped by default

By default CSS inside a <style> block will be scoped to that component.

This works by adding a class to affected elements, which is based on a hash of the component styles (e.g. svelte-123xyz).

<style>
	p {
		/* this will only affect <p> elements in this component */
		color: burlywood;
	}
</style>

:global

To apply styles to a selector globally, use the :global(...) modifier.

<style>
	:global(body) {
		/* this will apply to <body> */
		margin: 0;
	}

	div :global(strong) {
		/* this will apply to all <strong> elements, in any
			 component, that are inside <div> elements belonging
			 to this component */
		color: goldenrod;
	}

	p:global(.red) {
		/* this will apply to all <p> elements belonging to this
			 component with a class of red, even if class="red" does
			 not initially appear in the markup, and is instead
			 added at runtime. This is useful when the class
			 of the element is dynamically applied, for instance
			 when updating the element's classList property directly. */
	}
</style>

If you want to make @keyframes that are accessible globally, you need to prepend your keyframe names with -global-.

The -global- part will be removed when compiled, and the keyframe will then be referenced using just my-animation-name elsewhere in your code.

<style>
	@keyframes -global-my-animation-name {
		/* code goes here */
	}
</style>

Nested style tags

There should only be 1 top-level <style> tag per component.

However, it is possible to have a <style> tag nested inside other elements or logic blocks.

In that case, the <style> tag will be inserted as-is into the DOM; no scoping or processing will be done on the <style> tag.

<div>
	<style>
		/* this style tag will be inserted as-is */
		div {
			/* this will apply to all `<div>` elements in the DOM */
			color: red;
		}
	</style>
</div>

class:name

<!--- copy: false --->
class:name={value}
<!--- copy: false --->
class:name

A class: directive provides a shorter way of toggling a class on an element.

<!-- These are equivalent -->
<div class={isActive ? 'active' : ''}>...</div>
<div class:active={isActive}>...</div>

<!-- Shorthand, for when name and value match -->
<div class:active>...</div>

<!-- Multiple class toggles can be included -->
<div class:active class:inactive={!active} class:isAdmin>...</div>

style:property

<!--- copy: false --->
style:property={value}
<!--- copy: false --->
style:property="value"
<!--- copy: false --->
style:property

The style: directive provides a shorthand for setting multiple styles on an element.

<!-- These are equivalent -->
<div style:color="red">...</div>
<div style="color: red;">...</div>

<!-- Variables can be used -->
<div style:color={myColor}>...</div>

<!-- Shorthand, for when property and variable name match -->
<div style:color>...</div>

<!-- Multiple styles can be included -->
<div style:color style:width="12rem" style:background-color={darkMode ? 'black' : 'white'}>...</div>

<!-- Styles can be marked as important -->
<div style:color|important="red">...</div>

When style: directives are combined with style attributes, the directives will take precedence:

<div style="color: blue;" style:color="red">This will be red</div>

--style-props

<!--- copy: false --->
--style-props="anycssvalue"

You can also pass styles as props to components for the purposes of theming, using CSS custom properties.

Svelte's implementation is essentially syntactic sugar for adding a wrapper element. This example:

<Slider bind:value min={0} --rail-color="black" --track-color="rgb(0, 0, 255)" />

Desugars to this:

<div style="display: contents; --rail-color: black; --track-color: rgb(0, 0, 255)">
	<Slider bind:value min={0} max={100} />
</div>

For SVG namespace, the example above desugars into using <g> instead:

<g style="--rail-color: black; --track-color: rgb(0, 0, 255)">
	<Slider bind:value min={0} max={100} />
</g>

Since this is an extra <div> (or <g>), beware that your CSS structure might accidentally target this. Be mindful of this added wrapper element when using this feature.

Svelte's CSS Variables support allows for easily themeable components:

<style>
	.potato-slider-rail {
		background-color: var(--rail-color, var(--theme-color, 'purple'));
	}
</style>

So you can set a high-level theme color:

/* global.css */
html {
	--theme-color: black;
}

Or override it at the consumer level:

<Slider --rail-color="goldenrod" />