pages
Vue Router
如果您只使用 app.vue
,它將不會被包含。要強制使用頁面系統,請在 nuxt.config
中設定 pages: true
或擁有一個 router.options.ts
。使用
頁面是 Vue 元件,可以擁有 Nuxt 支援的任何有效副檔名(預設情況下為 .vue
、.js
、.jsx
、.mjs
、.ts
或 .tsx
)。
Nuxt 將自動為您 ~/pages/
目錄中的每個頁面建立路由。
<template>
<h1>Index page</h1>
</template>
// https://vuejs.tw/guide/extras/render-function.html
export default defineComponent({
render () {
return h('h1', 'Index page')
},
})
// https://nuxtjs.tw/docs/4.x/examples/advanced/jsx
// https://vuejs.tw/guide/extras/render-function.html#jsx-tsx
export default defineComponent({
render () {
return <h1>Index page</h1>
},
})
app/pages/index.vue
檔案將被對映到應用程式的 /
路由。
如果您正在使用 app.vue
,請確保使用 <NuxtPage/>
元件來顯示當前頁面。
<template>
<div>
<!-- Markup shared across all pages, ex: NavBar -->
<NuxtPage />
</div>
</template>
頁面必須只有一個根元素,才能在頁面之間實現路由過渡。HTML 註釋也被視為元素。
這意味著當路由在伺服器端渲染或靜態生成時,您將能夠正確看到其內容,但當您在客戶端導航期間導航到該路由時,路由之間的過渡將失敗,並且您會看到該路由將不會被渲染。
以下是一些示例,說明具有單個根元素的頁面是什麼樣的
<template>
<div>
<!-- This page correctly has only one single root element -->
Page content
</div>
</template>
<template>
<!-- This page will not render when route changes during client side navigation, because of this comment -->
<div>Page content</div>
</template>
<template>
<div>This page</div>
<div>Has more than one root element</div>
<div>And will not render when route changes during client side navigation</div>
</template>
動態路由
如果您將任何內容放在方括號內,它將變成一個動態路由引數。您可以在檔名或目錄中混合搭配多個引數,甚至是非動態文字。
如果您希望某個引數是可選的,則必須將其用雙括號括起來——例如,~/pages/[[slug]]/index.vue
或 ~/pages/[[slug]].vue
將匹配 /
和 /test
。
-| pages/
---| index.vue
---| users-[group]/
-----| [id].vue
根據上述示例,您可以透過 $route
物件在元件中訪問 group/id
<template>
<p>{{ $route.params.group }} - {{ $route.params.id }}</p>
</template>
導航到 /users-admins/123
將渲染
<p>admins - 123</p>
如果您想使用 Composition API 訪問路由,有一個全域性的 useRoute
函式,它允許您像 Options API 中的 this.$route
一樣訪問路由。
<script setup lang="ts">
const route = useRoute()
if (route.params.group === 'admins' && !route.params.id) {
console.log('Warning! Make sure user is authenticated!')
}
</script>
/foo/hello
路由,~/pages/foo.vue
將優先於 ~/pages/foo/[slug].vue
。使用
~/pages/foo/index.vue
和 ~/pages/foo/[slug].vue
來匹配 /foo
和 /foo/hello
,並使用不同的頁面。捕獲所有路由
如果您需要一個包羅永珍的路由,您可以透過使用名為 [...slug].vue
的檔案來建立它。這將匹配該路徑下的所有路由。
<template>
<p>{{ $route.params.slug }}</p>
</template>
導航到 /hello/world
將渲染
<p>["hello", "world"]</p>
巢狀路由
可以顯示巢狀路由與 <NuxtPage>
。
示例
-| pages/
---| parent/
-----| child.vue
---| parent.vue
此檔案樹將生成這些路由
[
{
path: '/parent',
component: '~/pages/parent.vue',
name: 'parent',
children: [
{
path: 'child',
component: '~/pages/parent/child.vue',
name: 'parent-child',
},
],
},
]
要顯示 child.vue
元件,您必須將 <NuxtPage>
元件插入到 app/pages/parent.vue
中
<template>
<div>
<h1>I am the parent view</h1>
<NuxtPage :foobar="123" />
</div>
</template>
<script setup lang="ts">
const props = defineProps({
foobar: String,
})
console.log(props.foobar)
</script>
子路由鍵
如果您想對 <NuxtPage>
元件何時重新渲染(例如,用於過渡)進行更多控制,您可以透過 pageKey
prop 傳遞字串或函式,或者透過 definePageMeta
定義 key
值
<template>
<div>
<h1>I am the parent view</h1>
<NuxtPage :page-key="route => route.fullPath" />
</div>
</template>
或者
<script setup lang="ts">
definePageMeta({
key: route => route.fullPath,
})
</script>
路由組
在某些情況下,您可能希望以不影響基於檔案的路由的方式將一組路由分組。為此,您可以將檔案放在用括號括起來的資料夾中——(
和 )
。
例如
-| pages/
---| index.vue
---| (marketing)/
-----| about.vue
-----| contact.vue
這將在你的應用中生成 /
、/about
和 /contact
頁面。 marketing
組在 URL 結構中會被忽略。
頁面元資料
您可能希望為應用程式中的每個路由定義元資料。您可以使用 definePageMeta
宏來完成此操作,它在 <script>
和 <script setup>
中都有效
<script setup lang="ts">
definePageMeta({
title: 'My home page',
})
</script>
然後可以透過 route.meta
物件在應用程式的其餘部分訪問此資料。
<script setup lang="ts">
const route = useRoute()
console.log(route.meta.title) // My home page
</script>
如果您正在使用巢狀路由,則所有這些路由的頁面元資料將合併到一個物件中。有關路由元資料的更多資訊,請參閱vue-router 文件.
與 defineEmits
或 defineProps
(參見Vue 文件)非常相似,definePageMeta
是一個編譯器宏。它將被編譯掉,因此您無法在元件中引用它。相反,傳遞給它的元資料將被提升到元件之外。因此,頁面元物件不能引用元件。但是,它可以引用匯入的繫結以及本地定義的純函式。
<script setup lang="ts">
import { someData } from '~/utils/example'
function validateIdParam (route) {
return route.params.id && !Number.isNaN(Number(route.params.id))
}
const title = ref('')
definePageMeta({
validate: validateIdParam,
someData,
title, // do not do this, the ref will be hoisted out of the component
})
</script>
特殊元資料
當然,歡迎您在應用程式中定義自己的元資料。但是,使用 definePageMeta
定義的一些元資料具有特定用途
alias
您可以定義頁面別名。它們允許您從不同的路徑訪問同一頁面。它可以是字串或字串陣列,如vue-router 文件中所定義.
keepalive
如果您在 definePageMeta
中設定了 keepalive: true
,Nuxt 會自動將您的頁面包裝在Vue <KeepAlive>
元件中。這可能很有用,例如,在具有動態子路由的父路由中,如果您想在路由更改時保留頁面狀態。
當您的目標是保留父路由的狀態時,請使用以下語法:<NuxtPage keepalive />
。您還可以設定要傳遞給 <KeepAlive>
的 props(參見完整列表).
您可以在您的 nuxt.config
中為此屬性設定預設值。
key
參見上方.
layout
您可以定義用於渲染路由的佈局。它可以是 false(停用任何佈局),一個字串或一個 ref/computed,如果您想以某種方式使其具有響應性。關於佈局的更多資訊。
layoutTransition
和 pageTransition
您可以為包裝頁面和佈局的 <transition>
元件定義過渡屬性,或者傳入 false
來停用該路由的 <transition>
包裝器。您可以檢視可以傳遞的選項列表或閱讀更多關於過渡如何工作的資訊.
您可以在您的 nuxt.config
中為此屬性設定預設值。
middleware
您可以定義在載入此頁面之前應用的中介軟體。它將與任何匹配的父/子路由中使用的所有其他中介軟體合併。它可以是字串、函式(遵循全域性前置守衛模式的匿名/內聯中介軟體函式)或字串/函式的陣列。關於命名中介軟體的更多資訊。
name
您可以為此頁面的路由定義名稱。
path
如果您有比檔名更復雜的模式,可以定義路徑匹配器。請參閱vue-router
文件獲取更多資訊。
props
允許將路由 params
作為 props 傳遞給頁面元件。請參閱vue-router
文件獲取更多資訊。
自定義元資料的型別化
如果您為頁面添加了自定義元資料,您可能希望以型別安全的方式進行。可以增強 definePageMeta
接受的物件的型別
declare module '#app' {
interface PageMeta {
pageType?: string
}
}
// It is always important to ensure you import/export something when augmenting a type
export {}
導航
要在應用程式頁面之間導航,您應該使用 <NuxtLink>
元件。
此元件已包含在 Nuxt 中,因此您無需像其他元件一樣匯入它。
指向 app/pages
資料夾中 index.vue
頁面的簡單鏈接
<template>
<NuxtLink to="/">Home page</NuxtLink>
</template>
程式設計式導航
Nuxt 允許透過 navigateTo()
實用方法進行程式設計導航。使用此實用方法,您將能夠在應用程式中以程式設計方式導航使用者。這對於獲取使用者輸入並在整個應用程式中動態導航他們非常有用。在此示例中,我們有一個名為 navigate()
的簡單方法,當用戶提交搜尋表單時會呼叫該方法。
await
navigateTo
或透過從函式返回來鏈式處理其結果。<script setup lang="ts">
const name = ref('')
const type = ref(1)
function navigate () {
return navigateTo({
path: '/search',
query: {
name: name.value,
type: type.value,
},
})
}
</script>
僅限客戶端頁面
您可以透過給頁面新增 .client.vue
字尾將其定義為僅限客戶端。此頁面的任何內容都不會在伺服器上渲染。
僅限伺服器頁面
您可以透過給頁面新增 .server.vue
字尾將其定義為僅限伺服器。雖然您可以使用客戶端導航(由 vue-router
控制)導航到該頁面,但它將自動使用伺服器元件渲染,這意味著渲染該頁面所需的程式碼將不會在您的客戶端包中。
自定義路由
隨著您的應用程式變得越來越大和複雜,您的路由可能需要更大的靈活性。為此,Nuxt 直接公開了路由器、路由和路由器選項,以便以不同的方式進行自定義。
多個頁面目錄
預設情況下,您的所有頁面都應位於專案根目錄下的一個 app/pages
目錄中。
但是,您可以使用 Nuxt Layers 來建立應用程式頁面的分組
-| some-app/
---| nuxt.config.ts
---| pages/
-----| app-page.vue
-| nuxt.config.ts
// some-app/nuxt.config.ts
export default defineNuxtConfig({
})
export default defineNuxtConfig({
extends: ['./some-app'],
})