components
components/ 目录是你放置所有 Vue 组件的地方。
Nuxt3 会自动导入该目录中所有组件(以及您可能使用的任何模块注册的组件)
| components/
--| AppHeader.vue
--| AppFooter.vue
- app.vue
<template>
<div>
<AppHeader />
<NuxtPage />
<AppFooter />
</div>
</template>
组件名称
如果您在嵌套目录中有一个组件,例如:
组件名称
- 依据路径结构(引入名称)
| components/
--| base/
----| foo/
------| Button.vue
那么组件的名称将基于其自身的路径目录和文件名,重复的部分将被删除。因此,组件的名称将是
<BaseFooButton />
- 依据文件名称
如果您希望仅根据组件名称而不是路径自动导入组件,则需要使用扩展形式的配置对象将 pathPrefix
选项设置为 false
:
// nuxt.config.ts
export default defineNuxtConfig({
components: [
{
path: '~/components',
+ pathPrefix: false,
},
],
});
例如,~/components/Some/MyComponent.vue
将可用作 <MyComponent>
而不是 <SomeMyComponent>
。
动态组件
如果您想使用 Vue 的 <component :is="someComputedComponent">
语法,您需要使用 Vue 提供的 resolveComponent
辅助函数,或直接从 #components
导入组件并将其传递给 is
属性。
<script setup lang="ts">
import { SomeComponent } from "#components";
const MyButton = resolveComponent("MyButton");
</script>
<template>
<component :is="clickable ? MyButton : 'div'" />
<component :is="SomeComponent" />
</template>
INFO
如果您使用 resolveComponent 处理动态组件,请确保仅插入组件名称,它必须是一个字符串而不是一个变量。
另外,虽然不推荐,但您可以全局注册所有组件,这将为所有组件创建异步块,并使它们在整个应用程序中可用。
export default defineNuxtConfig({
components: {
+ global: true,
+ dirs: ['~/components']
},
})
动态导入
要动态导入组件(也称为延迟加载组件),您只需将 Lazy
前缀添加到组件的名称中。如果组件不总是需要,这特别有用。
通过使用 Lazy
前缀,您可以将组件代码的加载延迟到正确的时机,这有助于优化 JavaScript
包的大小。
<script setup>
const show = ref(false);
</script>
<template>
<div>
<h1>Mountains</h1>
<LazyMountainsList v-if="show" />
<button v-if="!show" @click="show = true">Show List</button>
</div>
</template>
直接导入
如果需要绕过 Nuxt
的自动导入功能,您还可以从 #components
直接导入组件。
<script setup lang="ts">
import { NuxtLink, LazyMountainsList } from "#components";
const show = ref(false);
</script>
<template>
<div>
<h1>Mountains</h1>
<LazyMountainsList v-if="show" />
<button v-if="!show" @click="show = true">Show List</button>
<NuxtLink to="/">Home</NuxtLink>
</div>
</template>
自定义目录
默认情况下,只会扫描 ~/components
目录。如果您想添加其他目录,或更改在该目录的子文件夹中如何扫描组件,您可以将其他目录添加到配置中:
// nuxt.config.ts
export default defineNuxtConfig({
components: [
// ~/calendar-module/components/event/Update.vue => <EventUpdate />
{ path: "~/calendar-module/components" },
// ~/user-module/components/account/UserDeleteDialog.vue => <UserDeleteDialog />
{ path: "~/user-module/components", pathPrefix: false },
// ~/components/special-components/Btn.vue => <SpecialBtn />
{ path: "~/components/special-components", prefix: "Special" },
// 如果您想要覆盖 `~/components` 的子目录,请确保它是最后一个。
//
// ~/components/Btn.vue => <Btn />
// ~/components/base/Btn.vue => <BaseBtn />
"~/components",
],
});
INFO
任何嵌套的目录都需要首先添加,因为它们按顺序扫描。
ClientOnly 组件
Nuxt 提供了 <ClientOnly>
组件,用于仅在客户端渲染组件。
<template>
<div>
<Sidebar />
<ClientOnly>
<!-- 此组件仅在客户端渲染 -->
<Comments />
</ClientOnly>
</div>
</template>
NuxtClientFallback 组件(重点)
Nuxt 提供了 <NuxtClientFallback>
组件,如果其任何子组件在 SSR 中触发错误,则在客户端渲染其内容。
您可以指定 fallbackTag
,以便在服务器端无法渲染时渲染特定的标记。
<template>
<div>
<Sidebar />
<!-- 此组件将在客户端渲染 -->
<NuxtClientFallback fallback-tag="span">
<Comments />
<BrokeInSSR />
</NuxtClientFallback>
</div>
</template>