4.3 KiB
Extending the Default Theme
VitePress' default theme is optimized for documentation, and can be customized. Consult the Default Theme Config Overview for a comprehensive list of options.
However, there are a number of cases where configuration alone won't be enough. For example:
- You need to tweak the CSS styling;
- You need to modify the Vue app instance, for example to register global components;
- You need to inject custom content into the theme via layout slots.
These advanced customizations will require using a custom theme that "extends" the default theme.
:::tip Before proceeding, make sure to first read Using a Custom Theme to understand how custom themes work. :::
Customizing CSS
The default theme CSS is customizable by overriding root level CSS variables:
// .vitepress/theme/index.js
import DefaultTheme from 'vitepress/theme'
import './custom.css'
export default DefaultTheme
/* .vitepress/theme/custom.css */
:root {
--vp-c-brand: #646cff;
--vp-c-brand-light: #747bff;
}
See default theme CSS variables that can be overridden.
Registering Global Components
// .vitepress/theme/index.js
import DefaultTheme from 'vitepress/theme'
export default {
extends: DefaultTheme,
enhanceApp(ctx) {
// register your custom global components
ctx.app.component('MyGlobalComponent' /* ... */)
}
}
Since we are using Vite, you can also leverage Vite's glob import feature to auto register a directory of components.
Layout Slots
The default theme's <Layout/> component has a few slots that can be used to inject content at certain locations of the page. Here's an example of injecting a component into the before outline:
// .vitepress/theme/index.js
import DefaultTheme from 'vitepress/theme'
import MyLayout from './MyLayout.vue'
export default {
...DefaultTheme,
// override the Layout with a wrapper component that
// injects the slots
Layout: MyLayout
}
<!--.vitepress/theme/MyLayout.vue-->
<script setup>
import DefaultTheme from 'vitepress/theme'
const { Layout } = DefaultTheme
</script>
<template>
<Layout>
<template #aside-outline-before>
My custom sidebar top content
</template>
</Layout>
</template>
Or you could use render function as well.
// .vitepress/theme/index.js
import { h } from 'vue'
import DefaultTheme from 'vitepress/theme'
import MyComponent from './MyComponent.vue'
export default {
...DefaultTheme,
Layout() {
return h(DefaultTheme.Layout, null, {
'aside-outline-before': () => h(MyComponent)
})
}
}
Full list of slots available in the default theme layout:
- When
layout: 'doc'(default) is enabled via frontmatter:doc-footer-beforedoc-beforedoc-aftersidebar-nav-beforesidebar-nav-afteraside-topaside-bottomaside-outline-beforeaside-outline-afteraside-ads-beforeaside-ads-after
- When
layout: 'home'is enabled via frontmatter:home-hero-beforehome-hero-infohome-hero-imagehome-hero-afterhome-features-beforehome-features-after
- On not found (404) page:
not-found
- Always:
layout-toplayout-bottomnav-bar-title-beforenav-bar-title-afternav-bar-content-beforenav-bar-content-afternav-screen-content-beforenav-screen-content-after
Overriding Internal Components
You can use Vite's aliases to replace default theme components with your custom ones:
import { fileURLToPath, URL } from 'node:url'
import { defineConfig } from 'vitepress'
export default defineConfig({
vite: {
resolve: {
alias: [
{
find: /^.*\/VPNavBar\.vue$/,
replacement: fileURLToPath(
new URL('./components/CustomNavBar.vue', import.meta.url)
)
}
]
}
}
})
To know the exact name of the component refer our source code. Since the components are internal, there is a slight chance their name is updated between minor releases.