Однофайловые компоненты (Single File Components — SFC) — это фундаментальная концепция Vue.js, позволяющая инкапсулировать шаблон, логику и стили компонента в одном файле с расширением .vue
.
Типичный файл .vue
состоит из трех основных секций:
<template>
<!-- HTML-шаблон компонента -->
<div class="example">{{ message }}</div>
</template>
<script>
// Логика компонента
export default {
data() {
return {
message: 'Привет, Vue!'
}
}
}
</script>
<style>
/* Стили компонента */
.example {
color: #42b983;
}
</style>
Полная инкапсуляция
Все части компонента находятся в одном месте, что упрощает поддержку.
Модульность
Каждый компонент — самостоятельная единица, которую легко повторно использовать.
Горячая перезагрузка (HMR)
Возможность обновлять компоненты без перезагрузки страницы.
Предпроцессоры
Поддержка Sass, Less, TypeScript, JSX и других языков.
Область видимости стилей
Стили можно ограничить только текущим компонентом.
<template>
<div>
<h1>{{ title }}</h1>
<button @click="handleClick">Нажми меня</button>
</div>
</template>
<script setup>
)<script>
// Options API
export default {
data() {
return { count: 0 }
},
methods: {
increment() {
this.count++
}
}
}
</script>
<script setup>
// Composition API
import { ref } from 'vue'
const count = ref(0)
const increment = () => count.value++
</script>
<style scoped>
/* Стили только для этого компонента */
.button {
background: #42b983;
}
</style>
<style lang="scss">
/* Использование Sass */
$primary-color: #42b983;
.title {
color: $primary-color;
}
</style>
Добавляет уникальные атрибуты к элементам, ограничивая область действия стилей:
<style scoped>
.example { color: red; }
</style>
<!-- Преобразуется в -->
<div class="example" data-v-f3f3eg9>...</div>
<style>
.example[data-v-f3f3eg9] { color: red; }
</style>
Ленивая загрузка компонентов:
const AsyncComponent = defineAsyncComponent(() =>
import('./components/AsyncComponent.vue')
)
Можно добавлять собственные блоки для документации или тестов:
<docs>
Это компонент кнопки. Используется для...
</docs>
<template>
<div class="user-card">
<img :src="avatar" :alt="name" />
<h2>{{ name }}</h2>
<p>{{ bio }}</p>
<button @click="follow">Подписаться</button>
</div>
</template>
<script setup>
import { ref } from 'vue'
const props = defineProps({
name: String,
bio: String,
avatar: String
})
const isFollowing = ref(false)
const follow = () => {
isFollowing.value = !isFollowing.value
}
</script>
<style lang="scss" scoped>
.user-card {
border: 1px solid #eee;
border-radius: 8px;
padding: 16px;
img {
width: 100px;
height: 100px;
border-radius: 50%;
}
button {
background: #42b983;
color: white;
padding: 8px 16px;
border: none;
border-radius: 4px;
cursor: pointer;
&:hover {
opacity: 0.9;
}
}
}
</style>
.vue
файлы, содержащие шаблон, логику и стили<template>
, <script>
и <style>
Однофайловые компоненты — это: