仿 ElementPlus 组件库(七)—— 使用 VitePress 生成文档页

1,147 阅读4分钟

在仿 ElementPlus 组件库的开发道路上,我们已经陆续完成了多个重要组件的实现。随着组件数量的不断增加,如何让开发者们更便捷地了解和使用这些组件成为了关键问题。VitePress 作为一款强大的静态网站生成器,为我们提供了一个绝佳的解决方案。接下来,让我们深入探索如何使用 VitePress 为我们的组件库生成高质量的文档页。

一、VitePress 简介

(一)什么是 VitePress

VitePress 是一款专为技术文档和博客打造的静态网站生成器,它巧妙地融合了 Vue 的强大功能与 Vite 的卓越性能。作为 Vue 生态系统的一部分,VitePress 利用 Vue 组件化的开发模式和响应式数据绑定机制,使得文档编写和展示变得更加灵活和高效。同时,Vite 所具备的快速热模块替换(HMR)以及高效的构建优化,为 VitePress 赋予了极快的开发体验和构建速度。

(二)使用 VitePress 的优势

组件库文档生成优势

  • API 自动生成:分析组件源代码,自动提取属性、方法、事件等信息,生成组件 API 文档,保证文档与代码一致性 。
  • 示例代码展示:支持将示例代码嵌入 Markdown,语法高亮且可实时运行,还能对示例分组分类,方便查阅 。

与其他工具对比优势

  • 性能强:相比传统工具如 Sphinx,构建速度快,页面加载流畅,热模块替换功能提升开发体验 。
  • 易用性好:以 Markdown 编写,主题定制和插件系统简单,比 Docusaurus 等工具学习成本低 。

二、搭建 VitePress 项目

(一)安装 VitePress

npm add -D vitepress

构建基本项目

命令行设置向导

运行初始化命令:

npx vitepress init

将看到以下交互式配置流程

    Welcome to VitePress!
    │
    ◇  Where should VitePress initialize the config?
    │  ./docs
    │
    ◇  Where should VitePress look for your markdown files?
    │  ./docs
    │
    ◇  Site title:
    │  My Awesome Project
    │
    ◇  Site description:
    │  A VitePress Site
    │
    ◇  Theme:
    │  Default Theme
    │
    ◇  Use TypeScript for config and theme files?
    │  Yes
    │
    ◇  Add VitePress npm scripts to package.json?
    │  Yes
    │
    ◇  Add a prefix for VitePress npm scripts?
    │  Yes
    │
    ◇  Prefix for VitePress npm scripts:
    │  docs
    │
    └  Done! Now run npm run docs:dev and start writing.

启动 VitePress 项目

    npm run docs:dev

成功启动后:

  1. 项目将生成以下初始文件结构:
        ├── docs/
            ├── .vitepress/
            │   └── config.ts  # TypeScript 配置文件
            ├── api-examples.md
            ├── index.md
            └── markdown-examples.md

image.png

三、将 Vue 组件集成到 VitePress 文档

(一)在文档中展示组件

创建组件文档页面

安装了开发依赖插件,用于在 VitePress 文档中展示组件示例

npm install @vitepress-demo-preview/component @vitepress-demo-preview/plugin --save-dev
  • 引入插件:在 vite.plugins 数组中引入 @vitejs/plugin-vue-jsx 和 unplugin - vue - macros/vite,并对 VueMacros.vite 进行了配置,这有助于支持 Vue JSX 语法以及相关宏功能,为组件的正确解析和展示提供基础。
  • 路径别名设置:在 vite.resolve.alias 中设置 @ 别名,指向项目 src 目录,方便在项目中导入组件和其他资源。
  • Markdown 配置:在 markdown.config 中使用 md.use(containerPreview) 和 md.use(componentPreview),启用插件提供的容器预览和组件预览功能,使得在 Markdown 文档中能够使用特定语法展示组件示例。
  • 主题配置(themeConfig :在 sidebar 配置中添加 Button 组件的文档链接,方便在文档侧边栏导航到 Button 组件的文档页面。
  • config.ts
import vueJsx from '@vitejs/plugin-vue-jsx'
import VueMacros from 'unplugin-vue-macros/vite'
import { containerPreview, componentPreview } from '@vitepress-demo-preview/plugin'
import { fileURLToPath, URL } from 'node:url'

  srcDir: 'components',
  vite: {
    plugins: [
      // eslint-disable-next-line @typescript-eslint/ban-ts-comment
      // @ts-ignore
      VueMacros.vite({
        setupComponent: false,
        setupSFC: false,
        plugins: {
          vueJsx: vueJsx(),
        },
      }),
    ],
    resolve: {
      alias: {
        '@': fileURLToPath(new URL('../../src', import.meta.url))
      }
    }
  },
    markdown: {
    config(md) {
      md.use(containerPreview)
      md.use(componentPreview)
    },
  },
  
  themeConfig: {
    sidebar: [
     //...
      {
        text: 'Basic',
        items: [
          {text: 'Button', link: '/components/button' }
        ]
      }
    ],
   },

新建docs/demo/Button/basic.vue

    <script setup>
    import Button from '@/components/Button/Button.vue'
    </script>
    <template>
    <Button> hello </Button>
    <Button type="primary"> Primary </Button>
    <Button type="danger"> Danger </Button>
    <Button loading> Loading </Button>
    </template>

新建 docs/components/button.md

title: Button 
description: Button 组件的文档
---

# Button 按钮

常用的操作按钮。

## 基础用法

使用 `type``plain``round``circle` 来定义按钮的样式。

<preview path="../demo/Button/Basic.vue" title="基础用法" description="Button 组件的基础用法"></preview>

### Button Attributes

| Name        | Description                            | Type                                                             | Default |
| ----------- | -------------------------------------- | ---------------------------------------------------------------- | ------- |
| size        | button size                            | `enum` - `'large'\| 'small'`                                     | —       |
| type        | button type                            | `enum` - `'primary'\| 'success'\| 'warning'\| 'danger'\| 'info'` | —       |
| plain       | determine whether it's a plain button  | `boolean`                                                        | false   |
| round       | determine whether it's a round button  | `boolean`                                                        | false   |
| circle      | determine whether it's a circle button | `boolean`                                                        | false   |
| loading     | determine whether it's loading         | `boolean`                                                        | false   |
| disabled    | disable the button                     | `boolean`                                                        | false   |
| icon        | icon component                         | `string`                                                         | —       |
| autofocus   | same as native button's `autofocus`    | `boolean`                                                        | false   |
| native-type | same as native button's `type`         | `enum` - `'button'\| 'submit'\| 'reset'`                         | button  |



(二)主题样式修改

新建 .vitepress/theme/custom.css 自定义样式文件

:root {
  --vp-c-brand: var(--yl-color-primary);
  --vp-c-brand-light: var(--yl-color-primary-light-3);
  --vp-c-brand-lighter: var(--yl-color-primary-light-5);
  --vp-c-brand-dark: var(--yl-color-primary-dark-2);
  --vp-c-brand-darker: #265F99;

  --component-preview-bg: var(--vp-code-block-bg);
  --component-preview-soft: var(--vp-code-block-bg-light);
}

body {
  color: var(--vp-c-text-1);
}
h1, h2, h3, h4, h5, h6, p {
  color: var(--vp-c-text-1);
}

导入样式

新建 .vitepress/theme/index.ts

    import DefaultTheme from 'vitepress/theme'
    import { library } from '@fortawesome/fontawesome-svg-core'
    import { fas } from '@fortawesome/free-solid-svg-icons'
    import { ElementPlusContainer } from '@vitepress-demo-preview/component'

    import '@vitepress-demo-preview/component/dist/style.css'
    import '../../../src/styles/index.css'
    import './custom.css'

    library.add(fas)

    export default {
      ...DefaultTheme,
      enhanceApp({ app }) {
        app.component('demo-preview', ElementPlusContainer)
      }
    }

image.png

四、为生产环境打包且部署

打包

    npm run docs:build

打包生成的文件存放于docs\.vitepress\dist

部署

    npm run docs:preview