SvelteKit предоставляет мощный каркас для создания современных веб-приложений на основе Svelte. Одним из ключевых аспектов разработки интерфейсов является эффективная стилизация компонентов. Комбинация Tailwind CSS и class-variance-authority (CVA) обеспечивает гибкий, декларативный подход к управлению классами и состояниями компонентов.
Для начала необходимо установить Tailwind CSS и его зависимости:
npm install -D tailwindcss postcss autoprefixer
npx tailwindcss init tailwind.config.cjs -p
Конфигурационный файл tailwind.config.cjs позволяет
указать пути к файлам, где Tailwind должен искать классы:
/** @type {import('tailwindcss').Config} */
module.exports = {
content: [
'./src/**/*.{html,js,svelte,ts}'
],
theme: {
extend: {},
},
plugins: [],
}
Включение Tailwind в SvelteKit осуществляется через
src/app.css:
@tailwind base;
@tailwind components;
@tailwind utilities;
Импорт этого файла в src/routes/+layout.svelte
обеспечивает глобальную доступность классов:
<script lang="ts">
import "../app.css";
</script>
<slot />
class-variance-authority (CVA) — это библиотека для декларативного управления комбинациями CSS-классов на основе состояний компонента. Она особенно полезна в сочетании с Tailwind, где часто возникают длинные цепочки утилитарных классов.
Установка CVA:
npm install class-variance-authority
Основная идея CVA — создание функции cva, которая
возвращает строку классов на основе переданных опций. Пример для
кнопки:
import { cva } from 'class-variance-authority';
const button = cva(
'px-4 py-2 font-semibold rounded-md transition-colors',
{
variants: {
color: {
primary: 'bg-blue-600 text-white hover:bg-blue-700',
secondary: 'bg-gray-200 text-gray-800 hover:bg-gray-300',
},
size: {
small: 'text-sm',
medium: 'text-base',
large: 'text-lg',
},
disabled: {
true: 'opacity-50 cursor-not-allowed',
}
},
defaultVariants: {
color: 'primary',
size: 'medium',
disabled: false,
},
}
);
Использование в SvelteKit компоненте:
<script lang="ts">
import { button } from './buttonStyles';
export let color: 'primary' | 'secondary' = 'primary';
export let size: 'small' | 'medium' | 'large' = 'medium';
export let disabled: boolean = false;
</script>
<button class={button({ color, size, disabled })} disabled={disabled}>
<slot />
</button>
Такой подход минимизирует повторение классов и упрощает поддержку сложных UI.
CVA позволяет управлять динамическими состояниями без использования условных операторов в шаблоне Svelte. Например, для кнопки с состоянием загрузки:
const loadingButton = cva(
'px-4 py-2 font-semibold rounded-md flex items-center justify-center gap-2',
{
variants: {
loading: {
true: 'cursor-wait opacity-70',
false: '',
},
color: {
primary: 'bg-blue-600 text-white hover:bg-blue-700',
secondary: 'bg-gray-200 text-gray-800 hover:bg-gray-300',
},
},
defaultVariants: {
loading: false,
color: 'primary',
},
}
);
Использование:
<script lang="ts">
import { loadingButton } from './buttonStyles';
export let loading: boolean = false;
</script>
<button class={loadingButton({ loading })} disabled={loading}>
{#if loading}
Загрузка...
{:else}
Отправить
{/if}
</button>
Такой подход позволяет легко расширять компонент новыми вариантами без дублирования классов.
CVA особенно полезна для сложных компонентов, таких как карточки, модальные окна, табы, формы. Пример карточки с несколькими вариантами состояния:
import { cva } from 'class-variance-authority';
export const card = cva(
'rounded-lg shadow-md p-4 transition-all',
{
variants: {
variant: {
elevated: 'shadow-lg',
flat: 'shadow-none border border-gray-200',
},
highlight: {
true: 'ring-2 ring-blue-500',
false: '',
},
},
defaultVariants: {
variant: 'flat',
highlight: false,
},
}
);
Использование в SvelteKit:
<script lang="ts">
import { card } from './cardStyles';
export let variant: 'elevated' | 'flat' = 'flat';
export let highlight: boolean = false;
</script>
<div class={card({ variant, highlight })}>
<slot />
</div>
Такой подход обеспечивает чистую и поддерживаемую архитектуру UI, где стили полностью управляются декларативно через Tailwind и CVA.
src/lib/styles для повторного использования.variants без изменения шаблона Svelte.Tailwind CSS и class-variance-authority создают мощный дуэт для построения масштабируемых интерфейсов в SvelteKit, позволяя управлять сложными комбинациями классов декларативно и поддерживать единый стиль компонентов по всему проекту.