963 markdown files reformatted with the repository's pinned prettier so pnpm format:check covers the folded tree like every other repo file. The formatter's embedded-language pass also normalized code fences (TS semicolons, closed HTML tags in examples, lowercased CSS hex colors, one renumbered list that skipped an index). Alphanumeric token deltas vs the fold commit were audited file-by-file; all are formatter-equivalent markup normalizations plus the four sanitized skills.
3.9 KiB
name, description
| name | description |
|---|---|
| script-setup-macros | Vue 3 script setup syntax and compiler macros for defining props, emits, models, and more |
Script Setup & Macros
<script setup> is the recommended syntax for Vue SFCs with Composition API. It provides better runtime performance and IDE type inference.
Basic Syntax
<script setup lang="ts">
// Top-level bindings are exposed to template
import { ref } from 'vue';
import MyComponent from './MyComponent.vue';
const count = ref(0);
const increment = () => count.value++;
</script>
<template>
<button @click="increment">{{ count }}</button>
<MyComponent />
</template>
defineProps
Declare component props with full TypeScript support.
// Type-based declaration (recommended)
const props = defineProps<{
title: string;
count?: number;
items: string[];
}>();
// With defaults (Vue 3.5+)
const { title, count = 0 } = defineProps<{
title: string;
count?: number;
}>();
// With defaults (Vue 3.4 and below)
const props = withDefaults(
defineProps<{
title: string;
items?: string[];
}>(),
{
items: () => [], // Use factory for arrays/objects
},
);
defineEmits
Declare emitted events with typed payloads.
// Named tuple syntax (recommended)
const emit = defineEmits<{
update: [value: string];
change: [id: number, name: string];
close: [];
}>();
emit('update', 'new value');
emit('change', 1, 'name');
emit('close');
defineModel
Two-way binding prop consumed via v-model. Available in Vue 3.4+.
// Basic usage - creates "modelValue" prop
const model = defineModel<string>();
model.value = 'hello'; // Emits "update:modelValue"
// Named model - consumed via v-model:name
const count = defineModel<number>('count', { default: 0 });
// With modifiers
const [value, modifiers] = defineModel<string>();
if (modifiers.trim) {
// Handle trim modifier
}
// With transformers
const [value, modifiers] = defineModel({
get(val) {
return val?.toLowerCase();
},
set(val) {
return modifiers.trim ? val?.trim() : val;
},
});
Parent usage:
<Child v-model="name" />
<Child v-model:count="total" />
<Child v-model.trim="text" />
defineExpose
Explicitly expose properties to parent via template refs. Components are closed by default.
import { ref } from 'vue';
const count = ref(0);
const reset = () => {
count.value = 0;
};
defineExpose({
count,
reset,
});
Parent access:
const childRef = ref<{ count: number; reset: () => void }>();
childRef.value?.reset();
defineOptions
Declare component options without a separate <script> block. Available in Vue 3.3+.
defineOptions({
inheritAttrs: false,
name: 'CustomName',
});
defineSlots
Provide type hints for slot props. Available in Vue 3.3+.
const slots = defineSlots<{
default(props: { item: string; index: number }): any;
header(props: { title: string }): any;
}>();
Generic Components
Declare generic type parameters using the generic attribute.
<script setup lang="ts" generic="T extends string | number">
defineProps<{
items: T[];
selected: T;
}>();
</script>
Multiple generics with constraints:
<script setup lang="ts" generic="T, U extends Record<string, T>">
import type { Item } from './types';
defineProps<{
data: U;
key: keyof U;
}>();
</script>
Local Custom Directives
Use vNameOfDirective naming convention.
const vFocus = {
mounted: (el: HTMLElement) => el.focus(),
};
// Or import and rename
import { myDirective as vMyDirective } from './directives';
<template>
<input v-focus />
</template>
Top-level await
Use await directly in <script setup>. The component becomes async and must be used with <Suspense>.
<script setup lang="ts">
const data = await fetch('/api/data').then((r) => r.json());
</script>