feat: support customizing default theme via slots

Example:

```js
// .vitepress/theme/index.js
import { h } from 'vue'
import { defaultTheme } from 'vitepress'

const BaseLayout = defaultTheme.Layout

defaultTheme.Layout = () => {
  return h(BaseLayout, null, {
    'page-top-ads': () => h('h2', 'top ads!'),
    'page-bottom-ads': () => h('h2', 'bottom ads!'),
  })
}

export default defaultTheme
```
pull/183/head
Evan You 4 years ago
parent 7dd5c24a5f
commit b8e892e94a

@ -2,7 +2,6 @@
// so the user can do `import { useRoute, useSiteData } from 'vitepress'` // so the user can do `import { useRoute, useSiteData } from 'vitepress'`
// generic types // generic types
export type { SiteData, PageData } from '/@types/shared'
export type { Router, Route } from './router' export type { Router, Route } from './router'
// theme types // theme types
@ -25,3 +24,6 @@ import { ComponentOptions } from 'vue'
import _Debug from './components/Debug.vue' import _Debug from './components/Debug.vue'
const Debug = _Debug as ComponentOptions const Debug = _Debug as ComponentOptions
export { Debug } export { Debug }
// default theme
export { default as defaultTheme } from '/@default-theme/index'

@ -8,6 +8,7 @@
"types": ["vite"], "types": ["vite"],
"paths": { "paths": {
"/@theme/*": ["theme-default/*"], "/@theme/*": ["theme-default/*"],
"/@default-theme/*": ["theme-default/*"],
"/@shared/*": ["shared/*"], "/@shared/*": ["shared/*"],
"/@types/*": ["../../types/*"], "/@types/*": ["../../types/*"],
"vitepress": ["app/exports.ts"] "vitepress": ["app/exports.ts"]

@ -2,7 +2,7 @@ import path from 'path'
import fs from 'fs-extra' import fs from 'fs-extra'
import chalk from 'chalk' import chalk from 'chalk'
import globby from 'globby' import globby from 'globby'
import { createResolver, APP_PATH } from './resolver' import { createResolver, APP_PATH, DEFAULT_THEME_PATH } from './resolver'
import { Resolver } from 'vite' import { Resolver } from 'vite'
import { SiteData, HeadConfig, LocaleConfig } from '../../types/shared' import { SiteData, HeadConfig, LocaleConfig } from '../../types/shared'
import { MarkdownOptions } from './markdown/markdown' import { MarkdownOptions } from './markdown/markdown'
@ -48,7 +48,7 @@ export async function resolveConfig(
const userThemeDir = resolve(root, 'theme') const userThemeDir = resolve(root, 'theme')
const themeDir = (await fs.pathExists(userThemeDir)) const themeDir = (await fs.pathExists(userThemeDir))
? userThemeDir ? userThemeDir
: path.join(__dirname, '../client/theme-default') : DEFAULT_THEME_PATH
const config: SiteConfig = { const config: SiteConfig = {
root, root,

@ -4,6 +4,10 @@ import { UserConfig } from './config'
export const APP_PATH = path.join(__dirname, '../client/app') export const APP_PATH = path.join(__dirname, '../client/app')
export const SHARED_PATH = path.join(__dirname, '../client/shared') export const SHARED_PATH = path.join(__dirname, '../client/shared')
export const DEFAULT_THEME_PATH = path.join(
__dirname,
'../client/theme-default'
)
// special virtual file // special virtual file
// we can't directly import '/@siteData' becase // we can't directly import '/@siteData' becase
@ -25,6 +29,7 @@ export function createResolver(
...userConfig.alias, ...userConfig.alias,
'/@app/': APP_PATH, '/@app/': APP_PATH,
'/@theme/': themeDir, '/@theme/': themeDir,
'/@default-theme/': DEFAULT_THEME_PATH,
'/@shared/': SHARED_PATH, '/@shared/': SHARED_PATH,
vitepress: '/@app/exports.js', vitepress: '/@app/exports.js',
[SITE_DATA_ID]: SITE_DATA_REQUEST_PATH [SITE_DATA_ID]: SITE_DATA_REQUEST_PATH

1
types/index.d.ts vendored

@ -2,3 +2,4 @@ export * from './shared'
export * from '../dist/node/index' export * from '../dist/node/index'
export * from '../dist/client/app/exports' export * from '../dist/client/app/exports'
export * from '../dist/client/theme-default/config' export * from '../dist/client/theme-default/config'
export { default as defaultTheme } from '../dist/client/theme-default/index'

Loading…
Cancel
Save