0Pricing
Vue Academy · Урок

Типизированные свойства и события с defineProps/defineEmits

Обобщённый defineProps (), сложные типы, необязательные свойства и типизация событий

«Типизированные свойства и события с defineProps/defineEmits» — бесплатный урок Vue Academy на CoddyKit. Это урок 2 из 4. Ты можешь прочитать весь урок бесплатно ниже — а потом практиковать его прямо в браузере с встроенным редактором кода и ИИ-репетитором 24/7. Это часть пути обучения Vue Academy, и твой прогресс синхронизируется между веб-версией и приложением CoddyKit. Курс Vue Academy содержит 4 уроков всего.

Типизация входных и выходных данных компонентов

С lang="ts" макросы defineProps и defineEmits принимают типы TypeScript напрямую. Благодаря этому во время компиляции проверяется, какие данные поступают в компонент и выходят из него.

Props из интерфейса

Передайте тип в обобщённый параметр defineProps. Интерфейс помогает сделать сложные формы Props понятными и пригодными для повторного использования.

<script setup lang="ts">
interface Props {
  title: string
  count: number
}
const props = defineProps<Props>()
</script>

Встроенные литералы типов

Для небольших компонентов подходит встроенный тип объекта — отдельный интерфейс не нужен.

<script setup lang="ts">
const props = defineProps<{
  label: string
  disabled: boolean
}>()
</script>

Необязательные свойства с ?

Пометьте свойство как необязательное с помощью ?. Необязательные props имеют тип T | undefined, и родительский компонент может их не передавать.

<script setup lang="ts">
interface Props {
  title: string
  subtitle?: string
}
const props = defineProps<Props>()
</script>

Сложные типы Props

Props могут быть массивами, объединениями или формами объектов — всем, что может выразить TypeScript.

<script setup lang="ts">
interface Props {
  items: string[]
  size: 'sm' | 'md' | 'lg'
  user: { id: number; name: string }
}
const props = defineProps<Props>()
</script>

Значения по умолчанию с withDefaults

Форма, содержащая только тип, не может хранить значения по умолчанию, поэтому оберните её в withDefaults. Второй аргумент сопоставляет имена Props со значениями по умолчанию.

<script setup lang="ts">
const props = withDefaults(defineProps<{
  size?: string
  count?: number
}>(), {
  size: 'md',
  count: 0
})
</script>

Значения по умолчанию для объектов и массивов

Значения по умолчанию для объектов и массивов должны возвращаться фабричной функцией, как и в API параметров, чтобы один экземпляр не использовался несколькими компонентами.

withDefaults(defineProps<{
  tags?: string[]
}>(), {
  tags: () => []
})

Объявление типизированных событий

defineEmits может принимать тип, в котором каждое событие и его данные описаны сигнатурой вызова. Благодаря этому неправильные типы данных обнаруживаются во время компиляции.

<script setup lang="ts">
const emit = defineEmits<{
  (e: 'change', value: string): void
  (e: 'delete', id: number): void
}>()
</script>

Отправка типизированных данных событий

Теперь emit принимает только допустимые имена событий и соответствующие типы данных. Передача числа вместо ожидаемой строки вызывает ошибку компиляции.

function rename(name: string) {
  emit('change', name) // ok
  // emit('change', 123) // type error
}

Синтаксис именованных кортежей

Vue 3.3+ поддерживает сокращённую форму объекта, в которой каждому событию соответствует кортеж типов его аргументов. Она понятнее сигнатур вызова.

<script setup lang="ts">
const emit = defineEmits<{
  change: [value: string]
  delete: [id: number]
}>()
</script>

Props и события вместе

Обычно типизированный компонент объявляет и то и другое: входные данные через defineProps и выходные данные через defineEmits, полностью проверяя их от начала до конца.

<script setup lang="ts">
defineProps<{ modelValue: string }>()
const emit = defineEmits<{
  'update:modelValue': [value: string]
}>()
</script>

Быстрая проверка

Проверьте свои знания о типизированных props и событиях.

Итоги

Вы научились типизировать входные и выходные данные компонентов:

  • Передавать интерфейс или встроенный тип в defineProps<T>().
  • Использовать ? для необязательных props и withDefaults для значений по умолчанию (для объектов и массивов — фабричную функцию).
  • С помощью defineEmits<T>() задавать типы имён событий и их данных.
  • Использовать форму кортежа (event: [payload]) как современный сокращённый синтаксис.

Часто задаваемые вопросы

Урок «Типизированные свойства и события с defineProps/defineEmits» бесплатный?

Да — полный текст урока «Типизированные свойства и события с defineProps/defineEmits» бесплатно доступен здесь в веб-версии. Чтобы практиковать его интерактивно (встроенный редактор кода и ИИ-репетитор 24/7) и разблокировать остальной курс Vue Academy, подпишись на CoddyKit PRO. Курс Vue Academy содержит 4 уроков всего.

Чему я научусь в уроке «Типизированные свойства и события с defineProps/defineEmits»?

Обобщённый defineProps (), сложные типы, необязательные свойства и типизация событий Ты практикуешь Vue Academy с помощью реального кода, который запускаешь прямо в браузере, и ИИ-репетитор 24/7 отвечает на твои вопросы во время урока.

Нужен ли мне опыт, чтобы начать Vue Academy?

Предыдущий опыт не требуется. Vue Academy на CoddyKit структурирован для всех уровней — от новичков до продвинутых, поэтому ты можешь начать отсюда или с самого начала и учиться в своем темпе. Это урок 2 из 4.

Сколько времени занимает урок «Типизированные свойства и события с defineProps/defineEmits»?

Большинство уроков CoddyKit занимают около 5–10 минут. Каждый из них компактный и интерактивный, поэтому ты постоянно делаешь прогресс и продолжаешь с того же места в веб-версии и приложении.

Можно ли писать и запускать код в этом уроке Vue Academy?

Да. Каждый урок Vue Academy включает встроенный редактор кода, поэтому ты пишешь и запускаешь реальный код прямо в браузере и получаешь моментальную обратную связь от AI — локальная установка не требуется.

Все уроки этого курса

  1. Настройка TypeScript в проектах Vue
  2. Типизированные свойства и события с defineProps/defineEmits
  3. Типизация композируемых модулей и ссылок
  4. Обобщённые компоненты Vue
← Назад к Vue Academy