├── packages ├── i18n │ ├── README.md │ ├── guide │ │ └── README.md │ ├── .vuepress │ │ ├── config.ts │ │ └── styles │ │ │ └── index.styl │ └── package.json ├── init │ ├── src │ │ ├── index.ts │ │ └── cli.ts │ ├── tsconfig.json │ ├── bin │ │ └── cli.js │ ├── README.md │ ├── tsconfig.build.json │ ├── package.json │ ├── scripts │ │ └── build.js │ └── generator │ │ └── saofile.js ├── docs │ ├── docs │ │ ├── .vuepress │ │ │ ├── public │ │ │ │ ├── CNAME │ │ │ │ ├── full-text-search.png │ │ │ │ └── logo.svg │ │ │ ├── components │ │ │ │ ├── PageLayout1.vue │ │ │ │ ├── Close.vue │ │ │ │ └── GlobalStatus.vue │ │ │ └── styles │ │ │ │ └── index.styl │ │ ├── examples │ │ │ ├── using-page-layout.md │ │ │ └── disable-sidebar.md │ │ ├── api │ │ │ ├── index.md │ │ │ ├── config-frontmatter.md │ │ │ └── config-home.md │ │ ├── guide │ │ │ ├── page-layout.md │ │ │ ├── search.md │ │ │ ├── dark-mode.md │ │ │ ├── migration.md │ │ │ ├── configuration.md │ │ │ ├── api-page.md │ │ │ ├── index.md │ │ │ ├── navbar.md │ │ │ ├── global-components.md │ │ │ ├── status.md │ │ │ └── getting-started.md │ │ └── index.md │ └── package.json ├── vuepress-theme-vt │ ├── src │ │ ├── noopModule.ts │ │ ├── status.ts │ │ └── types.ts │ ├── index.js │ ├── tsconfig.json │ ├── styles │ │ ├── toc.styl │ │ ├── wrapper.styl │ │ ├── config.styl │ │ ├── home.styl │ │ ├── mixins.styl │ │ ├── vp-doc.styl │ │ ├── arrow.styl │ │ ├── mobile.styl │ │ ├── header.styl │ │ └── custom-blocks.styl │ ├── global-components │ │ ├── NextSteps.vue │ │ ├── Summary.vue │ │ ├── Details.vue │ │ ├── CodeBlock.vue │ │ ├── VPIconExternalLink.vue │ │ ├── Step.vue │ │ ├── Badge.vue │ │ └── VPLink.vue │ ├── components │ │ ├── icons │ │ │ ├── VPIconChevronDown.vue │ │ │ ├── VPIconChevronRight.vue │ │ │ ├── VPIconChevronLeft.vue │ │ │ ├── VPIconChevronUp.vue │ │ │ ├── VPIconLastUpdated.vue │ │ │ ├── VTIconMoon.vue │ │ │ ├── VPIconGithub.vue │ │ │ ├── VPIconGitlab.vue │ │ │ ├── VPIconEdit.vue │ │ │ └── VTIconSun.vue │ │ ├── VPNavBarAppearance.vue │ │ ├── Arrow.vue │ │ ├── NavLink.vue │ │ ├── DropdownTransition.vue │ │ ├── Page.vue │ │ ├── SidebarButton.vue │ │ ├── Navbar.vue │ │ ├── NavIcon.vue │ │ ├── VTSwitch.vue │ │ ├── StatusBar.vue │ │ ├── Sticker.vue │ │ ├── Sidebar.vue │ │ ├── VTSwitchAppearance.vue │ │ └── SidebarLinks.vue │ ├── tsconfig.build.json │ ├── plugins │ │ ├── copy-code │ │ │ ├── index.js │ │ │ ├── assets │ │ │ │ ├── copied.svg │ │ │ │ └── copy.svg │ │ │ ├── style.css │ │ │ └── clientRootMixin.js │ │ ├── fulltext-search │ │ │ ├── assets │ │ │ │ └── search.svg │ │ │ ├── components │ │ │ │ └── IconSearch.vue │ │ │ └── services │ │ │ │ └── matchQuery.js │ │ └── code-switcher │ │ │ └── index.js │ ├── layouts │ │ └── 404.vue │ ├── enhanceApp.js │ └── package.json └── vuepress-docs │ ├── docs │ ├── .vuepress │ │ ├── images │ │ │ └── logo.png │ │ ├── public │ │ │ ├── hero.png │ │ │ ├── logo.png │ │ │ ├── plugin.png │ │ │ ├── architecture.png │ │ │ ├── assets │ │ │ │ ├── 1.9-lang.png │ │ │ │ ├── 1.9-overview.png │ │ │ │ ├── 1.9-official-plugin-options.png │ │ │ │ └── 1.9-official-plugin-tuple-usage.png │ │ │ ├── icons │ │ │ │ ├── favicon-16x16.png │ │ │ │ ├── favicon-32x32.png │ │ │ │ ├── mstile-150x150.png │ │ │ │ ├── apple-touch-icon.png │ │ │ │ ├── android-chrome-192x192.png │ │ │ │ ├── android-chrome-512x512.png │ │ │ │ ├── apple-touch-icon-60x60.png │ │ │ │ ├── apple-touch-icon-76x76.png │ │ │ │ ├── apple-touch-icon-120x120.png │ │ │ │ ├── apple-touch-icon-152x152.png │ │ │ │ ├── apple-touch-icon-180x180.png │ │ │ │ └── msapplication-icon-144x144.png │ │ │ ├── line-numbers-desktop.png │ │ │ ├── line-numbers-mobile.gif │ │ │ └── manifest.json │ │ ├── components │ │ │ ├── OtherComponent.vue │ │ │ ├── demo-1.vue │ │ │ ├── Foo │ │ │ │ └── Bar.vue │ │ │ ├── svg-container.vue │ │ │ └── UpgradePath.vue │ │ ├── styles │ │ │ ├── palette.styl │ │ │ └── index.styl │ │ ├── config │ │ │ ├── index.ts │ │ │ ├── sidebar │ │ │ │ ├── zh.ts │ │ │ │ ├── en.ts │ │ │ │ └── shared.ts │ │ │ └── nav │ │ │ │ ├── zh.ts │ │ │ │ └── en.ts │ │ └── enhanceApp.js │ ├── theme │ │ ├── README.md │ │ ├── blog-theme.md │ │ └── using-a-theme.md │ ├── zh │ │ ├── theme │ │ │ ├── README.md │ │ │ ├── blog-theme.md │ │ │ └── using-a-theme.md │ │ ├── plugin │ │ │ ├── writing-a-plugin.md │ │ │ ├── official │ │ │ │ ├── plugin-back-to-top.md │ │ │ │ ├── plugin-nprogress.md │ │ │ │ ├── plugin-blog.md │ │ │ │ ├── plugin-active-header-links.md │ │ │ │ ├── plugin-google-analytics.md │ │ │ │ ├── plugin-medium-zoom.md │ │ │ │ ├── plugin-search.md │ │ │ │ ├── plugin-register-components.md │ │ │ │ └── plugin-last-updated.md │ │ │ ├── context-api.md │ │ │ ├── life-cycle.md │ │ │ ├── README.md │ │ │ └── using-a-plugin.md │ │ ├── README.md │ │ ├── api │ │ │ ├── cli.md │ │ │ └── node.md │ │ ├── guide │ │ │ ├── assets.md │ │ │ ├── global-computed.md │ │ │ ├── basic-config.md │ │ │ ├── permalinks.md │ │ │ ├── getting-started.md │ │ │ ├── markdown-slot.md │ │ │ ├── directory-structure.md │ │ │ └── i18n.md │ │ ├── miscellaneous │ │ │ ├── glossary.md │ │ │ ├── migration-guide.md │ │ │ └── local-development.md │ │ └── faq │ │ │ └── README.md │ ├── plugin │ │ ├── official │ │ │ ├── plugin-back-to-top.md │ │ │ ├── plugin-nprogress.md │ │ │ ├── plugin-active-header-links.md │ │ │ ├── plugin-blog.md │ │ │ ├── plugin-google-analytics.md │ │ │ ├── plugin-medium-zoom.md │ │ │ └── plugin-register-components.md │ │ ├── writing-a-plugin.md │ │ ├── life-cycle.md │ │ ├── context-api.md │ │ ├── README.md │ │ └── using-a-plugin.md │ ├── index.md │ ├── miscellaneous │ │ ├── migration-guide.md │ │ └── glossary.md │ ├── guide │ │ ├── global-computed.md │ │ ├── permalinks.md │ │ └── assets.md │ └── api │ │ ├── cli.md │ │ └── node.md │ ├── README.md │ └── package.json ├── jest.setup.js ├── pnpm-workspace.yaml ├── lerna.json ├── .vscode └── settings.json ├── .npmrc ├── tsconfig.json ├── .github ├── workflows │ ├── create-github-release.yml │ └── deploy-docs.yml └── FUNDING.yml ├── tsconfig.test.json ├── .gitignore ├── jest.config.js ├── media └── logo.svg ├── tsconfig.build.json ├── LICENSE └── package.json /packages/i18n/README.md: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /packages/i18n/guide/README.md: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /jest.setup.js: -------------------------------------------------------------------------------- 1 | jest.setTimeout(100000); 2 | -------------------------------------------------------------------------------- /packages/init/src/index.ts: -------------------------------------------------------------------------------- 1 | export * from './cli' -------------------------------------------------------------------------------- /packages/docs/docs/.vuepress/public/CNAME: -------------------------------------------------------------------------------- 1 | vt.insx.dev -------------------------------------------------------------------------------- /pnpm-workspace.yaml: -------------------------------------------------------------------------------- 1 | packages: 2 | - "packages/*" 3 | -------------------------------------------------------------------------------- /packages/vuepress-theme-vt/src/noopModule.ts: -------------------------------------------------------------------------------- 1 | export default {} 2 | -------------------------------------------------------------------------------- /packages/init/tsconfig.json: -------------------------------------------------------------------------------- 1 | { 2 | "extends": "../../tsconfig.json" 3 | } -------------------------------------------------------------------------------- /packages/vuepress-theme-vt/index.js: -------------------------------------------------------------------------------- 1 | module.exports = require('./lib').default -------------------------------------------------------------------------------- /packages/docs/docs/examples/using-page-layout.md: -------------------------------------------------------------------------------- 1 | --- 2 | pageLayout: PageLayout1 3 | --- -------------------------------------------------------------------------------- /packages/vuepress-theme-vt/tsconfig.json: -------------------------------------------------------------------------------- 1 | { 2 | "extends": "../../tsconfig.json" 3 | } -------------------------------------------------------------------------------- /packages/docs/docs/api/index.md: -------------------------------------------------------------------------------- 1 | --- 2 | groupTitle: API Reference 3 | api: true 4 | --- 5 | -------------------------------------------------------------------------------- /packages/init/bin/cli.js: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env node 2 | 3 | require('../lib').bootstrapCli(); 4 | -------------------------------------------------------------------------------- /lerna.json: -------------------------------------------------------------------------------- 1 | { 2 | "packages": [ 3 | "packages/*" 4 | ], 5 | "version": "0.15.1" 6 | } 7 | -------------------------------------------------------------------------------- /packages/docs/docs/.vuepress/components/PageLayout1.vue: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /packages/vuepress-theme-vt/styles/toc.styl: -------------------------------------------------------------------------------- 1 | .table-of-contents { 2 | .badge { 3 | vertical-align: middle; 4 | } 5 | } 6 | -------------------------------------------------------------------------------- /.vscode/settings.json: -------------------------------------------------------------------------------- 1 | { 2 | "cSpell.words": [ 3 | "collapsable", 4 | "darkmode", 5 | "Frontmatter" 6 | ] 7 | } -------------------------------------------------------------------------------- /packages/init/README.md: -------------------------------------------------------------------------------- 1 | # create-vt 2 | 3 | > Scaffolding a VuePress website with [vuepress-theme-vt](https://github.com/ulivz/vuepress-theme-vt). -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/.vuepress/images/logo.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ulivz/vt/HEAD/packages/vuepress-docs/docs/.vuepress/images/logo.png -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/.vuepress/public/hero.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ulivz/vt/HEAD/packages/vuepress-docs/docs/.vuepress/public/hero.png -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/.vuepress/public/logo.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ulivz/vt/HEAD/packages/vuepress-docs/docs/.vuepress/public/logo.png -------------------------------------------------------------------------------- /packages/docs/docs/.vuepress/public/full-text-search.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ulivz/vt/HEAD/packages/docs/docs/.vuepress/public/full-text-search.png -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/.vuepress/public/plugin.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ulivz/vt/HEAD/packages/vuepress-docs/docs/.vuepress/public/plugin.png -------------------------------------------------------------------------------- /.npmrc: -------------------------------------------------------------------------------- 1 | package-lock=true 2 | package-import-method=auto 3 | strict-peer-dependencies=false 4 | public-hoist-pattern[]=*eslint* 5 | public-hoist-pattern[]=*jest* -------------------------------------------------------------------------------- /packages/vuepress-docs/README.md: -------------------------------------------------------------------------------- 1 | # vuepress-docs 2 | 3 | This package is used to test migrating VuePress' docs to [vuepress-plugin-vt](https://github.com/ulivz/vt). -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/.vuepress/components/OtherComponent.vue: -------------------------------------------------------------------------------- 1 | 6 | -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/.vuepress/public/architecture.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ulivz/vt/HEAD/packages/vuepress-docs/docs/.vuepress/public/architecture.png -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/.vuepress/public/assets/1.9-lang.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ulivz/vt/HEAD/packages/vuepress-docs/docs/.vuepress/public/assets/1.9-lang.png -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/.vuepress/styles/palette.styl: -------------------------------------------------------------------------------- 1 | :root { 2 | --c-brand: #42b883; 3 | --c-brand-light: #42d392; 4 | --c-brand-dark: #33a06f; 5 | } 6 | 7 | -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/.vuepress/config/index.ts: -------------------------------------------------------------------------------- 1 | export * from './nav/en' 2 | export * from './nav/zh' 3 | export * from './sidebar/en' 4 | export * from './sidebar/zh' 5 | 6 | -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/.vuepress/public/assets/1.9-overview.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ulivz/vt/HEAD/packages/vuepress-docs/docs/.vuepress/public/assets/1.9-overview.png -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/.vuepress/public/icons/favicon-16x16.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ulivz/vt/HEAD/packages/vuepress-docs/docs/.vuepress/public/icons/favicon-16x16.png -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/.vuepress/public/icons/favicon-32x32.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ulivz/vt/HEAD/packages/vuepress-docs/docs/.vuepress/public/icons/favicon-32x32.png -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/.vuepress/public/icons/mstile-150x150.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ulivz/vt/HEAD/packages/vuepress-docs/docs/.vuepress/public/icons/mstile-150x150.png -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/.vuepress/public/line-numbers-desktop.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ulivz/vt/HEAD/packages/vuepress-docs/docs/.vuepress/public/line-numbers-desktop.png -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/.vuepress/public/line-numbers-mobile.gif: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ulivz/vt/HEAD/packages/vuepress-docs/docs/.vuepress/public/line-numbers-mobile.gif -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/.vuepress/public/icons/apple-touch-icon.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ulivz/vt/HEAD/packages/vuepress-docs/docs/.vuepress/public/icons/apple-touch-icon.png -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/.vuepress/public/icons/android-chrome-192x192.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ulivz/vt/HEAD/packages/vuepress-docs/docs/.vuepress/public/icons/android-chrome-192x192.png -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/.vuepress/public/icons/android-chrome-512x512.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ulivz/vt/HEAD/packages/vuepress-docs/docs/.vuepress/public/icons/android-chrome-512x512.png -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/.vuepress/public/icons/apple-touch-icon-60x60.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ulivz/vt/HEAD/packages/vuepress-docs/docs/.vuepress/public/icons/apple-touch-icon-60x60.png -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/.vuepress/public/icons/apple-touch-icon-76x76.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ulivz/vt/HEAD/packages/vuepress-docs/docs/.vuepress/public/icons/apple-touch-icon-76x76.png -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/.vuepress/public/icons/apple-touch-icon-120x120.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ulivz/vt/HEAD/packages/vuepress-docs/docs/.vuepress/public/icons/apple-touch-icon-120x120.png -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/.vuepress/public/icons/apple-touch-icon-152x152.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ulivz/vt/HEAD/packages/vuepress-docs/docs/.vuepress/public/icons/apple-touch-icon-152x152.png -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/.vuepress/public/icons/apple-touch-icon-180x180.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ulivz/vt/HEAD/packages/vuepress-docs/docs/.vuepress/public/icons/apple-touch-icon-180x180.png -------------------------------------------------------------------------------- /packages/docs/docs/.vuepress/styles/index.styl: -------------------------------------------------------------------------------- 1 | // :root { 2 | // --c-brand: #42b883; 3 | // --c-brand-light: #42d392; 4 | // --c-brand-dark: #33a06f; 5 | // } 6 | .dark .logo { 7 | filter: invert(1); 8 | } -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/.vuepress/public/icons/msapplication-icon-144x144.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ulivz/vt/HEAD/packages/vuepress-docs/docs/.vuepress/public/icons/msapplication-icon-144x144.png -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/.vuepress/public/assets/1.9-official-plugin-options.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ulivz/vt/HEAD/packages/vuepress-docs/docs/.vuepress/public/assets/1.9-official-plugin-options.png -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/theme/README.md: -------------------------------------------------------------------------------- 1 | # Theme 2 | 3 | ::: tip 4 | Theme components are under the same [browser API access restrictions](../guide/using-vue.md#browser-api-access-restrictions). 5 | ::: 6 | -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/.vuepress/public/assets/1.9-official-plugin-tuple-usage.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ulivz/vt/HEAD/packages/vuepress-docs/docs/.vuepress/public/assets/1.9-official-plugin-tuple-usage.png -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/.vuepress/enhanceApp.js: -------------------------------------------------------------------------------- 1 | export default ({ Vue, isServer }) => { 2 | if (!isServer) { 3 | import('vue-toasted' /* webpackChunkName: "notification" */).then((module) => { 4 | Vue.use(module.default) 5 | }) 6 | } 7 | } 8 | -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/.vuepress/components/demo-1.vue: -------------------------------------------------------------------------------- 1 | 6 | 7 | 16 | -------------------------------------------------------------------------------- /tsconfig.json: -------------------------------------------------------------------------------- 1 | { 2 | "extends": "./tsconfig.build.json", 3 | "compilerOptions": { 4 | "baseUrl": ".", 5 | "paths": { 6 | "vuepress-theme-vt": ["packages/vuepress-theme-vt"] 7 | } 8 | }, 9 | "include": ["packages"], 10 | "exclude": ["packages/*/lib", "lib"] 11 | } 12 | -------------------------------------------------------------------------------- /packages/i18n/.vuepress/config.ts: -------------------------------------------------------------------------------- 1 | import { ThemeConfig } from "vuepress-theme-vuejs"; 2 | import { 3 | defineConfig4CustomTheme, 4 | SidebarConfig4Multiple, 5 | NavItem, 6 | } from "vuepress/config"; 7 | 8 | export = defineConfig4CustomTheme((ctx) => ({ 9 | // .. 10 | })); 11 | -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/.vuepress/components/Foo/Bar.vue: -------------------------------------------------------------------------------- 1 | 6 | 7 | 16 | -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/.vuepress/components/svg-container.vue: -------------------------------------------------------------------------------- 1 | 6 | 7 | 14 | -------------------------------------------------------------------------------- /packages/vuepress-theme-vt/global-components/NextSteps.vue: -------------------------------------------------------------------------------- 1 | 6 | 7 | 15 | -------------------------------------------------------------------------------- /packages/vuepress-theme-vt/styles/wrapper.styl: -------------------------------------------------------------------------------- 1 | $wrapper { 2 | max-width: var(--vp-doc-max-width); 3 | padding: 2rem 2rem 2rem var(--vp-doc-padding); 4 | 5 | @media (max-width: $MQNarrow) { 6 | padding: 2rem; 7 | } 8 | 9 | @media (max-width: $MQMobileNarrow) { 10 | padding: 1.5rem; 11 | } 12 | } 13 | -------------------------------------------------------------------------------- /packages/vuepress-theme-vt/components/icons/VPIconChevronDown.vue: -------------------------------------------------------------------------------- 1 | 6 | -------------------------------------------------------------------------------- /packages/vuepress-theme-vt/components/icons/VPIconChevronRight.vue: -------------------------------------------------------------------------------- 1 | 6 | -------------------------------------------------------------------------------- /packages/vuepress-theme-vt/components/icons/VPIconChevronLeft.vue: -------------------------------------------------------------------------------- 1 | 6 | -------------------------------------------------------------------------------- /packages/vuepress-theme-vt/components/icons/VPIconChevronUp.vue: -------------------------------------------------------------------------------- 1 | 6 | -------------------------------------------------------------------------------- /packages/docs/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "private": true, 3 | "name": "docs", 4 | "version": "0.15.1", 5 | "scripts": { 6 | "dev": "vuepress dev docs --temp .temp", 7 | "build": "vuepress build docs --temp .temp" 8 | }, 9 | "devDependencies": { 10 | "vuepress": "1.9.9", 11 | "vuepress-theme-vt": "0.15.1" 12 | } 13 | } 14 | -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/zh/theme/README.md: -------------------------------------------------------------------------------- 1 | # 主题 2 | 3 | ::: tip 4 | 主题组件受到相同的 [浏览器的 API 访问限制](../guide/using-vue.md#浏览器的API访问限制). 5 | ::: 6 | 7 | 本栏的主要内容如下: 8 | 9 | - [使用主题](./using-a-theme.md) 10 | - [开发主题](./writing-a-theme.md) 11 | - [主题的配置](./option-api.md) 12 | - [主题的继承](./inheritance.md) 13 | - [默认主题配置](./default-theme-config.md) 14 | -------------------------------------------------------------------------------- /.github/workflows/create-github-release.yml: -------------------------------------------------------------------------------- 1 | name: Create Github Release 2 | 3 | on: push 4 | 5 | jobs: 6 | create-github-release: 7 | runs-on: ubuntu-latest 8 | steps: 9 | - name: Checkout 10 | uses: actions/checkout@v2 11 | - name: Release 12 | uses: softprops/action-gh-release@v1 13 | if: startsWith(github.ref, 'refs/tags/') -------------------------------------------------------------------------------- /packages/init/tsconfig.build.json: -------------------------------------------------------------------------------- 1 | { 2 | "extends": "../../tsconfig.build.json", 3 | "compilerOptions": { 4 | "lib": [ 5 | "es5", 6 | "es6" 7 | ], 8 | "skipLibCheck": true, 9 | "module": "commonjs", 10 | "outDir": "./lib", 11 | "typeRoots": [ 12 | "../../node_modules/@types" 13 | ] 14 | }, 15 | "include": [ 16 | "src" 17 | ] 18 | } -------------------------------------------------------------------------------- /packages/vuepress-theme-vt/styles/config.styl: -------------------------------------------------------------------------------- 1 | $contentClass = '.theme-default-content'; 2 | 3 | /** 4 | * CSS Varible cannot be used at media query, so we used stylus varaible here. 5 | */ 6 | $MQWiderDesktop = 1550px; 7 | $MQWideDesktop = 1376px; 8 | $MQDesktop = 1200px; 9 | 10 | /** 11 | * CSS Variables from VuePress Core. 12 | */ 13 | $MQNarrow = 959px 14 | $MQMobile = 719px 15 | $MQMobileNarrow = 419px -------------------------------------------------------------------------------- /packages/vuepress-theme-vt/tsconfig.build.json: -------------------------------------------------------------------------------- 1 | { 2 | "extends": "../../tsconfig.build.json", 3 | "compilerOptions": { 4 | "skipLibCheck": true, 5 | "lib": [ 6 | "es5", 7 | "es6", 8 | "DOM" 9 | ], 10 | "module": "commonjs", 11 | "outDir": "./lib", 12 | "typeRoots": [ 13 | "../../node_modules/@types" 14 | ] 15 | }, 16 | "include": [ 17 | "src" 18 | ] 19 | } -------------------------------------------------------------------------------- /packages/vuepress-theme-vt/plugins/copy-code/index.js: -------------------------------------------------------------------------------- 1 | const { path } = require("@vuepress/shared-utils"); 2 | 3 | /** 4 | * @type {import('@vuepress/types').Plugin} 5 | */ 6 | module.exports = (options, context) => ({ 7 | name: "@vt/copy-code", 8 | define: { 9 | COPY_SELECTOR: options.copy_selector || 'div[class*="language-"]', 10 | }, 11 | clientRootMixin: path.resolve(__dirname, "clientRootMixin.js"), 12 | }); 13 | -------------------------------------------------------------------------------- /packages/vuepress-theme-vt/plugins/fulltext-search/assets/search.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | -------------------------------------------------------------------------------- /tsconfig.test.json: -------------------------------------------------------------------------------- 1 | { 2 | "extends": "./tsconfig.build.json", 3 | "compilerOptions": { 4 | "jsx": "react-jsx", 5 | "allowJs": true, 6 | "noEmit": true, 7 | "noImplicitThis": false, 8 | "noImplicitAny": false, 9 | "moduleResolution": "node", 10 | "baseUrl": ".", 11 | "skipLibCheck": true 12 | }, 13 | "include": [ 14 | "packages/*/__tests__", 15 | ], 16 | "exclude": [ 17 | "node_modules" 18 | ] 19 | } -------------------------------------------------------------------------------- /packages/vuepress-theme-vt/styles/home.styl: -------------------------------------------------------------------------------- 1 | #hero { 2 | p { 3 | margin: 0; 4 | line-height: 1.25; 5 | } 6 | } 7 | 8 | html:not(.dark) { 9 | .heroText .gradient { 10 | font-weight: bolder; 11 | color: var(--c-brand); 12 | background: -webkit-linear-gradient(315deg, #42d392 25%, #647eff); 13 | -webkit-background-clip: text; 14 | -webkit-text-fill-color: transparent; 15 | } 16 | } 17 | -------------------------------------------------------------------------------- /packages/docs/docs/.vuepress/components/Close.vue: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | # See https://help.github.com/articles/ignoring-files/ for more about ignoring files. 2 | 3 | # dependencies 4 | vuepress 5 | node_modules 6 | npm-debug.log* 7 | yarn-error.log 8 | yarn.lock 9 | package-lock.json 10 | 11 | coverage 12 | .nyc_output 13 | .temp 14 | .tmp 15 | dist 16 | lib 17 | 18 | # misc 19 | .DS_Store 20 | .node 21 | *.log 22 | .rpt2_cache 23 | 24 | # generator assets 25 | packages/init/generator/default 26 | packages/init/generator/i18n 27 | -------------------------------------------------------------------------------- /packages/vuepress-theme-vt/plugins/copy-code/assets/copied.svg: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /packages/vuepress-theme-vt/plugins/fulltext-search/components/IconSearch.vue: -------------------------------------------------------------------------------- 1 | 6 | -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/.vuepress/config/sidebar/zh.ts: -------------------------------------------------------------------------------- 1 | import { SidebarConfig4Multiple } from 'vuepress/config' 2 | import { 3 | getApiSidebar, 4 | getGuideSidebar, 5 | getPluginSidebar, 6 | getThemeSidebar 7 | } from './shared' 8 | 9 | export const Sidebar4ZH: SidebarConfig4Multiple = { 10 | '/zh/api/': getApiSidebar(), 11 | '/zh/guide/': getGuideSidebar('指南', '深入'), 12 | '/zh/plugin/': getPluginSidebar('插件', '介绍', '官方插件'), 13 | '/zh/theme/': getThemeSidebar('主题', '介绍') 14 | } 15 | 16 | -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/zh/plugin/writing-a-plugin.md: -------------------------------------------------------------------------------- 1 | # 开发插件 2 | 3 | 一个插件应该导出一个普通的 JavaScript 对象(`#1`),如果插件需要接受配置选项,那么它可以是一个返回对象的函数(`#2`),这个函数接受插件的配置选项为第一个参数、包含编译期上下文的 [ctx](./context-api.md) 对象作为第二个参数。 4 | 5 | ``` js 6 | // #1 7 | module.exports = { 8 | // ... 9 | } 10 | ``` 11 | 12 | ``` js 13 | // #2 14 | module.exports = (options, ctx) => { 15 | return { 16 | // ... 17 | } 18 | } 19 | ``` 20 | 21 | ::: tip 22 | 一个 VuePress 插件应该是一个 `CommonJS 模块`,因为 VuePress 插件运行在 Node 端。 23 | ::: 24 | -------------------------------------------------------------------------------- /packages/vuepress-theme-vt/components/icons/VPIconLastUpdated.vue: -------------------------------------------------------------------------------- 1 | 9 | -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/.vuepress/config/sidebar/en.ts: -------------------------------------------------------------------------------- 1 | import { SidebarConfig4Multiple } from 'vuepress/config' 2 | import { 3 | getApiSidebar, 4 | getGuideSidebar, 5 | getPluginSidebar, 6 | getThemeSidebar 7 | } from './shared' 8 | 9 | export const Sidebar4EN: SidebarConfig4Multiple = { 10 | '/api/': getApiSidebar(), 11 | '/guide/': getGuideSidebar('Guide', 'Advanced'), 12 | '/plugin/': getPluginSidebar('Plugin', 'Introduction', 'Official Plugins'), 13 | '/theme/': getThemeSidebar('Theme', 'Introduction') 14 | } 15 | -------------------------------------------------------------------------------- /packages/vuepress-theme-vt/plugins/copy-code/assets/copy.svg: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /packages/vuepress-theme-vt/styles/mixins.styl: -------------------------------------------------------------------------------- 1 | sidebar-active-bg() { 2 | color: var(--vp-c-brand); 3 | background-color: rgba(100, 100, 100, 0.1); 4 | transition: background-color 0.1s; 5 | border-radius: var(--vp-common-border-radius); 6 | margin-left: -10px; 7 | padding-left: 10px; 8 | } 9 | 10 | navbar-active-bg() { 11 | color: var(--vp-c-brand); 12 | background-color: var(--vp-c-bg-soft); 13 | transition: background-color 0.1s; 14 | border-radius: var(--vp-common-border-radius); 15 | margin: -10px; 16 | padding: 10px; 17 | } -------------------------------------------------------------------------------- /packages/vuepress-theme-vt/styles/vp-doc.styl: -------------------------------------------------------------------------------- 1 | .vp-doc { 2 | ul { 3 | list-style: none; 4 | 5 | li { 6 | position: relative; 7 | 8 | &:before { 9 | content: ''; 10 | position: absolute; 11 | width: 5px; 12 | height: 5px; 13 | border-radius: 50%; 14 | background-color: rgba(60, 60, 60, 0.33); 15 | left: -1.25rem; 16 | top: 0.75rem; 17 | } 18 | } 19 | } 20 | } -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/.vuepress/public/manifest.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "VuePress", 3 | "short_name": "VuePress", 4 | "icons": [ 5 | { 6 | "src": "/icons/android-chrome-192x192.png", 7 | "sizes": "192x192", 8 | "type": "image/png" 9 | }, 10 | { 11 | "src": "/icons/android-chrome-512x512.png", 12 | "sizes": "512x512", 13 | "type": "image/png" 14 | } 15 | ], 16 | "start_url": "/index.html", 17 | "display": "standalone", 18 | "background_color": "#fff", 19 | "theme_color": "#3eaf7c" 20 | } 21 | -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/zh/plugin/official/plugin-back-to-top.md: -------------------------------------------------------------------------------- 1 | --- 2 | title: back-to-top 3 | metaTitle: Back-To-Top 插件 | VuePress 4 | --- 5 | 6 | # [@vuepress/plugin-back-to-top](https://github.com/vuejs/vuepress/tree/master/packages/@vuepress/plugin-back-to-top) 7 | 8 | > back-to-top 插件. 9 | 10 | ## 安装 11 | 12 | ```bash 13 | yarn add -D @vuepress/plugin-back-to-top 14 | # OR npm install -D @vuepress/plugin-back-to-top 15 | ``` 16 | 17 | ## 使用 18 | 19 | ```javascript 20 | module.exports = { 21 | plugins: ['@vuepress/back-to-top'] 22 | } 23 | ``` 24 | -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/plugin/official/plugin-back-to-top.md: -------------------------------------------------------------------------------- 1 | --- 2 | title: back-to-top 3 | metaTitle: Back-To-Top Plugin | VuePress 4 | --- 5 | 6 | # [@vuepress/plugin-back-to-top](https://github.com/vuejs/vuepress/tree/master/packages/%40vuepress/plugin-back-to-top) 7 | 8 | > Back-to-top plugin 9 | 10 | ## Install 11 | 12 | ```bash 13 | yarn add -D @vuepress/plugin-back-to-top 14 | # OR npm install -D @vuepress/plugin-back-to-top 15 | ``` 16 | 17 | ## Usage 18 | 19 | ```javascript 20 | module.exports = { 21 | plugins: ['@vuepress/back-to-top'] 22 | } 23 | ``` 24 | -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/zh/theme/blog-theme.md: -------------------------------------------------------------------------------- 1 | # 博客主题 2 | 3 | ## 网站 4 | 5 | - [文档](https://vuepress-theme-blog.billyyyyy3320.com) 6 | - [线上范例](https://example.vuepress-theme-blog.billyyyyy3320.com/) 7 | - [线上范例 - Billyyyyy3320's space](https://billyyyyy3320.com/) 8 | 9 | ## 安装 10 | 11 | ```bash 12 | yarn add @vuepress/theme-blog -D 13 | # OR npm install @vuepress/theme-blog -D 14 | ``` 15 | ## 使用 16 | 17 | ```js 18 | // .vuepress/config.js 19 | module.exports = { 20 | theme: '@vuepress/blog', 21 | themeConfig: { 22 | // 请参考文档来查看所有可用的选项。 23 | } 24 | } 25 | ``` 26 | -------------------------------------------------------------------------------- /packages/vuepress-theme-vt/components/VPNavBarAppearance.vue: -------------------------------------------------------------------------------- 1 | 2 | 7 | 8 | 17 | 18 | 29 | -------------------------------------------------------------------------------- /packages/vuepress-theme-vt/components/icons/VTIconMoon.vue: -------------------------------------------------------------------------------- 1 | 6 | -------------------------------------------------------------------------------- /packages/vuepress-theme-vt/plugins/code-switcher/index.js: -------------------------------------------------------------------------------- 1 | const { resolve } = require("path"); 2 | 3 | /** 4 | * @type {import('@vuepress/types').Plugin} 5 | */ 6 | module.exports = (options, ctx) => ({ 7 | name: "@vt/code-switcher", 8 | plugins: [ 9 | [ 10 | "@vuepress/register-components", 11 | { componentsDir: resolve(__dirname, "./components") }, 12 | ], 13 | ], 14 | clientDynamicModules() { 15 | return { 16 | name: "code-switcher-groups.js", 17 | content: `export default ${JSON.stringify(options.groups)}`, 18 | }; 19 | }, 20 | }); 21 | -------------------------------------------------------------------------------- /packages/init/src/cli.ts: -------------------------------------------------------------------------------- 1 | /** 2 | * Module dependencies 3 | */ 4 | import * as path from "path"; 5 | import { SAO } from "sao"; 6 | import chalk from "chalk"; 7 | 8 | const generator = path.resolve(__dirname, "../generator"); 9 | 10 | export async function bootstrapCli() { 11 | const cwd = process.cwd(); 12 | const dist = process.argv[2]; 13 | const outDir = dist ? path.resolve(cwd, dist) : cwd; 14 | const sao = new SAO({ 15 | outDir, 16 | generator, 17 | update: true, 18 | }); 19 | 20 | sao.logger.tip("output directory", chalk.gray(outDir)); 21 | await sao.run(); 22 | } 23 | -------------------------------------------------------------------------------- /packages/docs/docs/guide/page-layout.md: -------------------------------------------------------------------------------- 1 | # Page Layout 2 | 3 | ## Motivation 4 | 5 | If you want to hidden `sidebar`, `toc` and `pageEdit` at the page section and only remain `
`, you'll need page layout. 6 | 7 | ## Quick Start 8 | 9 | 1. Declare a [Global Vue Component](https://vuepress.vuejs.org/guide/directory-structure.html), e.g. `.vuepress/components/PageLayout1.vue`. 10 | 2. Declare `pageLayout` via [Frontmatter](https://vuepress.vuejs.org/guide/frontmatter.html): 11 | 12 | ```md 13 | --- 14 | pageLayout: PageLayout1 15 | --- 16 | ``` 17 | 18 | An example [here](../examples/using-page-layout.md). 19 | -------------------------------------------------------------------------------- /packages/docs/docs/guide/search.md: -------------------------------------------------------------------------------- 1 | # Search 2 | 3 | This theme ships full-text search by default, thi is one of the core reasons for the birth of this theme. For now uou just need to move the mouse to the search box to type some keywords: 4 | 5 | ![](2022-01-15-00-33-02.png) 6 | 7 |

8 | 9 |

10 | 11 | Note that there are **no server-side dependencies** here, it just works out of the box, thanks for the great work of [@leo-buneev](https://github.com/leo-buneev) at [vuepress-plugin-fulltext-search](https://github.com/leo-buneev/vuepress-plugin-fulltext-search). 12 | -------------------------------------------------------------------------------- /jest.config.js: -------------------------------------------------------------------------------- 1 | module.exports = { 2 | globals: { 3 | "ts-jest": { 4 | diagnostics: false, 5 | tsconfig: "tsconfig.test.json", 6 | }, 7 | }, 8 | testEnvironment: "node", 9 | setupFilesAfterEnv: [`${__dirname}/jest.setup.js`], 10 | testMatch: ["**/(*.)+(spec|test).ts?(x)"], 11 | transform: { 12 | "^.+\\.(t|j)sx?$": "ts-jest", 13 | }, 14 | snapshotSerializers: ["jest-serializer-path"], 15 | coveragePathIgnorePatterns: ["/__tests__/", "/__fixtures__/", "/bin/"], 16 | collectCoverageFrom: ["packages/**/src/**/*.{ts,tsx}"], 17 | moduleFileExtensions: ["ts", "tsx", "js", "jsx", "json", "node"], 18 | }; 19 | -------------------------------------------------------------------------------- /packages/docs/docs/guide/dark-mode.md: -------------------------------------------------------------------------------- 1 | # Dark Mode 2 | 3 | ## Quick Start 4 | 5 | ```js 6 | // .vuepress/config.js 7 | module.exports = { 8 | theme: "vt", 9 | themeConfig: { 10 | enableDarkMode: true, 11 | }, 12 | }; 13 | ``` 14 | 15 | ## Styling Guide 16 | 17 | To ensure that your site display correctly at dark mode, you need use following CSS Variables for your custom components: 18 | 19 | | Type | CSS Variable | 20 | | ------ | --------------------------- | 21 | | Background Color | `var(--vp-c-bg)` | 22 | | Text | `var(--vp-c-text-1)` | 23 | | Border | `var(--vp-c-divider-light)` | 24 | -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/zh/README.md: -------------------------------------------------------------------------------- 1 | --- 2 | home: true 3 | actionText: 快速上手 → 4 | actionLink: /zh/guide/getting-started.html 5 | subActionText: 介绍 6 | subActionLink: /zh/guide/ 7 | features: 8 | - title: 简洁至上 9 | details: 以 Markdown 为中心的项目结构,以最少的配置帮助你专注于写作。 10 | - title: Vue 驱动 11 | details: 享受 Vue + webpack 的开发体验,可以在 Markdown 中使用 Vue 组件,又可以使用 Vue 来开发自定义主题。 12 | - title: 高性能 13 | details: VuePress 会为每个页面预渲染生成静态的 HTML,同时,每个页面被加载的时候,将作为 SPA 运行。 14 | footer: MIT Licensed | Copyright © 2018-present Evan You 15 | --- 16 | 17 | ::: slot heroText 18 | Minimalistic Vue-powered
static site generator 19 | ::: -------------------------------------------------------------------------------- /packages/i18n/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "private": true, 3 | "name": "i18n", 4 | "version": "0.15.1", 5 | "description": "A VuePress implementation for VitePress theme @vue/theme, fully compatible with VuePress default theme.", 6 | "keywords": [ 7 | "documentation", 8 | "generator", 9 | "vue", 10 | "vuepress" 11 | ], 12 | "license": "MIT", 13 | "main": "index.js", 14 | "types": "lib/index.d.ts", 15 | "devDependencies": { 16 | "@vuepress/plugin-back-to-top": "1.9.9", 17 | "@vuepress/plugin-medium-zoom": "1.9.9", 18 | "less": "4.1.2", 19 | "vuepress": "1.9.9" 20 | }, 21 | "author": "ULIVZ " 22 | } 23 | -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/.vuepress/styles/index.styl: -------------------------------------------------------------------------------- 1 | // placeholder for test, dont't remove it. 2 | 3 | //.content { 4 | // font-size 30px; 5 | //} 6 | 7 | pre.vue-container 8 | background-color: var(--vp-c-bg-soft); 9 | border-left-width: .5rem; 10 | border-left-style: solid; 11 | border-color: #42b983; 12 | border-radius: 0px; 13 | & > code 14 | font-size: 14px !important; 15 | & > p 16 | margin: -5px 0 -20px 0; 17 | code 18 | background-color: var(--c-brand) !important; 19 | padding: 3px 5px; 20 | border-radius: 3px; 21 | color #ffffff 22 | em 23 | color #808080 24 | font-weight light 25 | 26 | -------------------------------------------------------------------------------- /packages/docs/docs/.vuepress/components/GlobalStatus.vue: -------------------------------------------------------------------------------- 1 | 7 | 8 | 17 | 18 | 33 | -------------------------------------------------------------------------------- /packages/vuepress-theme-vt/components/Arrow.vue: -------------------------------------------------------------------------------- 1 | 17 | 18 | -------------------------------------------------------------------------------- /packages/vuepress-theme-vt/layouts/404.vue: -------------------------------------------------------------------------------- 1 | 14 | 15 | 31 | -------------------------------------------------------------------------------- /packages/vuepress-theme-vt/components/NavLink.vue: -------------------------------------------------------------------------------- 1 | 11 | 12 | 37 | -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/theme/blog-theme.md: -------------------------------------------------------------------------------- 1 | # Blog theme 2 | 3 | ## Sites 4 | 5 | - [Documentation](https://vuepress-theme-blog.billyyyyy3320.com) 6 | - [Live Example](https://example.vuepress-theme-blog.billyyyyy3320.com/) 7 | - [Live Example - ULIVZ’s space](https://billyyyyy3320.com/) 8 | - [Live Example - Billyyyyy3320’s space](https://billyyyyy3320.com/) 9 | 10 | ## Install 11 | 12 | ```bash 13 | yarn add @vuepress/theme-blog -D 14 | # OR npm install @vuepress/theme-blog -D 15 | ``` 16 | ## Usage 17 | 18 | ```js 19 | // .vuepress/config.js 20 | module.exports = { 21 | theme: '@vuepress/blog', 22 | themeConfig: { 23 | // Please read documentation to see the available options. 24 | } 25 | } 26 | ``` 27 | -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/plugin/writing-a-plugin.md: -------------------------------------------------------------------------------- 1 | # Writing a Plugin 2 | 3 | A plugin should export a `plain JavaScript object`(`#1`). If the plugin needs to take options, it can be a function that returns a plain object(`#2`). The function will be called with the plugin’s options as the first argument, along with [ctx](./context-api.md) which provides some compile-time metadata. 4 | 5 | ``` js 6 | // #1 7 | module.exports = { 8 | // ... 9 | } 10 | ``` 11 | 12 | ``` js 13 | // #2 14 | module.exports = (options, ctx) => { 15 | return { 16 | // ... 17 | } 18 | } 19 | ``` 20 | 21 | ::: tip 22 | A VuePress plugin module should be a `CommonJS Module` because VuePress plugins runs on the Node.js side. 23 | ::: 24 | -------------------------------------------------------------------------------- /packages/vuepress-theme-vt/enhanceApp.js: -------------------------------------------------------------------------------- 1 | import { $status, STATUS_HIDDEN_EVENT } from "./lib/status"; 2 | 3 | export default ({ 4 | Vue, // the version of Vue being used in the VuePress app 5 | options, // the options for the root Vue instance 6 | router, // the router instance for the app 7 | siteData, // site metadata 8 | }) => { 9 | Vue.mixin({ 10 | methods: { 11 | $closeCurrentStatus() { 12 | $status.closeCurrentStatus(); 13 | this.$root.$emit(STATUS_HIDDEN_EVENT); 14 | }, 15 | $withLocale: function (path) { 16 | if (path.startsWith("/")) { 17 | return this.$localePath + path.replace(/^\//, ""); 18 | } 19 | return path; 20 | }, 21 | }, 22 | }); 23 | }; 24 | -------------------------------------------------------------------------------- /.github/FUNDING.yml: -------------------------------------------------------------------------------- 1 | # These are supported funding model platforms 2 | 3 | github: ulivz # Replace with up to 4 GitHub Sponsors-enabled usernames e.g., [user1, user2] 4 | patreon: ulivz # Replace with a single Patreon username 5 | open_collective: vuepress # Replace with a single Open Collective username 6 | ko_fi: # Replace with a single Ko-fi username 7 | tidelift: # Replace with a single Tidelift platform-name/package-name e.g., npm/babel 8 | community_bridge: # Replace with a single Community Bridge project-name e.g., cloud-foundry 9 | liberapay: # Replace with a single Liberapay username 10 | issuehunt: # Replace with a single IssueHunt username 11 | otechie: # Replace with a single Otechie username 12 | custom: # Replace with a single custom sponsorship URL -------------------------------------------------------------------------------- /packages/vuepress-theme-vt/plugins/copy-code/style.css: -------------------------------------------------------------------------------- 1 | .code-copy { 2 | color: #aaa; 3 | display: inline-block; 4 | cursor: pointer; 5 | } 6 | 7 | div[class*="language-"] .code-copy { 8 | position: absolute; 9 | z-index: 1000; 10 | bottom: 10px; 11 | right: 10px; 12 | width: 18px; 13 | height: 18px; 14 | content: url("./assets/copy.svg"); 15 | opacity: 0; 16 | transition: all 0.3s; 17 | } 18 | 19 | div[class*="language-"] .code-copy.copied { 20 | content: url("./assets/copied.svg"); 21 | } 22 | 23 | div[class*="language-"]:hover .code-copy { 24 | opacity: 0.5; 25 | } 26 | 27 | .content pre, 28 | .content pre[class*="language-"] { 29 | overflow-y: hidden; 30 | } 31 | 32 | .dark .code-copy { 33 | filter: invert(1); 34 | } 35 | -------------------------------------------------------------------------------- /packages/vuepress-theme-vt/global-components/Summary.vue: -------------------------------------------------------------------------------- 1 | 7 | 8 | -------------------------------------------------------------------------------- /packages/vuepress-theme-vt/components/DropdownTransition.vue: -------------------------------------------------------------------------------- 1 | 11 | 12 | 28 | 29 | 34 | -------------------------------------------------------------------------------- /packages/vuepress-theme-vt/global-components/Details.vue: -------------------------------------------------------------------------------- 1 | 6 | 7 | -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/.vuepress/components/UpgradePath.vue: -------------------------------------------------------------------------------- 1 | 23 | 24 | 36 | -------------------------------------------------------------------------------- /packages/vuepress-theme-vt/components/icons/VPIconGithub.vue: -------------------------------------------------------------------------------- 1 | 2 | 10 | -------------------------------------------------------------------------------- /packages/vuepress-theme-vt/styles/arrow.styl: -------------------------------------------------------------------------------- 1 | @require './config'; 2 | 3 | .arrow { 4 | display: inline-block; 5 | width: 0; 6 | height: 0; 7 | 8 | &.up { 9 | border-left: 4px solid transparent; 10 | border-right: 4px solid transparent; 11 | border-bottom: 6px solid $arrowBgColor; 12 | } 13 | 14 | &.down { 15 | border-left: 4px solid transparent; 16 | border-right: 4px solid transparent; 17 | border-top: 6px solid $arrowBgColor; 18 | } 19 | 20 | &.right { 21 | border-top: 4px solid transparent; 22 | border-bottom: 4px solid transparent; 23 | border-left: 6px solid $arrowBgColor; 24 | } 25 | 26 | &.left { 27 | border-top: 4px solid transparent; 28 | border-bottom: 4px solid transparent; 29 | border-right: 6px solid $arrowBgColor; 30 | } 31 | } 32 | -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/zh/plugin/context-api.md: -------------------------------------------------------------------------------- 1 | # Context API 2 | 3 | VuePress 提供了一个存储了当前页面所有状态的 Context API。 4 | 5 | ::: tip 提示 6 | 每个函数式插件的上下文对象是一个继承于根上下文的隔离上下文对象。 7 | ::: 8 | 9 | ```js 10 | module.exports = (options, ctx) => { 11 | // ... 12 | } 13 | ``` 14 | 15 | ## ctx.isProd 16 | 17 | - 类型: `boolean` 18 | 19 | VuePress 是否运行在生产环境模式下。 20 | 21 | ## ctx.pages 22 | 23 | - 类型: `array` 24 | 25 | 一个包含了页面对象的列表。 26 | 27 | ## ctx.sourceDir 28 | 29 | - 类型: `string` 30 | 31 | 文档的根目录路径。 32 | 33 | ## ctx.tempPath 34 | 35 | - 类型: `string` 36 | 37 | 临时文件所在的根目录路径。 38 | 39 | ## ctx.outDir 40 | 41 | - 类型: `string` 42 | 43 | 输出目录。 44 | 45 | ## ctx.base 46 | 47 | - 类型: `string` 48 | 49 | 参考: [base](../config/README.md#base). 50 | 51 | ## ctx.writeTemp 52 | 53 | - 类型: `Function` 54 | 55 | 一个用于向 tempPath 写入临时文件的方法。 56 | -------------------------------------------------------------------------------- /packages/vuepress-theme-vt/global-components/CodeBlock.vue: -------------------------------------------------------------------------------- 1 | 6 | 7 | 27 | 28 | 39 | -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/zh/plugin/life-cycle.md: -------------------------------------------------------------------------------- 1 | # 生命周期 2 | 3 | ## ready 4 | 5 | - 类型: `AsyncFunction` 6 | - 作用域:`dev|build` 7 | 8 | ```js 9 | module.exports = { 10 | async ready() { 11 | // ... 12 | } 13 | } 14 | ``` 15 | 16 | ::: tip 提示 17 | 18 | `ready` 钩子在应用初始化之后,并在某些特定的函数式 API 执行之前执行。这些函数式 API 包括: 19 | 20 | - [clientDynamicModules](./option-api.md#clientdynamicmodules) 21 | - [enhanceAppFiles](./option-api.md#enhanceappfiles) 22 | 23 | ::: 24 | 25 | ## updated 26 | 27 | - 类型: `Function` 28 | - 作用域:`dev` 29 | 30 | ```js 31 | module.exports = { 32 | updated() { 33 | // ... 34 | } 35 | } 36 | ``` 37 | 38 | ## generated 39 | 40 | - 类型: `AsyncFunction` 41 | - 作用域:`build` 42 | 43 | 在生产环境的构建结束后被调用,生成的页面的路径数组将作为该函数的第一个参数。 44 | 45 | ``` js 46 | module.exports = { 47 | async generated (pagePaths) { 48 | // ... 49 | } 50 | } 51 | ``` 52 | -------------------------------------------------------------------------------- /packages/i18n/.vuepress/styles/index.styl: -------------------------------------------------------------------------------- 1 | // placeholder for test, dont't remove it. 2 | b, strong { 3 | font-weight: bolder; 4 | } 5 | 6 | *, :before, :after { 7 | box-sizing: border-box; 8 | } 9 | 10 | 11 | 12 | .page.homepage .theme-default-content { 13 | max-width: 100%; 14 | } 15 | 16 | body { 17 | font-family: var(--vp-font-family-base); 18 | } 19 | 20 | pre.vue-container { 21 | border-left-width: 0.5rem; 22 | border-left-style: solid; 23 | border-color: #42b983; 24 | border-radius: 0px; 25 | 26 | & > code { 27 | font-size: 14px !important; 28 | 29 | & > p { 30 | margin: -5px 0 -20px 0; 31 | } 32 | } 33 | 34 | code { 35 | background-color: #42b983 !important; 36 | padding: 3px 5px; 37 | border-radius: 3px; 38 | color: #000; 39 | } 40 | 41 | em { 42 | color: #808080; 43 | font-weight: light; 44 | } 45 | } 46 | -------------------------------------------------------------------------------- /packages/vuepress-theme-vt/components/icons/VPIconGitlab.vue: -------------------------------------------------------------------------------- 1 | 2 | 15 | 16 | -------------------------------------------------------------------------------- /packages/vuepress-docs/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "private": true, 3 | "name": "vuepress-docs", 4 | "version": "0.15.1", 5 | "description": "docs of VuePress", 6 | "keywords": [ 7 | "documentation", 8 | "generator", 9 | "vue" 10 | ], 11 | "scripts": { 12 | "build": "vuepress build docs --temp .temp", 13 | "dev": "vuepress dev docs --temp .temp", 14 | "show-help": "vuepress --help", 15 | "view-info": "vuepress view-info docs --temp .temp" 16 | }, 17 | "devDependencies": { 18 | "@vuepress/plugin-back-to-top": "1.9.9", 19 | "@vuepress/plugin-google-analytics": "1.9.9", 20 | "@vuepress/plugin-medium-zoom": "1.9.9", 21 | "@vuepress/plugin-pwa": "1.9.9", 22 | "@vuepress/theme-vue": "1.9.9", 23 | "vue-toasted": "^1.1.25", 24 | "vuepress": "1.9.9", 25 | "vuepress-plugin-flowchart": "^1.4.2", 26 | "vuepress-theme-vt": "0.15.1" 27 | } 28 | } 29 | -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/index.md: -------------------------------------------------------------------------------- 1 | --- 2 | home: true 3 | # heroImage: /hero.png 4 | tagline: VuePress is composed of a minimalistic static site generator, and a default theme. 5 | actionText: Get Started → 6 | actionLink: /guide/getting-started.html 7 | subActionText: Introduction 8 | subActionLink: /guide/ 9 | footer: MIT Licensed | Copyright © 2018-present Evan You 10 | features: 11 | - title: Simplicity First 12 | details: Minimal setup with markdown-centered project structure helps you focus on writing. 13 | - title: Vue-Powered 14 | details: Enjoy the dev experience of Vue + webpack, use Vue components in markdown, and develop custom themes with Vue. 15 | - title: Performant 16 | details: VuePress generates pre-rendered static HTML for each page, and runs as an SPA once a page is loaded. 17 | --- 18 | 19 | ::: slot heroText 20 | Minimalistic Vue-powered
static site generator 21 | ::: -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/zh/plugin/official/plugin-nprogress.md: -------------------------------------------------------------------------------- 1 | --- 2 | title: nprogress 3 | metaTitle: Nprogress 插件 | VuePress 4 | --- 5 | 6 | # [@vuepress/plugin-nprogress](https://github.com/vuejs/vuepress/tree/master/packages/%40vuepress/plugin-nprogress) 7 | 8 | > 一个基于 [nprogress](https://github.com/rstacruz/nprogress) 的进度条插件。 9 | 10 | ## 安装 11 | 12 | ```bash 13 | yarn add -D @vuepress/plugin-nprogress 14 | # 或者 npm install -D @vuepress/plugin-nprogress 15 | ``` 16 | 17 | ## 使用 18 | 19 | ```javascript 20 | module.exports = { 21 | plugins: ['@vuepress/nprogress'] 22 | } 23 | ``` 24 | 25 | ## 自定义颜色 26 | 27 | 在你的 __site__ 或 __theme__ 的 `palette.styl` 文件中设置 `$nprogressColor` 来改变进度条的颜色(默认使用 `$accentColor`)。 28 | 29 | ```stylus 30 | // .vuepress/styles/palette.styl 31 | // 或者 32 | // .vuepress/theme/styles/palette.styl 33 | 34 | $nprogressColor = red 35 | ``` 36 | 37 | __参考:__ 38 | 39 | - [配置 > Styling](../../config/README.md#styling) 40 | -------------------------------------------------------------------------------- /media/logo.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | -------------------------------------------------------------------------------- /packages/docs/docs/.vuepress/public/logo.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/plugin/life-cycle.md: -------------------------------------------------------------------------------- 1 | # Lifecycle 2 | 3 | ## ready 4 | 5 | - Type: `AsyncFunction` 6 | - Scope:`dev|build` 7 | 8 | ```js 9 | module.exports = { 10 | async ready() { 11 | // ... 12 | } 13 | } 14 | ``` 15 | 16 | ::: tip 17 | The `ready` hook is executed after the application is initialized and before some specific functional APIs are executed. These functional APIs include: 18 | 19 | - [clientDynamicModules](./option-api.md#clientdynamicmodules) 20 | - [enhanceAppFiles](./option-api.md#enhanceappfiles) 21 | 22 | ::: 23 | 24 | ## updated 25 | 26 | - Type: `Function` 27 | - Scope:`dev` 28 | 29 | ```js 30 | module.exports = { 31 | updated() { 32 | // ... 33 | } 34 | } 35 | ``` 36 | 37 | ## generated 38 | 39 | - Type: `AsyncFunction` 40 | - Scope:`build` 41 | 42 | Called when a (production) build finishes, with an array of generated page HTML paths. 43 | 44 | ``` js 45 | module.exports = { 46 | async generated (pagePaths) { 47 | // ... 48 | } 49 | } 50 | ``` 51 | -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/zh/plugin/official/plugin-blog.md: -------------------------------------------------------------------------------- 1 | --- 2 | title: blog 3 | metaTitle: 博客插件 | VuePress 4 | --- 5 | 6 | # [@vuepress/plugin-blog](https://github.com/vuepressjs/vuepress-plugin-blog) 7 | 8 | ## 功能 9 | 10 | - [**分类**](https://vuepress-plugin-blog.billyyyyy3320.com/guide/getting-started.html#document-classifier):强大的分类系统让你快速将贴文分类。 11 | - [**分页**](https://vuepress-plugin-blog.billyyyyy3320.com/guide/getting-started.html#pagination): 极其简单的开箱即用的分页功能。 12 | - [**客户端 API**](https://vuepress-plugin-blog.billyyyyy3320.com/client-api/): 透过客户端 API 轻松地写一个博客主题。 13 | 14 | ## 安装 15 | 16 | 在使用这个插件之前,我们强烈建议你先阅读 [Getting Started](https://vuepress-plugin-blog.billyyyyy3320.com/guide/getting-started.html)。 17 | 18 | ```bash 19 | yarn add -D @vuepress/plugin-blog 20 | # OR npm install -D @vuepress/plugin-blog 21 | ``` 22 | 23 | ## 使用 24 | 25 | ```javascript 26 | module.exports = { 27 | plugins: ['@vuepress/blog'] 28 | } 29 | ``` 30 | 31 | 参考 [文档](https://vuepress-theme-blog.billyyyyy3320.com/) 来查看所有可用的选项。 32 | -------------------------------------------------------------------------------- /packages/vuepress-theme-vt/components/icons/VPIconEdit.vue: -------------------------------------------------------------------------------- 1 | 2 | 12 | 13 | -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/zh/api/cli.md: -------------------------------------------------------------------------------- 1 | # 命令行接口 2 | 3 | ## 基本用法 4 | 5 | ```bash 6 | vuepress targetDir [options] 7 | ``` 8 | 9 | ## build 10 | 11 | 在指定的目录生成一个静态站点。 12 | 13 | ### -p, --port `` 14 | 查看 [port](../config/README.md#port)。 15 | 16 | ### -t, --temp `` 17 | 查看 [temp](../config/README.md#temp)。 18 | 19 | ### -c, --cache `[cache]` 20 | ### --no-cache 21 | 查看 [cache](../config/README.md#cache)。 22 | 23 | ### --dest `` 24 | 查看 [dest](../config/README.md#dest)。 25 | 26 | ### --debug 27 | 以调试模式启动开发服务器。 28 | 29 | ### --silent 30 | 以安静模式启动开发服务器。 31 | 32 | ## dev 33 | 34 | 启动一个开发服务器。来自 `vuepress build` 的所有选项都可用。除此以外,还有几个专门针对 dev 的选项: 35 | 36 | ### --host `` 37 | 查看 [host](../config/README.md#host)。 38 | 39 | ### --open 40 | 当服务端准备就绪时自动打开浏览器。 41 | 42 | ### --no-clear-screen 43 | 当 dev server 就绪时不清除屏幕。请注意 dev server 不会在调试模式下清除屏幕。 44 | 45 | ## eject 46 | 47 | 将默认主题复制到 `.vuepress/theme` 目录,以供自定义。 48 | 49 | ## 更多指令 50 | 51 | 你可以使用 [extendCli](../plugin/option-api.md#extendcli) 来创建自定义命令。 52 | -------------------------------------------------------------------------------- /packages/docs/docs/guide/migration.md: -------------------------------------------------------------------------------- 1 | # Migration 2 | 3 | ## Migrate from default theme 4 | 5 | Since VT is fully compatible with [VuePress's Default Theme](https://vuepress.vuejs.org/theme/default-theme-config.html), migrating from default theme to VT is very easy: 6 | 7 | ```diff 8 | // .vuepress/config.js 9 | module.exports = { 10 | + theme: 'vt', 11 | themeConfig: { 12 | } 13 | } 14 | ``` 15 | 16 | We have migrated VuePress's documentation to VT at [#21](https://github.com/ulivz/vt/pull/21) with super minimal code changes, you can preview at [vuepress-docs.vercel.app](https://vuepress-docs.vercel.app/). 17 | 18 | ## Migrate from other themes 19 | 20 | First, you need to make sure you are not overly relying on the theme's features. Second, you can migrate based on [Getting Started > Manual Installation](./getting-started.md#manual-installation), if you encounter any issues or features that need to be added, feel free to submit an [issue](https://github.com/ulivz/vt/issues) or [pull request](https://github.com/ulivz/vt/pulls). 21 | -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/plugin/official/plugin-nprogress.md: -------------------------------------------------------------------------------- 1 | --- 2 | title: nprogress 3 | metaTitle: Nprogress Plugin | VuePress 4 | --- 5 | 6 | # [@vuepress/plugin-nprogress](https://github.com/vuejs/vuepress/tree/master/packages/%40vuepress/plugin-nprogress) 7 | 8 | > A progress bar plugin based on [nprogress](https://github.com/rstacruz/nprogress). 9 | 10 | ## Install 11 | 12 | ```bash 13 | yarn add -D @vuepress/plugin-nprogress 14 | # OR npm install -D @vuepress/plugin-nprogress 15 | ``` 16 | 17 | ## Usage 18 | 19 | ```javascript 20 | module.exports = { 21 | plugins: ['@vuepress/nprogress'] 22 | } 23 | ``` 24 | 25 | ## Custom color 26 | 27 | Set `$nprogressColor` in your __site__ or __theme__ `palette.styl` file to change the color of the progress bar (default is `$accentColor`). 28 | 29 | ```stylus 30 | // .vuepress/styles/palette.styl 31 | // or 32 | // .vuepress/theme/styles/palette.styl 33 | 34 | $nprogressColor = red 35 | ``` 36 | 37 | __Also see:__ 38 | 39 | - [Config Reference > Styling](../../config/README.md#styling) 40 | -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/zh/plugin/official/plugin-active-header-links.md: -------------------------------------------------------------------------------- 1 | --- 2 | title: active-header-links 3 | metaTitle: 页面滚动时自动激活侧边栏链接的插件 | VuePress 4 | --- 5 | 6 | # [@vuepress/plugin-active-header-links](https://github.com/vuejs/vuepress/tree/master/packages/@vuepress/plugin-active-header-links) 7 | 8 | > 页面滚动时自动激活侧边栏链接的插件 9 | 10 | ## 安装 11 | 12 | ```bash 13 | yarn add -D @vuepress/plugin-active-header-links 14 | # OR npm install -D @vuepress/plugin-active-header-links 15 | ``` 16 | 17 | ## 使用 18 | 19 | ```javascript 20 | module.exports = { 21 | plugins: ['@vuepress/active-header-links'] 22 | } 23 | ``` 24 | 25 | ### 配置选项 26 | 27 | ```javascript 28 | module.exports = { 29 | plugins: ['@vuepress/active-header-links', { 30 | sidebarLinkSelector: '.sidebar-link', 31 | headerAnchorSelector: '.header-anchor' 32 | }] 33 | } 34 | ``` 35 | 36 | ## 选项 37 | 38 | ### sidebarLinkSelector 39 | 40 | - 类型: `string` 41 | - 默认值: `.sidebar-link` 42 | 43 | ### headerAnchorSelector 44 | 45 | - 类型: `string` 46 | - 默认值: `.header-anchor` 47 | -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/zh/theme/using-a-theme.md: -------------------------------------------------------------------------------- 1 | # 使用主题 2 | 3 | 使用一个主题和使用一个插件的方式几乎一致。 4 | 5 | ## 使用来自依赖的主题 6 | 7 | 一个主题可以在以 `vuepress-theme-xxx` 的形式发布到 npm,你可以这样使用它: 8 | 9 | ``` js 10 | // .vuepress/config.js 11 | module.exports = { 12 | theme: 'vuepress-theme-xx' 13 | } 14 | ``` 15 | 16 | ## 主题的缩写 17 | 18 | 如果你的主题名以 `vuepress-theme-` 开头,你可以使用缩写来省略这个前缀: 19 | 20 | ``` js 21 | // .vuepress/config.js 22 | module.exports = { 23 | theme: 'xxx' 24 | } 25 | ``` 26 | 27 | 和下面等价: 28 | 29 | ``` js 30 | // .vuepress/config.js 31 | module.exports = { 32 | theme: 'vuepress-theme-xxx' 33 | } 34 | ``` 35 | 36 | 这也适用于 [Scoped Packages](https://docs.npmjs.com/misc/scope): 37 | 38 | ``` js 39 | // .vuepress/config.js 40 | module.exports = { 41 | theme: '@org/vuepress-theme-xxx', // 或者一个官方主题: '@vuepress/theme-xxx' 42 | } 43 | ``` 44 | 45 | 缩写: 46 | 47 | ``` js 48 | // .vuepress/config.js 49 | module.exports = { 50 | theme: '@org/xxx', // 或者一个官方主题: '@vuepress/xxx' 51 | } 52 | ``` 53 | 54 | ::: warning 55 | 以 `@vuepress/theme-` 开头的主题是官方维护的主题。 56 | ::: 57 | -------------------------------------------------------------------------------- /packages/init/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "create-vt", 3 | "version": "0.15.1", 4 | "description": "Scaffolding a VuePress website with vuepress-theme-vt.", 5 | "main": "lib/index.js", 6 | "repository": { 7 | "type": "git", 8 | "url": "https://github.com/ulivz/vuepress-theme-vt" 9 | }, 10 | "bin": "bin/cli.js", 11 | "scripts": { 12 | "dev": "npm run build -- -w", 13 | "build": "tsc -p tsconfig.build.json && node scripts/build.js", 14 | "prepublishOnly": "npm run build" 15 | }, 16 | "dependencies": { 17 | "@nomadland/cp": "0.1.2", 18 | "chalk": "^4.1.0", 19 | "sao": "^2.0.0-beta.1" 20 | }, 21 | "devDependencies": { 22 | "fs-extra": "9.1.0", 23 | "typescript": "4.4.4" 24 | }, 25 | "author": "ULIVZ ", 26 | "files": [ 27 | "bin", 28 | "lib", 29 | "!lib/*.tsbuildinfo", 30 | "!lib/*.map", 31 | "types", 32 | "*.d.ts", 33 | "generator" 34 | ], 35 | "publishConfig": { 36 | "registry": "https://registry.npmjs.org", 37 | "access": "public" 38 | } 39 | } 40 | -------------------------------------------------------------------------------- /packages/vuepress-theme-vt/styles/mobile.styl: -------------------------------------------------------------------------------- 1 | @require './config'; 2 | 3 | $mobileSidebarWidth = $sidebarWidth * 0.82; 4 | 5 | // wide mobile 6 | @media (max-width: $MQMobile) { 7 | .navbar { 8 | border-bottom: 1px solid var(--vp-c-divider-light); 9 | } 10 | 11 | .sidebar { 12 | top: 0; 13 | padding-top: var(--vp-navbar-height); 14 | transform: translateX(-100%); 15 | transition: transform 0.2s ease; 16 | } 17 | 18 | .page { 19 | padding-left: 0; 20 | } 21 | 22 | .theme-container { 23 | &.sidebar-open { 24 | .sidebar { 25 | border-right: 1px solid var(--vp-c-divider-light); 26 | transform: translateX(0); 27 | } 28 | } 29 | 30 | &.no-navbar { 31 | .sidebar { 32 | padding-top: 0; 33 | } 34 | } 35 | } 36 | } 37 | 38 | // narrow mobile 39 | @media (max-width: $MQMobileNarrow) { 40 | h1 { 41 | font-size: 1.9rem; 42 | } 43 | 44 | {$contentClass} { 45 | div[class*='language-'] { 46 | margin: 0.85rem -1.5rem; 47 | border-radius: 0; 48 | } 49 | } 50 | } 51 | -------------------------------------------------------------------------------- /packages/docs/docs/guide/configuration.md: -------------------------------------------------------------------------------- 1 | # Configuration 2 | 3 | ## Using TypeScript 4 | 5 | In [Getting Started](./getting-started.md), you've know you need use this theme as follows: 6 | 7 | ```js 8 | // .vuepress/config.js 9 | module.exports = { 10 | theme: "vt", 11 | themeConfig: {}, 12 | }; 13 | ``` 14 | 15 | From 1.9, VuePress introduced [full TypeScript Support](https://github.com/vuejs/vuepress/releases/tag/v1.9.0) for config file, to have type hints for this theme, you can write the configuration like this: 16 | 17 | ```ts 18 | // .vuepress/config.ts 19 | import { ThemeConfig } from "vuepress-theme-vt"; 20 | import { defineConfig4CustomTheme } from "vuepress/config"; 21 | 22 | export = defineConfig4CustomTheme({ 23 | theme: "vt", 24 | themeConfig: {}, 25 | }); 26 | ``` 27 | 28 | ## Theme Config 29 | 30 | VT's config is fully compatible with [VuePress's Default Theme Config](https://vuepress.vuejs.org/theme/default-theme-config.html), feel free to use VT as default theme. 31 | 32 | In additions, VT introduced the following additional features: 33 | 34 | > TODO 35 | -------------------------------------------------------------------------------- /tsconfig.build.json: -------------------------------------------------------------------------------- 1 | { 2 | "compilerOptions": { 3 | "strict": true, 4 | "strictPropertyInitialization": false, 5 | "strictNullChecks": false, 6 | "strictFunctionTypes": true, 7 | "incremental": true, 8 | "noUncheckedIndexedAccess": true, 9 | "allowSyntheticDefaultImports": true, 10 | "esModuleInterop": true, 11 | "experimentalDecorators": true, 12 | "allowJs": false, 13 | "alwaysStrict": true, 14 | "module": "commonjs", 15 | "moduleResolution": "node", 16 | "noEmitOnError": false, 17 | "noImplicitThis": true, 18 | "noImplicitAny": true, 19 | "outDir": "./lib", 20 | "sourceMap": true, 21 | "target": "ES2019", 22 | "typeRoots": [ 23 | "node_modules/@types", 24 | "types" 25 | ], 26 | "declaration": true, 27 | "declarationMap": true, 28 | "resolveJsonModule": true, 29 | "downlevelIteration": true, 30 | "lib": [ 31 | "es5", 32 | "es6", 33 | "DOM" 34 | ] 35 | }, 36 | "include": [ 37 | "src", 38 | "types", 39 | "*.d.ts" 40 | ], 41 | "exclude": [ 42 | "node_modules" 43 | ] 44 | } -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | The MIT License (MIT) 2 | 3 | Copyright (c) 2018-present, ULIVZ 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in 13 | all copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 21 | THE SOFTWARE. 22 | -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/plugin/context-api.md: -------------------------------------------------------------------------------- 1 | # Context API 2 | 3 | Starting with VuePress 1.x.x, VuePress provides an `AppContext` object that stores all the state of the current app and can be accessed through the plugin API. 4 | 5 | ::: warning Note 6 | Context of each plugin is a isolated context inherited from the same app context. 7 | ::: 8 | 9 | ```js 10 | module.exports = (options, ctx) => { 11 | // ... 12 | } 13 | ``` 14 | 15 | ## ctx.isProd 16 | 17 | - Type: `boolean` 18 | 19 | Whether VuePress run in production environment mode. 20 | 21 | ## ctx.pages 22 | 23 | - Type: `array` 24 | 25 | Contains a list of Page objects 26 | 27 | ## ctx.sourceDir 28 | 29 | - Type: `string` 30 | 31 | Root directory where the documents are located. 32 | 33 | ## ctx.tempPath 34 | 35 | - Type: `string` 36 | 37 | Root directory where the temporary files are located. 38 | 39 | ## ctx.outDir 40 | 41 | - Type: `string` 42 | 43 | Output path. 44 | 45 | ## ctx.base 46 | 47 | - Type: `string` 48 | 49 | See: [base](../config/README.md#base). 50 | 51 | ## ctx.writeTemp 52 | 53 | - Type: `Function` 54 | 55 | A utility for writing temporary files to tempPath. 56 | -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/plugin/official/plugin-active-header-links.md: -------------------------------------------------------------------------------- 1 | --- 2 | title: active-header-links 3 | metaTitle: A plugin of automatically activating sidebar links when page scrolls | VuePress 4 | --- 5 | 6 | # [@vuepress/plugin-active-header-links](https://github.com/vuejs/vuepress/tree/master/packages/%40vuepress/plugin-active-header-links) 7 | 8 | > A plugin of automatically activating sidebar links when page scrolls 9 | 10 | ## Install 11 | 12 | ```bash 13 | yarn add -D @vuepress/plugin-active-header-links 14 | # OR npm install -D @vuepress/plugin-active-header-links 15 | ``` 16 | 17 | ## Usage 18 | 19 | ```javascript 20 | module.exports = { 21 | plugins: ['@vuepress/active-header-links'] 22 | } 23 | ``` 24 | 25 | ### Passing Options 26 | 27 | ```javascript 28 | module.exports = { 29 | plugins: ['@vuepress/active-header-links', { 30 | sidebarLinkSelector: '.sidebar-link', 31 | headerAnchorSelector: '.header-anchor' 32 | }] 33 | } 34 | ``` 35 | 36 | ## Options 37 | 38 | ### sidebarLinkSelector 39 | 40 | - Type: `string` 41 | - Default: `.sidebar-link` 42 | 43 | ### headerAnchorSelector 44 | 45 | - Type: `string` 46 | - Default: `.header-anchor` 47 | -------------------------------------------------------------------------------- /packages/vuepress-theme-vt/components/Page.vue: -------------------------------------------------------------------------------- 1 | 19 | 20 | 37 | 38 | 50 | -------------------------------------------------------------------------------- /packages/vuepress-theme-vt/components/SidebarButton.vue: -------------------------------------------------------------------------------- 1 | 18 | 19 | 43 | -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/zh/plugin/official/plugin-google-analytics.md: -------------------------------------------------------------------------------- 1 | --- 2 | title: google-analytics 3 | metaTitle: Google Analytics 插件 | VuePress 4 | --- 5 | 6 | # [@vuepress/plugin-google-analytics](https://github.com/vuejs/vuepress/tree/master/packages/@vuepress/plugin-google-analytics) 7 | 8 | > Google analytics 插件 9 | 10 | ## 安装 11 | 12 | ```bash 13 | yarn add -D @vuepress/plugin-google-analytics 14 | # OR npm install -D @vuepress/plugin-google-analytics 15 | ``` 16 | 17 | ::: warning 18 | 如果你的项目正在使用 Google analytics 插件,推荐使用 [Yarn](https://yarnpkg.com/en/) 而不是 npm 来安装所有依赖。因为在这种情形下,npm 会生成错误的依赖树。 19 | ::: 20 | 21 | ## 使用 22 | 23 | ```javascript 24 | module.exports = { 25 | plugins: [ 26 | [ 27 | '@vuepress/google-analytics', 28 | { 29 | 'ga': '' // UA-00000000-0 30 | } 31 | ] 32 | ] 33 | } 34 | ``` 35 | 36 | ::: tip 提示 37 | 请留意 [GDPR (2018年欧盟数据保护规则改革)](https://ec.europa.eu/commission/priorities/justice-and-fundamental-rights/data-protection/2018-reform-eu-data-protection-rules_en), 在合适或者需要的情况下,考虑将 Google Analytics 设置为[匿名化的 IP](https://support.google.com/analytics/answer/2763052?hl=zh-Hans)。 38 | ::: 39 | 40 | ## 选项 41 | 42 | ### ga 43 | 44 | - 类型: `string` 45 | - 默认值: `undefined` 46 | 47 | 提供 Google Analytics ID 以启用集成。 48 | -------------------------------------------------------------------------------- /packages/vuepress-theme-vt/components/icons/VTIconSun.vue: -------------------------------------------------------------------------------- 1 | 14 | -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/plugin/official/plugin-blog.md: -------------------------------------------------------------------------------- 1 | --- 2 | title: blog 3 | metaTitle: Blog plugin | VuePress 4 | --- 5 | 6 | # [@vuepress/plugin-blog](https://github.com/vuepressjs/vuepress-plugin-blog) 7 | 8 | ## Features 9 | 10 | - [**Classification**](https://vuepress-plugin-blog.billyyyyy3320.com/guide/getting-started.html#document-classifier): 11 | Powerful classification system lets you quickly classify your posts. 12 | - [**Pagination**](https://vuepress-plugin-blog.billyyyyy3320.com/guide/getting-started.html#pagination): 13 | Pagination runs through the entire plugin, and it has never been so simple. 14 | - [**Client APIs**](https://vuepress-plugin-blog.billyyyyy3320.com/client-api/): Simple client APIs make it easier for you to write a blog theme. 15 | 16 | ## Install 17 | 18 | We strongly recommend that you read the [Getting Started](https://vuepress-plugin-blog.billyyyyy3320.com/guide/getting-started.html) section before using this plugin. 19 | 20 | ```bash 21 | yarn add -D @vuepress/plugin-blog 22 | # OR npm install -D @vuepress/plugin-blog 23 | ``` 24 | 25 | ## Usage 26 | 27 | ```javascript 28 | module.exports = { 29 | plugins: ['@vuepress/blog'] 30 | } 31 | ``` 32 | 33 | Please head [documentation](https://vuepress-theme-blog.billyyyyy3320.com/) to see all available options. 34 | -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/theme/using-a-theme.md: -------------------------------------------------------------------------------- 1 | # Using a theme 2 | 3 | Using a theme is almost the same as using a plugin. 4 | 5 | ## Using a theme from a dependency 6 | 7 | Themes can be published on npm in raw Vue SFC format as `vuepress-theme-xxx`. 8 | 9 | ``` js 10 | // .vuepress/config.js 11 | module.exports = { 12 | theme: 'vuepress-theme-xx' 13 | } 14 | ``` 15 | 16 | ## Theme Shorthand 17 | 18 | If you prefix the theme with `vuepress-theme-`, you can use a shorthand to leave out that prefix: 19 | 20 | ``` js 21 | // .vuepress/config.js 22 | module.exports = { 23 | theme: 'xxx' 24 | } 25 | ``` 26 | 27 | Same with: 28 | 29 | ``` js 30 | // .vuepress/config.js 31 | module.exports = { 32 | theme: 'vuepress-theme-xxx' 33 | } 34 | ``` 35 | 36 | This also works with [Scoped Packages](https://docs.npmjs.com/misc/scope): 37 | 38 | ``` js 39 | // .vuepress/config.js 40 | module.exports = { 41 | theme: '@org/vuepress-theme-xxx', // or an official theme: '@vuepress/theme-xxx' 42 | } 43 | ``` 44 | 45 | Shorthand: 46 | 47 | ``` js 48 | // .vuepress/config.js 49 | module.exports = { 50 | theme: '@org/xxx', // or an official theme: '@vuepress/xxx' 51 | } 52 | ``` 53 | 54 | ::: warning Note 55 | The theme whose name starts with `@vuepress/theme-` is an officially maintained theme. 56 | ::: 57 | -------------------------------------------------------------------------------- /packages/vuepress-theme-vt/plugins/fulltext-search/services/matchQuery.js: -------------------------------------------------------------------------------- 1 | // Original search logic from Vuepress 2 | // Not used 3 | import get from "lodash/get"; 4 | 5 | export default (query, page, additionalStr = null) => { 6 | let domain = get(page, "title", ""); 7 | 8 | if (get(page, "frontmatter.tags")) { 9 | domain += ` ${page.frontmatter.tags.join(" ")}`; 10 | } 11 | 12 | if (additionalStr) { 13 | domain += ` ${additionalStr}`; 14 | } 15 | 16 | return matchTest(query, domain); 17 | }; 18 | 19 | const matchTest = (query, domain) => { 20 | const escapeRegExp = (str) => str.replace(/[-/\\^$*+?.()|[\]{}]/g, "\\$&"); 21 | 22 | const words = query 23 | .split(/\s+/g) 24 | .map((str) => str.trim()) 25 | .filter((str) => !!str); 26 | const hasTrailingSpace = query.endsWith(" "); 27 | const searchRegex = new RegExp( 28 | words 29 | .map((word, index) => { 30 | if (words.length === index + 1 && !hasTrailingSpace) { 31 | // The last word - ok with the word being "startswith"-like 32 | return `(?=.*\\b${escapeRegExp(word)})`; 33 | } 34 | // Not the last word - expect the whole word exactly 35 | return `(?=.*\\b${escapeRegExp(word)}\\b)`; 36 | }) 37 | .join("") + ".+", 38 | "gi" 39 | ); 40 | return searchRegex.test(domain); 41 | }; 42 | -------------------------------------------------------------------------------- /packages/docs/docs/guide/api-page.md: -------------------------------------------------------------------------------- 1 | # API Page 2 | 3 | ## Motivation 4 | 5 | VT helps you generate an API page [like this site's API page](/api/), which is very useful to index APIs. 6 | 7 | ## Quick Start 8 | 9 | ### 1. Create API pages 10 | 11 | Create `api/index.md` and some sub pages: 12 | 13 | ```diff 14 | ├── docs 15 | │   ├── api 16 | +│   │   ├── config-foo.md 17 | +│   │   ├── config-bar.md 18 | +│   │   ├── config-baz.md 19 | +│   │   └── index.md 20 | │   ├── guide 21 | │   │   ├── getting-started.md 22 | │   │   ├── index.md 23 | │   │   └── ... 24 | │   └── index.md 25 | └── package.json 26 | ``` 27 | 28 | ### 2. Config sidebar 29 | 30 | Using [Multiple Sidebars](https://vuepress.vuejs.org/theme/default-theme-config.html#multiple-sidebars) to define a sidebar for API. 31 | 32 | ```ts 33 | // .vuepress/config.js 34 | module.exports = { 35 | theme: "vt", 36 | themeConfig: { 37 | sidebar: { 38 | "/api/": [ 39 | { 40 | title: "Config", 41 | path: "/api/", 42 | collapsable: false, 43 | children: ["/api/config-foo", "/api/config-bar", "/api/config-baz"], 44 | }, 45 | ], 46 | }, 47 | }, 48 | }; 49 | ``` 50 | 51 | ### 3. Enable API page layout 52 | 53 | Declare that `api/index.md` is api index page: 54 | 55 | ```md 56 | --- 57 | api: true 58 | --- 59 | ``` 60 | -------------------------------------------------------------------------------- /packages/vuepress-theme-vt/components/Navbar.vue: -------------------------------------------------------------------------------- 1 | 10 | 11 | 26 | 27 | 60 | -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/plugin/official/plugin-google-analytics.md: -------------------------------------------------------------------------------- 1 | --- 2 | title: google-analytics 3 | metaTitle: Google Analytics Plugin | VuePress 4 | --- 5 | 6 | # [@vuepress/plugin-google-analytics](https://github.com/vuejs/vuepress/tree/master/packages/%40vuepress/plugin-google-analytics) 7 | 8 | 9 | > Google analytics plugin 10 | 11 | ## Install 12 | 13 | ```bash 14 | yarn add -D @vuepress/plugin-google-analytics 15 | # OR npm install -D @vuepress/plugin-google-analytics 16 | ``` 17 | 18 | ::: warning 19 | We currently recommend using [Yarn](https://yarnpkg.com/en/) instead of npm to install all dependencies if you are using Google Analytics Plugin, because npm fails to generate the correct dependency tree in this case. 20 | ::: 21 | 22 | ## Usage 23 | 24 | ```javascript 25 | module.exports = { 26 | plugins: [ 27 | [ 28 | '@vuepress/google-analytics', 29 | { 30 | 'ga': '' // UA-00000000-0 31 | } 32 | ] 33 | ] 34 | } 35 | ``` 36 | 37 | ::: tip 38 | Please be aware of [GDPR (2018 reform of EU data protection rules)](https://ec.europa.eu/commission/priorities/justice-and-fundamental-rights/data-protection/2018-reform-eu-data-protection-rules_en) as IPs are anonymized automatically. 39 | ::: 40 | 41 | ## Options 42 | 43 | ### ga 44 | 45 | - Type: `string` 46 | - Default: `undefined` 47 | 48 | Provide the Google Analytics ID to enable integration. 49 | -------------------------------------------------------------------------------- /packages/vuepress-theme-vt/components/NavIcon.vue: -------------------------------------------------------------------------------- 1 | 18 | 19 | -------------------------------------------------------------------------------- /packages/vuepress-theme-vt/global-components/VPIconExternalLink.vue: -------------------------------------------------------------------------------- 1 | 2 | 44 | 45 | 52 | -------------------------------------------------------------------------------- /packages/init/scripts/build.js: -------------------------------------------------------------------------------- 1 | const fs = require("fs-extra"); 2 | const path = require("path"); 3 | const { cp } = require("@nomadland/cp"); 4 | 5 | async function build() { 6 | const generatorDir = path.join(__dirname, "../generator"); 7 | const actions = [ 8 | { 9 | source: path.join(__dirname, "../../docs"), 10 | target: path.join(generatorDir, "default"), 11 | }, 12 | { 13 | source: path.join(__dirname, "../../i18n"), 14 | target: path.join(generatorDir, "i18n"), 15 | }, 16 | ]; 17 | 18 | for (const action of actions) { 19 | if (fs.existsSync(action.target)) { 20 | await fs.emptyDir(action.target); 21 | } else { 22 | fs.ensureDirSync(action.target); 23 | } 24 | 25 | await cp({ 26 | src: action.source, 27 | dist: action.target, 28 | files: { 29 | "**": true, 30 | node_modules: false, 31 | "docs/.vuepress/dist": false, 32 | "package.json": { 33 | rename: "_package.json", 34 | // set basic interpolation 35 | transform: (content) => { 36 | const pkg = JSON.parse(content); 37 | pkg.name = "{{ name }}"; 38 | pkg.description = "{{ description }}"; 39 | pkg.author = "{{ username }} <{{ email }}>"; 40 | return JSON.stringify(pkg, null, 2); 41 | }, 42 | }, 43 | }, 44 | }); 45 | } 46 | } 47 | 48 | build(); 49 | -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/zh/plugin/official/plugin-medium-zoom.md: -------------------------------------------------------------------------------- 1 | --- 2 | title: medium-zoom 3 | metaTitle: Medium-Zoom 插件 | VuePress 4 | --- 5 | 6 | # [@vuepress/plugin-medium-zoom](https://github.com/vuejs/vuepress/tree/master/packages/@vuepress/plugin-medium-zoom) 7 | 8 | > [medium-zoom](https://github.com/francoischalifour/medium-zoom) 插件 9 | 10 | ## 安装 11 | 12 | ```bash 13 | yarn add -D @vuepress/plugin-medium-zoom 14 | # OR npm install -D @vuepress/plugin-medium-zoom 15 | ``` 16 | 17 | ## 使用 18 | 19 | **简单使用**: 20 | 21 | ```javascript 22 | module.exports = { 23 | plugins: ['@vuepress/medium-zoom'] 24 | } 25 | ``` 26 | 27 | **自定义选项**: 28 | 29 | ```javascript 30 | module.exports = { 31 | plugins: { 32 | '@vuepress/medium-zoom': { 33 | selector: 'img.zoom-custom-imgs', 34 | // medium-zoom options here 35 | // See: https://github.com/francoischalifour/medium-zoom#options 36 | options: { 37 | margin: 16 38 | } 39 | } 40 | } 41 | } 42 | ``` 43 | 44 | ## 选项 45 | 46 | ### selector 47 | 48 | - 类型: `string` 49 | - 默认值: `.theme-default-content :not(a) > img` 50 | 51 | 值得注意的是, `.theme-default-content` 是默认主题添加给 [``](../../guide/using-vue.md#content) 组件的 class name。 52 | 53 | ### options 54 | 55 | - 类型: `object` 56 | - 默认值: `undefined` 57 | 58 | [medium-zoom](https://github.com/francoischalifour/medium-zoom) 的 [选项](https://github.com/francoischalifour/medium-zoom#options)。 59 | -------------------------------------------------------------------------------- /packages/vuepress-theme-vt/global-components/Step.vue: -------------------------------------------------------------------------------- 1 | 9 | 10 | 15 | 16 | -------------------------------------------------------------------------------- /.github/workflows/deploy-docs.yml: -------------------------------------------------------------------------------- 1 | name: Deploy Docs 2 | 3 | on: 4 | pull_request: 5 | push: 6 | branches: 7 | - master 8 | 9 | jobs: 10 | deploy-docs: 11 | runs-on: ubuntu-latest 12 | steps: 13 | - name: Checkout 14 | uses: actions/checkout@v3 15 | 16 | - name: Install Node.js 17 | uses: actions/setup-node@v3 18 | with: 19 | node-version: 18 20 | 21 | - uses: pnpm/action-setup@v2 22 | name: Install pnpm 23 | id: pnpm-install 24 | with: 25 | version: 7 26 | run_install: false 27 | 28 | - name: Get pnpm store directory 29 | id: pnpm-cache 30 | shell: bash 31 | run: | 32 | echo "STORE_PATH=$(pnpm store path)" >> $GITHUB_OUTPUT 33 | 34 | - uses: actions/cache@v3 35 | name: Setup pnpm cache 36 | with: 37 | path: ${{ steps.pnpm-cache.outputs.STORE_PATH }} 38 | key: ${{ runner.os }}-pnpm-store-${{ hashFiles('**/pnpm-lock.yaml') }} 39 | restore-keys: | 40 | ${{ runner.os }}-pnpm-store- 41 | 42 | - name: Install dependencies 43 | run: pnpm install 44 | 45 | - name: Build 46 | run: pnpm run build:docs 47 | 48 | - name: Deploy 49 | uses: peaceiris/actions-gh-pages@v3 50 | if: ${{ github.ref == 'refs/heads/master' }} 51 | with: 52 | github_token: ${{ secrets.GITHUB_TOKEN }} 53 | publish_dir: packages/docs/docs/.vuepress/dist 54 | -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/plugin/official/plugin-medium-zoom.md: -------------------------------------------------------------------------------- 1 | --- 2 | title: medium-zoom 3 | metaTitle: Medium-Zoom Plugin | VuePress 4 | --- 5 | 6 | # [@vuepress/plugin-medium-zoom](https://github.com/vuejs/vuepress/tree/master/packages/%40vuepress/plugin-medium-zoom) 7 | 8 | > [medium-zoom](https://github.com/francoischalifour/medium-zoom) plugin 9 | 10 | ## Install 11 | 12 | ```bash 13 | yarn add -D @vuepress/plugin-medium-zoom 14 | # OR npm install -D @vuepress/plugin-medium-zoom 15 | ``` 16 | 17 | ## Usage 18 | 19 | **Simple**: 20 | 21 | ```javascript 22 | module.exports = { 23 | plugins: ['@vuepress/medium-zoom'] 24 | } 25 | ``` 26 | 27 | **With options**: 28 | 29 | ```javascript 30 | module.exports = { 31 | plugins: { 32 | '@vuepress/medium-zoom': { 33 | selector: 'img.zoom-custom-imgs', 34 | // medium-zoom options here 35 | // See: https://github.com/francoischalifour/medium-zoom#options 36 | options: { 37 | margin: 16 38 | } 39 | } 40 | } 41 | } 42 | ``` 43 | 44 | ## Options 45 | 46 | ### selector 47 | 48 | - Type: `string` 49 | - Default: `.theme-default-content :not(a) > img` 50 | 51 | Note that `.theme-default-content` is the class name of [``](../../guide/using-vue.md#content) component in default theme. 52 | 53 | ### options 54 | 55 | - Type: `object` 56 | - Default: `undefined` 57 | 58 | [Options](https://github.com/francoischalifour/medium-zoom#options) for [medium-zoom](https://github.com/francoischalifour/medium-zoom). 59 | -------------------------------------------------------------------------------- /packages/docs/docs/index.md: -------------------------------------------------------------------------------- 1 | --- 2 | home: true 3 | # heroImage: /logo.svg 4 | actionText: Getting Started 5 | actionLink: /guide/ 6 | subActionText: Install 7 | subActionLink: /guide/getting-started.html 8 | features: 9 | - title: Compatibility 10 | details: API familiar for VuePress old users, migrating from default theme is almost no costing. 11 | - title: Full-text search 12 | details: Full-text search is supported by default, no server dependency, distinguishing locales. 13 | - title: Out of the box 14 | details: Compatible with VuePress' default theme, built-in common documentation features. 15 | - title: TypeScript 16 | details: It's easier to custom your own config with full TypeScript support. 17 | - title: Homepage 18 | details: It's easier to have a homepage like as you can see. 19 | - title: API Page 20 | details: Generate an API page like this site's API page, which is very useful to index APIs. 21 | 22 | sponsors: 23 | - title: n8n.io 24 | img: https://avatars.githubusercontent.com/u/45487711?s=200&v=4 25 | link: https://n8n.io/ 26 | - title: n8n.io (2) 27 | img: https://avatars.githubusercontent.com/u/45487711?s=200&v=4 28 | link: https://n8n.io/ 29 | --- 30 | 31 | ::: slot heroText 32 | A "Post-VuePress Era" Theme 33 | ::: 34 | 35 | ::: slot tagline 36 | An elegant theme fully compatible with VuePress default theme, 37 | ::: 38 | 39 | ::: slot footer 40 | Released under the MIT License.
41 | Copyright © 2022 ULIVZ 42 | ::: 43 | -------------------------------------------------------------------------------- /packages/vuepress-theme-vt/components/VTSwitch.vue: -------------------------------------------------------------------------------- 1 | 10 | 11 | -------------------------------------------------------------------------------- /packages/vuepress-theme-vt/components/StatusBar.vue: -------------------------------------------------------------------------------- 1 | 12 | 13 | 20 | 21 | 77 | -------------------------------------------------------------------------------- /packages/docs/docs/guide/index.md: -------------------------------------------------------------------------------- 1 | --- 2 | groupTitle: Guide 3 | --- 4 | 5 | # Introduction 6 | 7 | ## Motivation 8 | 9 | [Next Vue's documentation](https://staging.vuejs.org/) is very cool, which is built by `@vue/theme` and [VitePress](https://github.com/vuejs/vitepress) —— A next-generation SSG for Vue ecosystem, but currently VitePress is still in early stage and there is no plugin system. 10 | 11 | I made this theme to combine eXperience of `@vue/theme` and [current huge VuePress ecosystem](https://github.com/vuepress/awesome-vuepress/), also introducing some built-in features like **full-text search**, **i18n** etc. 12 | 13 | ## Features 14 | 15 | - [**Compatibility**](./migration.md): fully compatible with [VuePress's Default Theme](https://vuepress.vuejs.org/theme/default-theme-config.html). 16 | - [**Full-text search**](./search.md): No server dependencies, distinguishing locales. 17 | - Enhanced Sidebar: [Nested Sidebar Group](./sidebar.md#nested-sidebar-group)、[Sidebar Nav Links](./sidebar.md#sidebar-nav-links). 18 | - [Dark Mode](./dark-mode.md) 19 | - [TypeScript Support](./configuration.md) 20 | - [Homepage](./home.md) 21 | - [API Page](./api-page.md) 22 | - i18n, Code Copy, TOC, etc. 23 | - ... 24 | 25 | ## Next Step 26 | 27 | 28 | 29 | 30 | 31 | 32 | -------------------------------------------------------------------------------- /package.json: -------------------------------------------------------------------------------- 1 | { 2 | "private": "true", 3 | "name": "vuepress-theme-vuejs", 4 | "scripts": { 5 | "bootstrap": "pnpm install --prefer-offline --registry https://registry.npmjs.org", 6 | "build": "lerna exec --scope vuepress-theme-vt -- NODE_OPTIONS=--openssl-legacy-provider npm run build", 7 | "test": "jest", 8 | "cov": "jest --coverage", 9 | "dev:docs": "lerna exec --scope docs -- NODE_OPTIONS=--openssl-legacy-provider npm run dev", 10 | "build:docs": "npm run build && lerna exec --scope docs -- NODE_OPTIONS=--openssl-legacy-provider npm run build", 11 | "dev:vuepress-docs": "lerna exec --scope vuepress-docs -- NODE_OPTIONS=--openssl-legacy-provider npm run dev", 12 | "build:vuepress-docs": "npm run build && lerna exec --scope vuepress-docs -- NODE_OPTIONS=--openssl-legacy-provider npm run build", 13 | "dev:i18n": "lerna exec --scope i18n -- NODE_OPTIONS=--openssl-legacy-provider npm run dev", 14 | "build:i18n": "lerna exec --scope i18n -- NODE_OPTIONS=--openssl-legacy-provider npm run build", 15 | "dev": "mono d", 16 | "release": "mono r --changelog --ignore-scripts --build", 17 | "release:one:click": "npm run release && npm run bootstrap && git add pnpm-lock.yaml && git commit -m 'chore: lock' && git push" 18 | }, 19 | "engines": { 20 | "node": ">=18" 21 | }, 22 | "devDependencies": { 23 | "@nomadland/mono": "0.3.4", 24 | "@types/jest": "27.0.0", 25 | "@types/node": "16.10.9", 26 | "jest": "27.3.1", 27 | "jest-cli": "27.3.1", 28 | "jest-serializer-path": "0.1.15", 29 | "lerna": "^4.0.0", 30 | "ts-jest": "27.0.7" 31 | } 32 | } -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/zh/guide/assets.md: -------------------------------------------------------------------------------- 1 | # 静态资源 2 | 3 | ## 相对路径 4 | 5 | 所有的 Markdown 文件都会被 webpack 编译成 Vue 组件,因此你可以,并且**应该更倾向于**使用相对路径(Relative URLs)来引用所有的静态资源: 6 | 7 | ``` md 8 | ![An image](./image.png) 9 | ``` 10 | 11 | 同样地,这在 `*.vue` 文件的模板中一样可以工作,图片将会被 `url-loader` 和 `file-loader` 处理,在运行生成静态文件的构建任务时,文件会被复制到正确的位置。 12 | 13 | 除此之外,你也使用 `~` 前缀来明确地指出这是一个 webpack 的模块请求,这将允许你通过 webpack 别名来引用文件或者 npm 的依赖: 14 | 15 | ``` md 16 | ![Image from alias](~@alias/image.png) 17 | ![Image from dependency](~some-dependency/image.png) 18 | ``` 19 | 20 | Webpack 的别名可以通过 `.vuepress/config.js` 中 [configureWebpack](../config/README.md#configurewebpack) 来配置,如: 21 | 22 | ``` js 23 | module.exports = { 24 | configureWebpack: { 25 | resolve: { 26 | alias: { 27 | '@alias': 'path/to/some/dir' 28 | } 29 | } 30 | } 31 | } 32 | ``` 33 | 34 | ## 公共文件 35 | 36 | 有时,你可能需要提供一个静态资源,但是它们并不直接被你的任何一个 markdown 文件或者主题组件引用 —— 举例来说,favicons 和 PWA 的图标,在这种情形下,你可以将它们放在 `.vuepress/public` 中, 它们最终会被复制到生成的静态文件夹中。 37 | 38 | ## 基础路径 39 | 40 | 如果你的网站会被部署到一个**非根路径**,你将需要在 `.vuepress/config.js` 中设置 `base`,举例来说,如果你打算将你的网站部署到 `https://foo.github.io/bar/`,那么 `base` 的值就应该被设置为 `"/bar/"` (应当总是以斜杠开始,并以斜杠结束)。 41 | 42 | 有了基础路径(Base URL),如果你希望引用一张放在 `.vuepress/public` 中的图片,你需要使用这样路径:`/bar/image.png`,然而,一旦某一天你决定去修改 `base`,这样的路径引用将会显得异常脆弱。为了解决这个问题,VuePress 提供了内置的一个 helper `$withBase`(它被注入到了 Vue 的原型上),可以帮助你生成正确的路径: 43 | 44 | ``` vue 45 | foo 46 | ``` 47 | 48 | 值得一提的是,你不仅可以在你的 Vue 组件中使用上述的语法,在 Markdown 文件中亦是如此。 49 | 50 | 最后补充一句,一个 `base` 路径一旦被设置,它将会自动地作为前缀插入到 `.vuepress/config.js` 中所有以 `/` 开始的资源路径中。 51 | -------------------------------------------------------------------------------- /packages/docs/docs/guide/navbar.md: -------------------------------------------------------------------------------- 1 | # Navbar 2 | 3 | ## Motivation 4 | 5 | Same to [VuePress Default Theme](https://vuepress.vuejs.org/theme/default-theme-config.html), The Navbar may contain your page title, [Search Box](https://vuepress.vuejs.org/theme/default-theme-config.html#search-box), [Navbar Links](https://vuepress.vuejs.org/theme/default-theme-config.html#navbar-links), [Languages](https://vuepress.vuejs.org/guide/i18n.html) and [Repository Link](https://vuepress.vuejs.org/theme/default-theme-config.html#git-repository-and-edit-links), they all depend on your configuration. 6 | 7 | VT introduced some extra Navbar features. 8 | 9 | ## Nav Links on the left 10 | 11 | In [VuePress Default Theme](https://vuepress.vuejs.org/theme/default-theme-config.html), you can add links to the navbar via `themeConfig.nav`: 12 | 13 | ```ts 14 | // .vuepress/config.js 15 | module.exports = { 16 | themeConfig: { 17 | nav: [ 18 | { text: "Guide", link: "/guide/" }, 19 | { text: "API", link: "/api/" }, 20 | ], 21 | }, 22 | }; 23 | ``` 24 | 25 | These links display on the right by default, you can change them into the right via additional `position` config: 26 | 27 | ```ts{10} 28 | // .vuepress/config.js 29 | module.exports = { 30 | themeConfig: { 31 | nav: [ 32 | { text: "Guide", link: "/guide/" }, 33 | { text: "API", link: "/api/" }, 34 | { 35 | text: "Nav Links on the left", 36 | link: "/guide/navbar.html#nav-links-on-the-left", 37 | position: "left", 38 | }, 39 | ], 40 | }, 41 | }; 42 | ``` 43 | 44 | The effect is shown on this site. 45 | -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/zh/plugin/official/plugin-search.md: -------------------------------------------------------------------------------- 1 | --- 2 | title: search 3 | metaTitle: Search 插件 | VuePress 4 | --- 5 | 6 | # [@vuepress/plugin-search](https://github.com/vuejs/vuepress/tree/master/packages/@vuepress/plugin-search) 7 | 8 | > 基于 [Headers](../../miscellaneous/glossary.md#headers) 的搜索插件 9 | 10 | ## 安装 11 | 12 | ```bash 13 | yarn add -D @vuepress/plugin-search 14 | # OR npm install -D @vuepress/plugin-search 15 | ``` 16 | 17 | ::: tip 18 | 请注意,此插件已包含在**默认主题**中,你现在看到的搜索便是由本插件提供支持。 19 | ::: 20 | 21 | ## 使用 22 | 23 | 1. 启用此插件: 24 | 25 | ```js 26 | // .vuepress/config.js or themePath/index.js 27 | module.exports = { 28 | plugins: [ 29 | ['@vuepress/search', { 30 | searchMaxSuggestions: 10 31 | }] 32 | ] 33 | } 34 | ``` 35 | 36 | 2. 本插件将自动注入指向搜索组件的 webpack 别名 `@SearchBox`,以便您可以直接在 [layout](../../miscellaneous/glossary.md#layout) 组件中使用它: 37 | 38 | ```vue 39 | 49 | 50 | 57 | ``` 58 | 59 | ## 选项 60 | 61 | ### searchMaxSuggestions 62 | 63 | - 类型: `number` 64 | - 默认值: 5 65 | 66 | 设置搜索的最大结果数。 67 | 68 | ## 技巧 69 | 70 | ### 调整默认颜色 71 | 72 | 由于该搜索组件使用了内置调色板,你可以通过 `styles/palette.styl` 来调整搜索框的默认颜色: 73 | 74 | ```stylus 75 | // 你现在看到的这个搜索栏的颜色: 76 | $accentColor = #3eaf7c 77 | $textColor = #2c3e50 78 | $borderColor = #eaecef 79 | $codeBgColor = #282c34 80 | $arrowBgColor = #ccc 81 | ``` 82 | -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/zh/plugin/official/plugin-register-components.md: -------------------------------------------------------------------------------- 1 | --- 2 | title: register-components 3 | metaTitle: 注册组件的插件 | VuePress 4 | --- 5 | 6 | # [@vuepress/plugin-register-components](https://github.com/vuejs/vuepress/tree/master/packages/%40vuepress/plugin-register-components) 7 | 8 | > 注册组件的插件 9 | 10 | ## 安装 11 | 12 | ```bash 13 | yarn add -D @vuepress/plugin-register-components 14 | # OR npm install -D @vuepress/plugin-register-components 15 | ``` 16 | 17 | ## 使用 18 | 19 | ```javascript 20 | module.exports = { 21 | plugins: ['@vuepress/register-components'] 22 | } 23 | ``` 24 | 25 | ## 选项 26 | 27 | ### componentsDir 28 | 29 | - 类型: `Array | String` 30 | - 默认值: `[]` 31 | 32 | 在这个目录下的所有组件将会被注册为全局组件,组件的命名将遵循在 [.vuepress/components](https://vuepress.vuejs.org/guide/using-vue.html#using-components) 中找到的组件的命名。 33 | 34 | ``` js 35 | module.exports = { 36 | plugins: [ 37 | [ 38 | '@vuepress/register-components', 39 | { 40 | componentsDir: somepath 41 | } 42 | ] 43 | ] 44 | } 45 | ``` 46 | 47 | ### components 48 | 49 | - 类型: `{ name: string, path: string }` 50 | - 默认值: `[]` 51 | 52 | 通过明确的名称和路径来注册组件。 53 | 54 | ``` js 55 | module.exports = { 56 | plugins: [ 57 | [ 58 | '@vuepress/register-components', 59 | { 60 | components: [ 61 | { 62 | name: 'V-Card', 63 | path: 'path/to/card.vue' 64 | } 65 | ] 66 | } 67 | ] 68 | ] 69 | } 70 | ``` 71 | 72 | ### getComponentName 73 | 74 | - 类型: `(file: string) => string` 75 | - 默认值: `file => file.replace(/\/|\\/g, '-')` 76 | 77 | 自定义 `componentsDir` 中注册的组件的名称。 78 | -------------------------------------------------------------------------------- /packages/docs/docs/guide/global-components.md: -------------------------------------------------------------------------------- 1 | # Global Components 2 | 3 | ## `` 4 | 5 | A universal link component with internal and external link support: 6 | 7 | - Input: 8 | 9 | ```vue 10 | 11 | ``` 12 | 13 | - Output: 14 | 15 | 16 | 17 | ## `` 18 | 19 | - Input: 20 | 21 | ```vue 22 | 23 | 24 | 25 | 26 | 27 | ``` 28 | 29 | - Output: 30 | 31 | 32 | 33 | 34 | 35 | 36 | 37 | ## `
` 38 | 39 | - Input: 40 | 41 | ```md 42 |
43 | Create .gitignore. 44 | 45 | ```bash 46 | echo 'node_modules 47 | dist' >> .gitignore 48 | ``` 49 | 50 |
51 | 52 | - Output: 53 | 54 |
55 | Create .gitignore. 56 | 57 | ```bash 58 | echo 'node_modules 59 | dist' >> .gitignore 60 | ``` 61 | 62 |
63 | -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/zh/plugin/README.md: -------------------------------------------------------------------------------- 1 | # 插件 2 | 3 | 插件通常会为 VuePress 添加全局功能。插件的范围没有限制。你可以在 [Awesome VuePress](https://github.com/vuepressjs/awesome-vuepress#plugins) 中找到更多的插件。 4 | 5 | ## 样例 6 | 7 | 以下是几种比较常见的插件: 8 | 9 | 1. 拓展在编译期生成的页面元数据,如:[@vuepress/plugin-last-updated](./official/plugin-last-updated.md); 10 | 2. 在编译前后生成额外的文件,如:[@vuepress/plugin-pwa](./official/plugin-pwa.md); 11 | 3. 注入全局的 UI, 如:[@vuepress/plugin-back-to-top](./official/plugin-back-to-top.md); 12 | 4. 拓展 CLI 的指令,如:[vuepress-plugin-export](https://github.com/ulivz/vuepress-plugin-export)。 13 | 14 | 这里也有一个略微复杂的插件案例 [@vuepress/plugin-blog](https://vuepress-plugin-blog.billyyyyy3320.com),其使用了编译期的元数据来生成了一些动态模块,并在客户端使用 `enhanceAppFiles` 来初始化他们。 15 | 16 | ## 开箱即用 17 | 18 | 为了让项目尽可能地简洁,并非所有官方插件都会随着 VuePress 一同安装。以下是一些随着 VuePress 和默认主题一同安装的插件,**没有出现在下表中的插件需要手动安装**(比如:[@vuepress/plugin-back-to-top](./official/plugin-back-to-top.md))。 19 | 20 | ### VuePress 自带的插件 21 | 22 | - [@vuepress/plugin-last-updated](./official/plugin-last-updated.md) 23 | - [@vuepress/plugin-register-components](./official/plugin-register-components.md) 24 | 25 | ### 默认主题自带的插件 26 | 27 | - [@vuepress/plugin-active-header-links](./official/plugin-active-header-links.md) 28 | - [@vuepress/plugin-nprogress](./official/plugin-nprogress.md) 29 | - [@vuepress/plugin-search](./official/plugin-search.md) 30 | - [vuepress-plugin-container](https://vuepress-community.netlify.app/zh/plugins/container/#vuepress-plugin-container) 31 | - [vuepress-plugin-smooth-scroll](https://vuepress-community.netlify.app/zh/plugins/smooth-scroll/#vuepress-plugin-smooth-scroll) 32 | 33 | ## 架构 34 | 35 | 整个插件系统的架构如下: 36 | 37 | ![Architecture of VuePress](/architecture.png) 38 | -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/zh/guide/global-computed.md: -------------------------------------------------------------------------------- 1 | # 全局计算属性 2 | 3 | 在 VuePress 中,内置了一些核心的[计算属性](https://cn.vuejs.org/v2/guide/computed.html#%E8%AE%A1%E7%AE%97%E5%B1%9E%E6%80%A7),以供[默认主题](../theme/default-theme-config.md) 或自定义主题使用。 4 | 5 | ## $site 6 | 7 | 这是你现在看到的这个网站的 `$site` 的值: 8 | 9 | ``` json 10 | { 11 | "title": "VuePress", 12 | "description": "Vue 驱动的静态网站生成器", 13 | "base": "/", 14 | "pages": [ 15 | { 16 | "lastUpdated": 1524027677000, 17 | "path": "/", 18 | "title": "VuePress", 19 | "frontmatter": {} 20 | }, 21 | ... 22 | ] 23 | } 24 | ``` 25 | 26 | ## $page 27 | 28 | 这是你现在看到的这个页面的 `$page` 的值: 29 | 30 | ``` json 31 | { 32 | "title": "Global Computed", 33 | "frontmatter": { 34 | "sidebar": "auto" 35 | }, 36 | "regularPath": "/zh/miscellaneous/global-computed.html", 37 | "key": "v-bc9a3e3f9692d", 38 | "path": "/zh/miscellaneous/global-computed.html", 39 | "headers": [ 40 | { 41 | "level": 2, 42 | "title": "$site", 43 | "slug": "site" 44 | }, 45 | { 46 | "level": 2, 47 | "title": "$page", 48 | "slug": "page" 49 | }, 50 | ... 51 | ] 52 | } 53 | ``` 54 | 55 | ## $frontmatter 56 | 57 | [$page](#page).frontmatter 的引用。 58 | 59 | ## $lang 60 | 61 | 当前页面的语言,默认值为 `en-US`。 62 | 63 | **参考:** 64 | 65 | - [多语言支持](i18n.md) 66 | 67 | ## $localePath 68 | 69 | 当前页面的 locale 路径前缀,默认值为 `/`,当前页面为 `/zh/`。 70 | 71 | **参考:** 72 | 73 | - [多语言支持](i18n.md) 74 | 75 | ## $title 76 | 77 | 用于当前页面的 `` 标签的值。 78 | 79 | ## $description 80 | 81 | 用于当前页面的 `<meta name="description" content="...">` 的 `content` 值。 82 | 83 | ## $themeConfig 84 | 85 | 即 `siteConfig.themeConfig`。 86 | -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/zh/miscellaneous/glossary.md: -------------------------------------------------------------------------------- 1 | --- 2 | sidebar: auto 3 | --- 4 | 5 | # 术语 6 | 7 | 你可能会在文档中碰到一些陌生的概念,本节列出了文档中常见的术语,方便查阅、学习、插件/主题开发之用。 8 | 9 | ## layout 10 | 11 | - Access: `$page.frontmatter.layout` 12 | 13 | 当前页面所使用的布局组件名。 14 | 15 | ## frontmatter 16 | 17 | - Access: `$page.frontmatter` 18 | 19 | 当前页面的 `markdown` 文件中包裹在 `---` 中的配置,一般用于做一些页面级别的配置,参考 [Front Matter](../guide/frontmatter.md) 一节了解更多。 20 | 21 | ## permalink 22 | 23 | - Access: `$page.frontmatter.permalink` 24 | 25 | 永久链接,参考 [Permalinks](../guide/permalinks.md) 一节了解更多。 26 | 27 | ## regularPath 28 | 29 | - Access: `$page.regularPath` 30 | 31 | 当前页面基于目录结构生成的 URL。 32 | 33 | ## path 34 | 35 | - Access: `$page.path` 36 | 37 | 当前页面的实际 URL。在构建期生成路由时,一个页面的 URL 将优先使用 `permalink`,若不存在则降级到 `regularPath`。 38 | 39 | ## headers 40 | 41 | - Access: `$page.headers` 42 | 43 | 即 `markdown` 中那些以一个或多个 `#` 定义的标题。 44 | 45 | ## siteConfig 46 | 47 | - Access: `$site | Context.siteConfig` 48 | 49 | 即 `.vuepress/config.js`,译为 `站点配置`。 50 | 51 | ## themeConfig 52 | 53 | - Access: `$themeConfig | Context.themeConfig` 54 | 55 | 即 `.vuepress/config.js` 中 `themeConfig` 的值,是用户对当前所使用的主题的配置。 56 | 57 | ## themePath 58 | 59 | - Access: `Context.themeAPI.theme.path` 60 | 61 | 当前使用的主题的所在的绝对路径。 62 | 63 | ## themeEntry 64 | 65 | - Access: `Context.themeAPI.theme.entry` 66 | 67 | 主题的配置文件 `themePath/index.js`。 68 | 69 | ## parentThemePath 70 | 71 | - Access: `Context.themeAPI.parentTheme.path` 72 | 73 | 如果当前使用的主题是一个派生主题,那么 `parentThemePath` 就是指父主题的所在绝对路径。 74 | 75 | ## parentThemeEntry 76 | 77 | - Access: `Context.themeAPI.parentTheme.entry` 78 | 79 | 如果当前使用的主题是一个派生主题,那么 `parentThemePath` 就是指父主题的主题的配置文件 `parentThemePath/index.js`。 80 | 81 | -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/zh/guide/basic-config.md: -------------------------------------------------------------------------------- 1 | # 基本配置 2 | 3 | ## 配置文件 4 | 5 | 如果没有任何配置,这个网站将会是非常局限的,用户也无法在你的网站上自由导航。为了更好地自定义你的网站,让我们首先在你的文档目录下创建一个 `.vuepress` 目录,所有 VuePress 相关的文件都将会被放在这里。你的项目结构可能是这样: 6 | 7 | ``` 8 | . 9 | ├─ docs 10 | │ ├─ README.md 11 | │ └─ .vuepress 12 | │ └─ config.js 13 | └─ package.json 14 | ``` 15 | 16 | 一个 VuePress 网站必要的配置文件是 `.vuepress/config.js`,它应该导出一个 JavaScript 对象: 17 | 18 | ``` js 19 | module.exports = { 20 | title: 'Hello VuePress', 21 | description: 'Just playing around' 22 | } 23 | ``` 24 | 25 | 对于上述的配置,如果你运行起 dev server,你应该能看到一个页面,它包含一个页头,里面包含一个标题和一个搜索框。VuePress 内置了基于 headers 的搜索 —— 它会自动为所有页面的标题、`h2` 和 `h3` 构建起一个简单的搜索索引。 26 | 27 | 参见 [配置](../config/README.md) 来查看所有可配置的选项。 28 | 29 | ::: tip 其他配置格式 30 | 你也可以使用 YAML (`.vuepress/config.yml`) 或是 TOML (`.vuepress/config.toml`) 格式的配置文件。 31 | ::: 32 | 33 | ## 主题配置 34 | 35 | 一个 VuePress 主题应该负责整个网站的布局和交互细节。在 VuePress 中,目前自带了一个默认的主题(正是你现在所看到的),它是为技术文档而设计的。同时,默认主题提供了一些选项,让你可以去自定义导航栏(navbar)、 侧边栏(sidebar)和 首页(homepage) 等,详情请参见 [默认主题](../theme/default-theme-config.md) 。 36 | 37 | 如果你想开发一个自定义主题,可以参考 [自定义主题](../theme/README.md)。 38 | 39 | ## 应用级别的配置 40 | 41 | 由于 VuePress 是一个标准的 Vue 应用,你可以通过创建一个 `.vuepress/enhanceApp.js` 文件来做一些应用级别的配置,当该文件存在的时候,会被导入到应用内部。`enhanceApp.js` 应该 `export default` 一个钩子函数,并接受一个包含了一些应用级别属性的对象作为参数。你可以使用这个钩子来安装一些附加的 Vue 插件、注册全局组件,或者增加额外的路由钩子等: 42 | 43 | ``` js 44 | // 使用异步函数也是可以的 45 | export default ({ 46 | Vue, // VuePress 正在使用的 Vue 构造函数 47 | options, // 附加到根实例的一些选项 48 | router, // 当前应用的路由实例 49 | siteData, // 站点元数据 50 | isServer // 当前应用配置是处于 服务端渲染 或 客户端 51 | }) => { 52 | // ...做一些其他的应用级别的优化 53 | } 54 | ``` 55 | 56 | **相关阅读:** 57 | 58 | - [插件 API 中的 enhanceApp](../plugin/option-api.md#enhanceappfiles) 59 | -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/zh/guide/permalinks.md: -------------------------------------------------------------------------------- 1 | # 永久链接 2 | 3 | ## 背景 4 | 5 | 在 1.x.x 版本之前,VuePress 会检索文档源目录下的所有 markdown 文件并按照文件的层次结构去定义页面链接。 6 | 比如你有以下的文件结构: 7 | 8 | ``` 9 | ├── package.json 10 | └── source 11 | ├── _post 12 | │   └── intro-vuepress.md 13 | ├── index.md 14 | └── tags.md 15 | ``` 16 | 17 | 那么你就会获得以下的可用页面: 18 | 19 | ``` 20 | /source/ 21 | /source/tags.html 22 | /source/_post/intro-vuepress.html 23 | ``` 24 | 25 | 然而对于 blog 来说,我们希望文章的链接更加灵活,而不是局限于目录结构。VuePress 把这个功能称为永久链接 (permalinks) ,并从 `1.0.0` 版本开始支持。 26 | 27 | 如果使用永久链接,那么实际的页面链接会像这样: 28 | 29 | ``` 30 | /source/ 31 | /source/tags/ 32 | /source/2018/4/1/intro-vuepress.html 33 | ``` 34 | 35 | 看起来我们已经看过了 blog 的阴暗面。那么让我们继续看下去。 36 | 37 | ## 永久链接 38 | 39 | 一个永久链接是一个旨在未来很多年里维持不变的 URL,由此产生一个发生链接失效(link rot<sup>[1][1]</sup>)的可能性较小的超链接。VuePress 支持一种灵活的方式去生成固定链接,这种方式允许你使用各种模板变量。 40 | 41 | 默认的永久链接是`/:regular`。 42 | 43 | ### 配置永久链接 44 | 45 | 你可以使用全局配置来向所有页面应用永久链接: 46 | 47 | ```js 48 | // .vuepress/config.js 49 | module.exports = { 50 | permalink: "/:year/:month/:day/:slug" 51 | }; 52 | ``` 53 | 54 | 另外,你也可以只为单独一个页面去设置永久链接。这种方式比全局配置拥有更高的优先级。 55 | 56 | 📝 **hello.md**: 57 | 58 | ```markdown 59 | --- 60 | title: Hello World 61 | permalink: /hello-world 62 | --- 63 | 64 | Hello! 65 | ``` 66 | 67 | ### 模板变量 68 | 69 | | 变量 | 介绍 | 70 | | --- | --- | 71 | | :year | 文章发布的年份 (4数字) | 72 | | :month | 文章发布的月份 (2数字) | 73 | | :i_month | 文章发布的月份 (前面不带0) | 74 | | :day | 文章发布的日份 (2数字) | 75 | | :i_day | 文章发布的日份 (前面不带0) | 76 | | :slug | 蛞蝓化文件路径 (不带扩展名) | 77 | | :regular | VuePress默认的生成永久链接的方式,具体实现看 [这里][2] | 78 | 79 | [1]:https://en.wikipedia.org/wiki/Link_rot 80 | [2]:https://github.com/vuejs/vuepress/blob/master/packages/%40vuepress/shared-utils/src/fileToPath.ts 81 | -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/zh/miscellaneous/migration-guide.md: -------------------------------------------------------------------------------- 1 | --- 2 | sidebar: auto 3 | --- 4 | 5 | # 从 VuePress 0.x 迁移 6 | 7 | ## 站点配置 8 | 9 | ### ga <Badge text="替换"/> 10 | 11 | GA 已经被分离为一个单独的插件 [@vuepress/plugin-google-analytics](../plugin/official/plugin-google-analytics.md)。 12 | 13 | ::: upgrade 14 | 15 | 1. 安装 `@vuepress/plugin-google-analytics`: 16 | 17 | ```bash 18 | yarn add -D @vuepress/plugin-google-analytics@next 19 | # OR npm install -D @vuepress/plugin-google-analytics@next 20 | ``` 21 | 22 | 2. 更新 `vuepress/config.js`: 23 | 24 | ```diff 25 | module.exports = { 26 | - ga: 'UA-12345678-9' 27 | + plugins: [ 28 | + ['@vuepress/google-analytics', { 29 | + ga: 'UA-12345678-9' 30 | + }] 31 | + ] 32 | } 33 | ``` 34 | ::: 35 | 36 | ### markdown.config <Badge text="重命名"/> 37 | 38 | 使用 `extendMarkdown`: 39 | 40 | ::: upgrade 41 | 更新 `vuepress/config.js`: 42 | ```diff 43 | // vuepress/config.js 44 | module.exports = { 45 | - markdown: { 46 | - config(md) { /* ... */ } 47 | - }, 48 | + extendMarkdown(md) { /* ... */ } 49 | } 50 | ``` 51 | ::: 52 | 53 | ### serviceWorker <Badge text="替换"/> 54 | 55 | Service Worker 相关的功能已经被分离为一个单独的插件 [@vuepress/plugin-pwa](../plugin/official/plugin-pwa.md)。 56 | 57 | ::: upgrade 58 | 参考: [@vuepress/plugin-pwa > 从 0.x 迁移](../plugin/official/plugin-pwa.md#从-0-x-迁移) 59 | ::: 60 | 61 | ## 默认主题配置 62 | 63 | ### `.vuepress/override.styl` <Badge text="替换"/> 64 | 65 | 使用 `.vuepress/styles/palette.styl` 代替。 66 | 67 | ::: upgrade 68 | 参考: [Config > palette.styl](../config/README.md#palette-styl) 69 | ::: 70 | 71 | ### `.vuepress/style.styl` <Badge text="替换"/> 72 | 73 | 使用 `.vuepress/styles/index.styl` 代替。 74 | 75 | ::: upgrade 76 | 参考: [Config > index.styl](../config/README.md#index-styl) 77 | ::: 78 | -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/zh/guide/getting-started.md: -------------------------------------------------------------------------------- 1 | # 快速上手 2 | 3 | ::: warning 前提条件 4 | VuePress 需要 [Node.js](https://nodejs.org/en/) >= 8.6 5 | ::: 6 | 7 | 本文会帮助你从头搭建一个简单的 VuePress 文档。如果你想在一个现有项目中使用 VuePress 管理文档,从步骤 3 开始。 8 | 9 | 1. 创建并进入一个新目录 10 | 11 | ``` bash 12 | mkdir vuepress-starter && cd vuepress-starter 13 | ``` 14 | 15 | 2. 使用你喜欢的包管理器进行初始化 16 | 17 | ``` bash 18 | yarn init # npm init 19 | ``` 20 | 21 | 3. 将 VuePress 安装为本地依赖 22 | 23 | 我们已经不再推荐全局安装 VuePress 24 | 25 | ``` bash 26 | yarn add -D vuepress # npm install -D vuepress 27 | ``` 28 | 29 | ::: warning 注意 30 | 如果你的现有项目依赖了 webpack 3.x,我们推荐使用 [Yarn](https://classic.yarnpkg.com/zh-Hans/) 而不是 npm 来安装 VuePress。因为在这种情形下,npm 会生成错误的依赖树。 31 | ::: 32 | 33 | 4. 创建你的第一篇文档 34 | 35 | ``` bash 36 | mkdir docs && echo '# Hello VuePress' > docs/README.md 37 | ``` 38 | 39 | 5. 在 `package.json` 中添加一些 [scripts](https://classic.yarnpkg.com/zh-Hans/docs/package-json#toc-scripts) 40 | 41 | 这一步骤是可选的,但我们推荐你完成它。在下文中,我们会默认这些 scripts 已经被添加。 42 | 43 | ``` json 44 | { 45 | "scripts": { 46 | "docs:dev": "vuepress dev docs", 47 | "docs:build": "vuepress build docs" 48 | } 49 | } 50 | ``` 51 | 52 | 6. 在本地启动服务器 53 | 54 | ``` bash 55 | yarn docs:dev # npm run docs:dev 56 | ``` 57 | 58 | VuePress 会在 [http://localhost:8080](http://localhost:8080) 启动一个热重载的开发服务器。 59 | 60 | 现在,你应该已经有了一个简单可用的 VuePress 文档。接下来,了解一下推荐的 [目录结构](directory-structure.html) 和 VuePress 中的 [基本配置](basic-config.html)。 61 | 62 | 等你了解完上文介绍的基础概念,再去学习一下如何使用 [静态资源](assets.html),[Markdown 拓展](markdown.html) 和 [在 Markdown 中使用 Vue](using-vue.html) 来丰富你的文档内容。 63 | 64 | 当你的文档逐渐成型的时候,不要忘记 VuePress 的 [多语言支持](i18n.html) 并了解一下如何将你的文档 [部署](deploy.html) 到任意静态文件服务器上。 65 | -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/plugin/official/plugin-register-components.md: -------------------------------------------------------------------------------- 1 | --- 2 | title: register-components 3 | metaTitle: Register Components Plugin | VuePress 4 | --- 5 | 6 | # [@vuepress/plugin-register-components](https://github.com/vuejs/vuepress/tree/master/packages/%40vuepress/plugin-register-components) 7 | 8 | > register-components plugin for VuePress 9 | 10 | ## Install 11 | 12 | ```bash 13 | yarn add -D @vuepress/plugin-register-components 14 | # OR npm install -D @vuepress/plugin-register-components 15 | ``` 16 | 17 | ## Usage 18 | 19 | ```javascript 20 | module.exports = { 21 | plugins: ['@vuepress/register-components'] 22 | } 23 | ``` 24 | 25 | ## Options 26 | 27 | ### componentsDir 28 | 29 | - Type: `Array | String` 30 | - Default: `[]` 31 | 32 | All components in this directory will be registered as global components, naming of components will follow the components found in [.vuepress/components](https://vuepress.vuejs.org/guide/using-vue.html#using-components). 33 | 34 | ``` js 35 | module.exports = { 36 | plugins: [ 37 | [ 38 | 'register-components', 39 | { 40 | componentsDir: somepath 41 | } 42 | ] 43 | ] 44 | } 45 | ``` 46 | 47 | ### components 48 | 49 | - Type: `{ name: string, path: string }` 50 | - Default: `[]` 51 | 52 | Register global components by explicit name and path. 53 | 54 | ``` js 55 | module.exports = { 56 | plugins: [ 57 | [ 58 | 'register-components', 59 | { 60 | components: [ 61 | { 62 | name: 'V-Card', 63 | path: 'path/to/card.vue' 64 | } 65 | ] 66 | } 67 | ] 68 | ] 69 | } 70 | ``` 71 | 72 | ### getComponentName 73 | 74 | - Type: `(file: string) => string` 75 | - Default: `file => file.replace(/\/|\\/g, '-')` 76 | 77 | Customize component names for files under `componentsDir`. 78 | -------------------------------------------------------------------------------- /packages/vuepress-theme-vt/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "vuepress-theme-vt", 3 | "version": "0.15.1", 4 | "description": "A \"Post-VuePress Era\" Documentation Theme", 5 | "keywords": [ 6 | "documentation", 7 | "generator", 8 | "vue", 9 | "vuepress" 10 | ], 11 | "license": "MIT", 12 | "main": "index.js", 13 | "types": "lib/index.d.ts", 14 | "scripts": { 15 | "dev": "npm run build -- -w", 16 | "build": "tsc -p tsconfig.build.json", 17 | "prepublishOnly": "npm run build" 18 | }, 19 | "devDependencies": { 20 | "typescript": "4.5.3" 21 | }, 22 | "dependencies": { 23 | "@vuepress/plugin-active-header-links": "1.9.9", 24 | "@vuepress/plugin-nprogress": "1.9.9", 25 | "@vuepress/shared-utils": "1.9.9", 26 | "@vuepress/types": "1.9.9", 27 | "cheap-watch": "1.0.3", 28 | "docsearch.js": "^2.5.2", 29 | "flexsearch": "^0.6.32", 30 | "html-to-text": "^7.0.0", 31 | "inquirer": "7.3.3", 32 | "lodash": "^4.17.15", 33 | "markdown-it-attrs": "^2", 34 | "markdown-it-link-attributes": "2", 35 | "node-google-translate-skidz": "1.1.2", 36 | "prism-themes": "1.9.0", 37 | "stylus": "^0.54.8", 38 | "stylus-loader": "^3.0.2", 39 | "throttle-debounce": "5.0.0", 40 | "vue": "^2", 41 | "vue-router": "^3.4.5", 42 | "vuepress-plugin-container": "^2.0.2", 43 | "vuepress-plugin-smooth-scroll": "^0.0.3" 44 | }, 45 | "files": [ 46 | "index.js", 47 | "enhanceApp.js", 48 | "components", 49 | "global-components", 50 | "layouts", 51 | "plugins", 52 | "styles", 53 | "lib", 54 | "!lib/*.tsbuildinfo", 55 | "!lib/*.map", 56 | "types", 57 | "*.d.ts" 58 | ], 59 | "author": "ULIVZ <chl814@foxmail.com>", 60 | "publishConfig": { 61 | "registry": "https://registry.npmjs.org", 62 | "access": "public" 63 | } 64 | } 65 | -------------------------------------------------------------------------------- /packages/vuepress-theme-vt/src/status.ts: -------------------------------------------------------------------------------- 1 | export const STATUS_HIDDEN_EVENT = "hidden-status"; 2 | export const STATUS_SETTING_KEY = "--status-setting--"; 3 | export const STATUS_CURRENT_VERSION_KEY = "--status-current-version--"; 4 | export const DEFAULT_VERSION = "v1"; 5 | 6 | export type StatusSetting = Record<string /* version */, boolean /* open */>; 7 | const DEFAULT_SETTING: StatusSetting = { 8 | [DEFAULT_VERSION]: true, 9 | }; 10 | 11 | export class Status { 12 | bootstrap() { 13 | const currentVersion = this.getCurrentVersion(); 14 | if (!currentVersion) { 15 | this.setCurrentVersion(DEFAULT_VERSION); 16 | } 17 | } 18 | 19 | getCurrentVersion() { 20 | return localStorage.getItem(STATUS_CURRENT_VERSION_KEY); 21 | } 22 | 23 | setCurrentVersion(version: string) { 24 | return localStorage.setItem(STATUS_CURRENT_VERSION_KEY, version); 25 | } 26 | 27 | getSetting(): StatusSetting { 28 | try { 29 | const res = JSON.parse(localStorage.getItem(STATUS_SETTING_KEY)); 30 | if (res === null) { 31 | return DEFAULT_SETTING; 32 | } 33 | return res; 34 | } catch (e) { 35 | return DEFAULT_SETTING; 36 | } 37 | } 38 | 39 | setSetting(setting: StatusSetting) { 40 | const currentSetting = this.getSetting(); 41 | localStorage.setItem( 42 | STATUS_SETTING_KEY, 43 | JSON.stringify({ 44 | ...currentSetting, 45 | ...setting, 46 | }) 47 | ); 48 | } 49 | 50 | isSettingEnabled() { 51 | const currentVersion = this.getCurrentVersion(); 52 | const setting = this.getSetting(); 53 | return setting[currentVersion] !== false; 54 | } 55 | 56 | closeCurrentStatus() { 57 | const currentVersion = this.getCurrentVersion(); 58 | this.setSetting({ 59 | [currentVersion]: false, 60 | }); 61 | } 62 | } 63 | 64 | export const $status = new Status(); 65 | -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/zh/faq/README.md: -------------------------------------------------------------------------------- 1 | --- 2 | sidebar: auto 3 | --- 4 | 5 | # FAQ 6 | 7 | ## 为什么不能把 `palette.styl` 和 `index.styl` 合并到一个 API? 8 | 9 | `palete.styl` 负责全局颜色设置。在编译期间,主题颜色常量应该首先由预处理器解析,然后应用于全局上下文。 10 | 11 | 但对于 `index.styl`,它的工作是重写应用的默认样式。根据 CSS 的优先级原则,后一种样式具有更高的优先级,因此应该在 CSS 文件的末尾生成。 12 | 13 | 描述 stylus 编译器编译顺序的简单图表如下: 14 | 15 | @flowstart 16 | stage1=>operation: palette.styl 17 | stage2=>operation: 默认 app 样式 18 | stage3=>operation: index.styl 19 | 20 | stage1->stage2->stage3 21 | @flowend 22 | 23 | <br> 24 | 25 | ## `clientDynamicModules` 和 `enhanceAppFiles` 的区别是什么? 26 | 27 | 让我们先来回顾一下,`clientDynamicModules` 和 `enhanceAppFiles` 都可以在编译期间通过动态 JavaScript 代码生成模块。 28 | 29 | 不同之处在于,当应用在客户端初始化时,`enhanceAppFiles` 生成的文件会自动加载和使用;而 `clientDynamicModules` 生成的文件则需要用户自己引入 `@dynamic/xxx`。 30 | 31 | ```js 32 | module.exports = (options, ctx) => ({ 33 | // 被入口文件自动引入 34 | enhanceAppFiles: { 35 | name: 'constans-a', 36 | content: `...` 37 | }, 38 | 39 | // 需要引入 '@dynamic/constans-b' 后使用 40 | clientDynamicModules() { 41 | return { 42 | name: 'constans-b', 43 | content: `...` 44 | } 45 | } 46 | }) 47 | ``` 48 | 49 | ## 什么时候需要使用 `enhanceAppFiles`? 50 | 51 | 1. 当你需要在客户端自动执行一些代码时; 52 | 2. 当你不需要复用这个模块时。 53 | 54 | **比如:** 55 | 56 | - [@vuepress/plugin-register-components](https://github.com/vuejs/vuepress/tree/master/packages/@vuepress/plugin-register-components/index.js#L24):在客户端自动注册组件 57 | - [@vuepress/plugin-google-analytics](https://github.com/vuejs/vuepress/blob/master/packages/@vuepress/plugin-google-analytics/enhanceAppFile.js):自动配置 Google Analytics 58 | 59 | ## 什么时候需要使用 `clientDynamicModules`? 60 | 61 | 1. 当你需要生成一个在特定时间被调用的动态模块时; 62 | 2. 当你需要复用这个模块。 63 | 64 | **比如:** 65 | 66 | - [@vuepress/plugin-blog](https://github.com/vuepressjs/vuepress-plugin-blog/blob/master/src/node/index.ts#L208):使用编译期元数据生成一些博客相关的动态模块并通过 `enhanceAppFiles` 将他们在客户端初始化 67 | 68 | -------------------------------------------------------------------------------- /packages/vuepress-theme-vt/components/Sticker.vue: -------------------------------------------------------------------------------- 1 | <template> 2 | <component 3 | :is="tag || 'div'" 4 | class="sticker" 5 | :class="needFloat ? ['stick-float'] : undefined" 6 | :style="needFloat ? { bottom: `${stickBottom}px` } : undefined" 7 | > 8 | <slot></slot> 9 | </component> 10 | </template> 11 | 12 | <script> 13 | import { findContainerInVm } from "../lib/util"; 14 | export default { 15 | props: ["stick", "tag"], 16 | 17 | data() { 18 | return { 19 | needFloat: false, 20 | stickBottom: 0, 21 | }; 22 | }, 23 | 24 | watch: { 25 | stick() { 26 | this.unStick(); 27 | this.stickHandle(); 28 | }, 29 | }, 30 | 31 | methods: { 32 | stickHandle() { 33 | if (!this.stick) return; 34 | const stickElement = findContainerInVm(this.stick, this); 35 | if (!stickElement) return; 36 | 37 | this._stickerScroll = () => { 38 | const rect = this.$el.getBoundingClientRect(); 39 | const scrollTop = 40 | document.body.scrollTop + document.documentElement.scrollTop; 41 | this.needFloat = 42 | document.body.offsetHeight - scrollTop - rect.height < 43 | stickElement.offsetHeight; 44 | this.stickBottom = stickElement.offsetHeight; 45 | }; 46 | 47 | this._stickerScroll(); 48 | window.addEventListener("scroll", this._stickerScroll); 49 | }, 50 | 51 | unStick() { 52 | this.needFloat = false; 53 | this.stickBottom = 0; 54 | window.removeEventListener("scroll", this._stickerScroll); 55 | }, 56 | }, 57 | 58 | mounted() { 59 | this.stickHandle(); 60 | }, 61 | 62 | beforeDestroy() { 63 | this.unStick(); 64 | }, 65 | }; 66 | </script> 67 | 68 | <style lang="stylus"> 69 | .sticker { 70 | position: fixed; 71 | 72 | &.stick-float { 73 | top: auto; 74 | position: absolute; 75 | } 76 | } 77 | </style> 78 | 79 | -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/miscellaneous/migration-guide.md: -------------------------------------------------------------------------------- 1 | --- 2 | sidebar: auto 3 | --- 4 | 5 | # Migration from 0.x 6 | 7 | ## Site Config 8 | 9 | ### ga <Badge text="replaced"/> 10 | 11 | GA has been separated into a standalone plugin [@vuepress/plugin-google-analytics](../plugin/official/plugin-google-analytics.md). 12 | 13 | ::: upgrade 14 | 15 | 1. Install `@vuepress/plugin-google-analytics`: 16 | 17 | ```bash 18 | yarn add -D @vuepress/plugin-google-analytics@next 19 | # OR npm install -D @vuepress/plugin-google-analytics@next 20 | ``` 21 | 22 | 2. Update `vuepress/config.js`: 23 | 24 | ```diff 25 | module.exports = { 26 | - ga: 'UA-12345678-9' 27 | + plugins: [ 28 | + ['@vuepress/google-analytics', { 29 | + ga: 'UA-12345678-9' 30 | + }] 31 | + ] 32 | } 33 | ``` 34 | ::: 35 | 36 | ### markdown.config <Badge text="renamed"/> 37 | 38 | Using `extendMarkdown`:。 39 | 40 | ::: upgrade 41 | Update `vuepress/config.js`: 42 | ```diff 43 | // vuepress/config.js 44 | module.exports = { 45 | - markdown: { 46 | - config(md) { /* ... */ } 47 | - }, 48 | + extendMarkdown(md) { /* ... */ } 49 | } 50 | ``` 51 | ::: 52 | 53 | ### serviceWorker <Badge text="replaced"/> 54 | 55 | Service Worker related features have been separated into a standalone plugin [@vuepress/plugin-pwa](../plugin/official/plugin-pwa.md). 56 | 57 | ::: upgrade 58 | See: [@vuepress/plugin-pwa > Migration from 0.x](../plugin/official/plugin-pwa.md#migration-from-0-x) 59 | ::: 60 | 61 | ## Default Theme Config 62 | 63 | ### `.vuepress/override.styl` <Badge text="replaced"/> 64 | 65 | Replaced by `.vuepress/styles/palette.styl`. 66 | 67 | ::: upgrade 68 | See: [Config > palette.styl](../config/README.md#palette-styl) 69 | ::: 70 | 71 | ### `.vuepress/style.styl` <Badge text="replaced"/> 72 | 73 | Replaced by `.vuepress/styles/index.styl`. 74 | 75 | ::: upgrade 76 | See: [Config > index.styl](../config/README.md#index-styl) 77 | ::: 78 | -------------------------------------------------------------------------------- /packages/vuepress-theme-vt/plugins/copy-code/clientRootMixin.js: -------------------------------------------------------------------------------- 1 | /* global SELECTOR */ 2 | 3 | import "./style.css"; 4 | 5 | export default { 6 | data: () => ({ zoom: null }), 7 | 8 | mounted() { 9 | this.updateCopy(); 10 | }, 11 | 12 | updated() { 13 | this.updateCopy(); 14 | }, 15 | 16 | methods: { 17 | updateCopy() { 18 | setTimeout(() => { 19 | document 20 | .querySelectorAll(COPY_SELECTOR) 21 | .forEach(this.generateCopyButton); 22 | }, 1000); 23 | }, 24 | generateCopyButton: function (parent) { 25 | if (parent.classList.contains("codecopy-enabled")) return; 26 | const copyElement = document.createElement("span"); 27 | copyElement.className = "code-copy"; 28 | copyElement.title = "Click to Copy to Clipboard"; 29 | copyElement.addEventListener("click", () => { 30 | this.copyToClipboard(parent.innerText); 31 | copyElement.classList.add("copied"); 32 | const timer = setTimeout(() => { 33 | copyElement.classList.remove("copied"); 34 | clearTimeout(timer); 35 | }, 2000); 36 | }); 37 | parent.appendChild(copyElement); 38 | parent.classList.add("codecopy-enabled"); 39 | }, 40 | copyToClipboard: function (str) { 41 | const el = document.createElement("textarea"); 42 | el.value = str; 43 | el.setAttribute("readonly", ""); 44 | el.style.position = "absolute"; 45 | el.style.left = "-9999px"; 46 | document.body.appendChild(el); 47 | const selected = 48 | document.getSelection().rangeCount > 0 49 | ? document.getSelection().getRangeAt(0) 50 | : false; 51 | el.select(); 52 | document.execCommand("copy"); 53 | document.body.removeChild(el); 54 | if (selected) { 55 | document.getSelection().removeAllRanges(); 56 | document.getSelection().addRange(selected); 57 | } 58 | }, 59 | }, 60 | }; 61 | -------------------------------------------------------------------------------- /packages/vuepress-theme-vt/global-components/Badge.vue: -------------------------------------------------------------------------------- 1 | <script> 2 | export default { 3 | functional: true, 4 | props: { 5 | type: { 6 | type: String, 7 | default: "tip", 8 | }, 9 | text: String, 10 | vertical: { 11 | type: String, 12 | default: "top", 13 | }, 14 | }, 15 | render(h, { props, slots }) { 16 | const badgeIcon = 17 | ["warning", "warn", "error"].indexOf(props.type) > -1 ? "⚠" : "ⓘ"; 18 | return h( 19 | "span", 20 | { 21 | class: ["badge", props.type], 22 | style: { 23 | verticalAlign: props.vertical, 24 | }, 25 | }, 26 | [ 27 | h("span", { class: ["badge-icon"] }, badgeIcon), 28 | h("span", { class: ["badge-text"] }, props.text || slots().default), 29 | ] 30 | ); 31 | }, 32 | }; 33 | </script> 34 | 35 | <style lang="stylus" scoped> 36 | .badge { 37 | display: inline-block; 38 | height: 22px; 39 | line-height: 20px; 40 | border-radius: 10px; 41 | padding: 0 5px; 42 | color: var(--vp-c-text-code); 43 | background-color: var(--vp-c-bg-soft); 44 | font-size: 0; 45 | 46 | .badge-icon { 47 | display: inline-block; 48 | margin-right: 5px; 49 | font-size: 16px; 50 | // font-weight: bolder; 51 | } 52 | 53 | .badge-text { 54 | font-size: 16px; 55 | font-weight: 400; 56 | vertical-align: baseline; 57 | } 58 | 59 | &.tip, &.green { 60 | border: 1px solid rgb(178, 186, 194); 61 | } 62 | 63 | &.error { 64 | color: var(--vp-c-red-dark); 65 | border: 1px solid var(--vp-c-red); 66 | } 67 | 68 | &.warning, &.warn, &.yellow { 69 | color: var(--vp-c-yellow-dark); 70 | border: 1px solid var(--vp-c-yellow); 71 | } 72 | 73 | & + & { 74 | margin-left: 5px; 75 | } 76 | } 77 | 78 | .dark { 79 | .badge { 80 | &.tip, &.green { 81 | color: var(--vp-c-brand); 82 | border: 1px solid var(--vp-c-brand); 83 | } 84 | } 85 | } 86 | </style> 87 | -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/.vuepress/config/nav/zh.ts: -------------------------------------------------------------------------------- 1 | import { NavItem } from 'vuepress/config' 2 | 3 | export const NavItems4ZH: NavItem[] = [ 4 | { 5 | text: '指南', 6 | link: '/zh/guide/' 7 | }, 8 | { 9 | text: '配置', 10 | link: '/zh/config/' 11 | }, 12 | { 13 | text: '插件', 14 | link: '/zh/plugin/' 15 | }, 16 | { 17 | text: '主题', 18 | link: '/zh/theme/' 19 | }, 20 | { 21 | text: '了解更多', 22 | ariaLabel: '了解更多', 23 | items: [ 24 | { 25 | text: 'API', 26 | items: [ 27 | { 28 | text: 'CLI', 29 | link: '/zh/api/cli.html' 30 | }, 31 | { 32 | text: 'Node', 33 | link: '/zh/api/node.html' 34 | } 35 | ] 36 | }, 37 | { 38 | text: '开发指南', 39 | items: [ 40 | { 41 | text: '本地开发', 42 | link: '/zh/miscellaneous/local-development.html' 43 | }, 44 | { 45 | text: '设计理念', 46 | link: '/zh/miscellaneous/design-concepts.html' 47 | }, 48 | { 49 | text: 'FAQ', 50 | link: '/zh/faq/' 51 | }, 52 | { 53 | text: '术语', 54 | link: '/zh/miscellaneous/glossary.html' 55 | } 56 | ] 57 | }, 58 | { 59 | text: '其他', 60 | items: [ 61 | { 62 | text: '从 0.x 迁移', 63 | link: '/zh/miscellaneous/migration-guide.html' 64 | }, 65 | { 66 | text: 'Changelog', 67 | link: 'https://github.com/vuejs/vuepress/blob/master/CHANGELOG.md' 68 | } 69 | ] 70 | } 71 | ] 72 | }, 73 | { 74 | text: 'v1.x', 75 | items: [ 76 | { 77 | text: 'v2.x', 78 | link: 'https://v2.vuepress.vuejs.org/zh/' 79 | }, 80 | { 81 | text: 'v0.x', 82 | link: 'https://v0.vuepress.vuejs.org/zh/' 83 | } 84 | ] 85 | } 86 | ] 87 | -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/guide/global-computed.md: -------------------------------------------------------------------------------- 1 | # Global Computed 2 | 3 | In VuePress, some core [computed properties](https://vuejs.org/v2/guide/computed.html#Computed-Properties) can be used by the [default theme](../theme/default-theme-config.md) or custom themes. Or in Markdown pages [using vue](./using-vue.md#access-to-site-page-data). 4 | 5 | ## $site 6 | 7 | This is the `$site` value of the site you’re currently reading: 8 | 9 | ``` json 10 | { 11 | "title": "VuePress", 12 | "description": "Vue-powered static site generator", 13 | "base": "/", 14 | "pages": [ 15 | { 16 | "lastUpdated": 1524027677000, 17 | "path": "/", 18 | "title": "VuePress", 19 | "frontmatter": {} 20 | }, 21 | ... 22 | ] 23 | } 24 | ``` 25 | 26 | ## $page 27 | 28 | This is the `$page` value of the page you’re currently reading: 29 | 30 | ``` json 31 | { 32 | "title": "Global Computed", 33 | "frontmatter": {}, 34 | "regularPath": "/guide/global-computed.html", 35 | "key": "v-d4cbeb69eff3d", 36 | "path": "/guide/global-computed.html", 37 | "headers": [ 38 | { 39 | "level": 2, 40 | "title": "$site", 41 | "slug": "site" 42 | }, 43 | { 44 | "level": 2, 45 | "title": "$page", 46 | "slug": "$page" 47 | }, 48 | ... 49 | ] 50 | } 51 | ``` 52 | 53 | ## $frontmatter 54 | 55 | Reference of [$page](#page).frontmatter. 56 | 57 | ## $lang 58 | 59 | The language of the current page. Default: `en-US`. 60 | 61 | For more information, see [Internationalization](../guide/i18n.md). 62 | 63 | ## $localePath 64 | 65 | The locale path prefix for the current page. Default: `/`. 66 | 67 | For more information, see [Internationalization](../guide/i18n.md). 68 | 69 | ## $title 70 | 71 | Value of the `<title>` label used for the current page. 72 | 73 | ## $description 74 | 75 | The `content` value of the `<meta name= "description" content= "...">` for the current page. 76 | 77 | ## $themeConfig 78 | 79 | Refers to `siteConfig.themeConfig`. 80 | -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/zh/api/node.md: -------------------------------------------------------------------------------- 1 | # Node.js API 2 | 3 | ## 使用 4 | 5 | ```js 6 | const { createApp, dev, build, eject } = require('vuepress') 7 | ``` 8 | 9 | ## 方法 10 | 11 | ### createApp(\[options]): Promise\<App> 12 | 13 | 创建一个 VuePress 应用实例。 14 | 15 | #### App.prototype.process: () => Promise\<void> | never 16 | 17 | 用于准备当前站点上下文的异步方法。其中包含加载页面和插件、应用插件等。 18 | 19 | #### App.prototype.dev: () => Promise\<App> | never 20 | 21 | 使用当前应用程序上下文启动一个 devProcess. 22 | 23 | 24 | #### App.prototype.build: () => Promise\<App> | never 25 | 26 | 使用当前应用程序上下文启动一个 buildProcess. 27 | 28 | ### dev(\[options]): Promise\<App> 29 | 30 | 启动一个 Dev Server,实际上它是由 `createapp` 实现的: 31 | 32 | ```js 33 | async function dev (options) { 34 | const app = createApp(options) 35 | await app.process() 36 | return app.dev() 37 | } 38 | ``` 39 | 40 | ### build(\[options]): Promise\<App> 41 | 42 | 将源文件构建为静态站点, 实际上它是由 `createapp` 实现的: 43 | 44 | ```js 45 | async function build (options) { 46 | const app = createApp(options) 47 | await app.process() 48 | return app.build() 49 | } 50 | ``` 51 | 52 | ### eject(targetDir): Promise\<void> 53 | 54 | 将默认主题复制到 `{targetDir}/.vuepress/theme`中进行自定义。 55 | 56 | 57 | ## Options 58 | 59 | ### sourceDir 60 | 61 | - 类型: `string` 62 | - 默认值: `true` 63 | 64 | 指定 VuePress 站点的源目录。 65 | 66 | ### theme 67 | 68 | - 类型: `string` 69 | - 默认值: `false` 70 | 71 | 参见 [theme](../config/README.md#theme)。 72 | 73 | ### plugins 74 | 75 | - 类型: `array` 76 | - 默认值: `false` 77 | 78 | 参见 [plugins](../config/README.md#plugins)。 79 | 80 | ### temp 81 | 82 | - 类型: `string` 83 | - 默认值: `false` 84 | 85 | 参见 [temp](../config/README.md#temp)。 86 | 87 | ### dest 88 | 89 | - 类型: `string` 90 | - 默认值: `false` 91 | 92 | 参见 [dest](../config/README.md#dest)。 93 | 94 | ### siteConfig 95 | 96 | - 类型: `object` 97 | - 默认值: `{}` 98 | 99 | 当你想编写测试且不想依赖于实际的配置文件时,它将非常有用。想要查看所有的配置选项,请移步 [siteConfig](../config/README.md)。 100 | -------------------------------------------------------------------------------- /packages/vuepress-theme-vt/styles/header.styl: -------------------------------------------------------------------------------- 1 | .vp-doc { 2 | h1, h2, h3, h4, h5, h6 { 3 | font-weight: 500; 4 | line-height: 1.5; 5 | 6 | /* @see https://css-tricks.com/hash-tag-links-padding/ */ 7 | &::before { 8 | display: block; 9 | content: ' '; 10 | margin-top: -72px; 11 | height: 72px; 12 | visibility: hidden; 13 | pointer-events: none; 14 | } 15 | 16 | &:hover { 17 | .header-anchor { 18 | opacity: 1; 19 | } 20 | } 21 | } 22 | 23 | h1 { 24 | margin: 5rem 0 0 0; 25 | font-size: 38px; 26 | line-height: 1.4; 27 | letter-spacing: -0.02em; 28 | } 29 | 30 | h2 { 31 | margin: 3.5rem 0 1.8rem 0; 32 | // border-top: 1px solid var(--vp-c-divider-light); 33 | font-size: 24px; 34 | letter-spacing: -0.02em; 35 | } 36 | 37 | @media (max-width: 768px) { 38 | h1 { 39 | font-size: 32px; 40 | margin-bottom: 1.8rem; 41 | } 42 | 43 | h1+h2 { 44 | margin-top: 36px; 45 | } 46 | } 47 | 48 | h3 { 49 | font-size: 19px; 50 | letter-spacing: -0.01em; 51 | margin: 3rem 0 1.25rem; 52 | } 53 | 54 | h2+h3 { 55 | margin-top: 0; 56 | } 57 | 58 | h4 { 59 | font-size: 17px; 60 | margin: 1.8rem 0 1rem; 61 | } 62 | 63 | .header-anchor { 64 | float: left; 65 | margin-left: -0.87em; 66 | padding-right: 0.23em; 67 | font-weight: 500; 68 | opacity: 0; 69 | transition: color 0.25s, opacity 0.25s; 70 | } 71 | } 72 | 73 | html.statusbar-enabled { 74 | .vp-doc { 75 | h1, h2, h3, h4, h5, h6 { 76 | &::before { 77 | margin-top: calc(-1 * (var(--vp-statusbar-height) + 72px)); 78 | height: calc(var(--vp-statusbar-height) + 72px); 79 | } 80 | } 81 | } 82 | } -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/.vuepress/config/nav/en.ts: -------------------------------------------------------------------------------- 1 | import { NavItem } from 'vuepress/config' 2 | 3 | export const NavItems4EN: NavItem[] = [ 4 | { 5 | text: 'Guide', 6 | link: '/guide/' 7 | }, 8 | { 9 | text: 'Config Reference', 10 | link: '/config/' 11 | }, 12 | { 13 | text: 'Plugin', 14 | link: '/plugin/' 15 | }, 16 | { 17 | text: 'Theme', 18 | link: '/theme/' 19 | }, 20 | { 21 | text: 'Learn More', 22 | ariaLabel: 'Learn More', 23 | items: [ 24 | { 25 | text: 'API', 26 | items: [ 27 | { 28 | text: 'CLI', 29 | link: '/api/cli.html' 30 | }, 31 | { 32 | text: 'Node', 33 | link: '/api/node.html' 34 | } 35 | ] 36 | }, 37 | { 38 | text: 'Contributing Guide', 39 | items: [ 40 | { 41 | text: 'Local Development', 42 | link: '/miscellaneous/local-development.html' 43 | }, 44 | { 45 | text: 'Design Concepts', 46 | link: '/miscellaneous/design-concepts.html' 47 | }, 48 | { 49 | text: 'FAQ', 50 | link: '/faq/' 51 | }, 52 | { 53 | text: 'Glossary', 54 | link: '/miscellaneous/glossary.html' 55 | } 56 | ] 57 | }, 58 | { 59 | text: 'Resources', 60 | items: [ 61 | { 62 | text: 'Migrate from 0.x', 63 | link: '/miscellaneous/migration-guide.html' 64 | }, 65 | { 66 | text: 'Changelog', 67 | link: 'https://github.com/vuejs/vuepress/blob/master/CHANGELOG.md' 68 | } 69 | ] 70 | } 71 | ] 72 | }, 73 | { 74 | text: 'v1.x', 75 | items: [ 76 | { 77 | text: 'v2.x', 78 | link: 'https://v2.vuepress.vuejs.org' 79 | }, 80 | { 81 | text: 'v0.x', 82 | link: 'https://v0.vuepress.vuejs.org' 83 | } 84 | ] 85 | } 86 | ] 87 | -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/zh/plugin/using-a-plugin.md: -------------------------------------------------------------------------------- 1 | # 使用插件 2 | 3 | 你可以通过在 `.vuepress/config.js` 中做一些配置来使用插件: 4 | 5 | ``` js 6 | module.exports = { 7 | plugins: [ 8 | require('./my-plugin.js') 9 | ] 10 | } 11 | ``` 12 | 13 | ## 使用来自依赖的插件 14 | 15 | 一个插件可以在以 `vuepress-plugin-xxx` 的形式发布到 npm,你可以这样使用它: 16 | 17 | ``` js 18 | module.exports = { 19 | plugins: [ 'vuepress-plugin-xx' ] 20 | } 21 | ``` 22 | 23 | ## 插件的缩写 24 | 25 | 如果你的插件名以 `vuepress-plugin-` 开头,你可以使用缩写来省略这个前缀: 26 | 27 | ``` js 28 | module.exports = { 29 | plugins: [ 'xxx' ] 30 | } 31 | ``` 32 | 33 | 和下面等价: 34 | 35 | ``` js 36 | module.exports = { 37 | plugins: [ 'vuepress-plugin-xxx' ] 38 | } 39 | ``` 40 | 41 | 这也适用于 [Scoped Packages](https://docs.npmjs.com/misc/scope): 42 | 43 | ``` js 44 | module.exports = { 45 | plugins: [ '@org/vuepress-plugin-xxx', '@vuepress/plugin-xxx' ] 46 | } 47 | ``` 48 | 49 | 等价于: 50 | 51 | ``` js 52 | module.exports = { 53 | plugins: [ '@org/xxx', '@vuepress/xxx' ] 54 | } 55 | ``` 56 | 57 | ::: warning 注意 58 | 以 `@vuepress/plugin-` 开头的插件是官方维护的插件。 59 | ::: 60 | 61 | ## 插件的选项 62 | 63 | ### Babel 式 64 | 65 | 插件可以通过在配置内的数组中封装名称和选项对象来指定选项: 66 | 67 | ``` js 68 | module.exports = { 69 | plugins: [ 70 | [ 71 | 'vuepress-plugin-xxx', 72 | { /* options */ } 73 | ] 74 | ] 75 | } 76 | ``` 77 | 78 | 由于这种风格和 [babeld Plugin/Preset Options](https://babeljs.io/docs/en/plugins#plugin-preset-options) 一致,我们称之为"Babel 风格"。 79 | 80 | ### 对象式 81 | 82 | VuePress 也提供了一种更简单的方式来使用来自依赖的插件: 83 | 84 | ``` js 85 | module.exports = { 86 | plugins: { 87 | 'xxx': { /* options */ } 88 | } 89 | } 90 | ``` 91 | 92 | ::: warning 注意 93 | 可以通过显示地将选项设置成 `false` 来禁用一个插件: 94 | 95 | - Babel 风格 96 | 97 | ``` js 98 | module.exports = { 99 | plugins: [ 100 | [ 'xxx', false ] // disabled. 101 | ] 102 | } 103 | ``` 104 | 105 | - 对象风格 106 | 107 | ``` js 108 | module.exports = { 109 | plugins: { 110 | 'xxx': false // disabled. 111 | } 112 | } 113 | ``` 114 | 115 | ::: 116 | -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/api/cli.md: -------------------------------------------------------------------------------- 1 | --- 2 | sidebarDepth: 3 3 | --- 4 | 5 | # Command-line Interface 6 | 7 | Currently, there are four cli commands in VuePress: [build](#build), [dev](#dev), [eject](#eject) and [info](#info). 8 | 9 | If they are not enough for you, you can also create [your own commands](#more-commands). 10 | 11 | ## Usage 12 | 13 | ```bash 14 | vuepress <command> [options] 15 | 16 | Commands: 17 | dev [targetDir] start development server 18 | build [targetDir] build dir as static site 19 | eject [targetDir] copy the default theme into .vuepress/theme for customization. 20 | info Shows debugging information about the local environment 21 | ``` 22 | 23 | You can always add `--help` flag for more information. 24 | 25 | ## Commands 26 | 27 | ### build 28 | 29 | Build dir as a static site. 30 | 31 | #### -p, --port `<port>` 32 | 33 | See [port](../config/README.md#port). 34 | 35 | #### -t, --temp `<temp>` 36 | 37 | See [temp](../config/README.md#temp). 38 | 39 | #### -c, --cache `[cache]` 40 | 41 | #### --no-cache 42 | 43 | See [cache](../config/README.md#cache). 44 | 45 | #### -d, --dest `<dest>` 46 | 47 | See [dest](../config/README.md#dest). 48 | 49 | #### --debug 50 | 51 | Start development server in debug mode. 52 | 53 | #### --silent 54 | 55 | Start development server in silent mode. 56 | 57 | ### dev 58 | 59 | Start a development server. All options from `vuepress build` are available. And there are several options specifically for dev: 60 | 61 | #### --host `<host>` 62 | 63 | See [host](../config/README.md#host). 64 | 65 | #### --open 66 | 67 | Open browser when ready. 68 | 69 | #### --no-clear-screen 70 | 71 | Do not clear screen when dev server is ready. Note that dev server will not clear screen if you start it in debug mode. 72 | 73 | ### eject 74 | 75 | Copy the default theme into `.vuepress/theme` for customization. 76 | 77 | ### info 78 | 79 | Shows debugging information about the local environment. 80 | 81 | ## more commands 82 | 83 | You can create a custom command with [extendCli](../plugin/option-api.md#extendcli). 84 | -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/zh/plugin/official/plugin-last-updated.md: -------------------------------------------------------------------------------- 1 | --- 2 | title: last-updated 3 | metaTitle: Last-Updated 插件 | VuePress 4 | --- 5 | 6 | # [@vuepress/plugin-last-updated](https://github.com/vuejs/vuepress/tree/master/packages/@vuepress/plugin-last-updated) 7 | 8 | > last-updated 插件。 9 | 10 | 如果你使用默认主题,你无需安装本插件,因为 VuePress 的 `core` 中已经包含此插件,同时,你应该直接使用 [themeConfig.lastUpdated](../../theme/default-theme-config.md#最后更新时间) 选项。 11 | 12 | 如果你在你的自定义主题中使用该插件,你将需要自己在主题中完成 lastUpdated 的 UI,你可以使用 __[$page.lastUpdated](../../guide/global-computed.md#page)__ 去访问当前页面的时间字符串。 13 | 14 | ## 使用 15 | 16 | ```js 17 | module.exports = { 18 | plugins: ['@vuepress/last-updated'] 19 | } 20 | ``` 21 | 22 | ## 选项 23 | 24 | ### transformer 25 | 26 | - 类型: `(timestamp: number, lang: string) => string` 27 | - 默认值: `undefined` 28 | 29 | 默认情况下,本插件为每个页面生成一个 13 位的时间戳,你可以传入一个 transformer 将其转换为你想要的任何格式。 30 | 31 | 例子: 32 | 33 | ``` javascript 34 | const moment = require('moment'); 35 | 36 | module.exports = { 37 | plugins: [ 38 | [ 39 | '@vuepress/last-updated', 40 | { 41 | transformer: (timestamp, lang) => { 42 | // 不要忘了安装 moment 43 | const moment = require('moment') 44 | moment.locale(lang) 45 | return moment(timestamp).fromNow() 46 | } 47 | } 48 | ] 49 | ] 50 | } 51 | ``` 52 | 53 | ::: tip 54 | 如果你在[多语言](../../guide/i18n.md)模式下运行,你还可以使用第二个参数 `lang` 为不同语言生成时间字符串。 55 | 56 | 请注意,在 VuePress 中,我们遵循以下规范:[W3C > Language tags in HTML and XML](https://en.wikipedia.org/wiki/Language_localisation),因此 `zh-CN` 使用连字符(`-`)而不是下划线(`_`)。 请确保你使用的库遵循此规范,否则请自行转换。 57 | ::: 58 | 59 | ### dateOptions 60 | 61 | - 类型: `object` 62 | - 默认值: `undefined` 63 | 64 | 你也可以传入一个对象作为选项,以自定义时间戳的输出格式。详细信息请参阅 [`Date.prototype.toLocaleString()`](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Date/toLocaleString) 的选项参数。 65 | 66 | ```javascript 67 | module.exports = { 68 | plugins: [ 69 | [ 70 | '@vuepress/last-updated', 71 | { 72 | dateOptions:{ 73 | hour12: false 74 | } 75 | } 76 | ] 77 | ] 78 | } 79 | ``` 80 | -------------------------------------------------------------------------------- /packages/docs/docs/guide/status.md: -------------------------------------------------------------------------------- 1 | --- 2 | status: <GlobalStatus /> 3 | statusVersion: v5 4 | --- 5 | 6 | # Status 7 | 8 | You can specify status text like the top of this document. 9 | 10 | ## Global Status 11 | 12 | Specify global status via `themeConfig.status`: 13 | 14 | ```ts 15 | // .vuepress/config.js 16 | module.exports = { 17 | theme: "vt", 18 | themeConfig: { 19 | status: 'This is global status' 20 | }, 21 | }; 22 | ``` 23 | 24 | ## Page Status 25 | 26 | Specify page status via [frontmatter.status](https://vuepress.vuejs.org/guide/frontmatter.html): 27 | 28 | 29 | ```md 30 | --- 31 | status: 'This is page status' 32 | --- 33 | ``` 34 | 35 | ## Using Vue Component 36 | 37 | You can specify page status via a global Vue Component, let's create `.vuepress/components/GlobalStatus.vue` as example: 38 | 39 | ```vue 40 | <template> 41 | <span> This is page status </span> 42 | </template> 43 | ``` 44 | 45 | - via page frontmatter config: 46 | 47 | ```md 48 | --- 49 | status: <GlobalStatus /> 50 | --- 51 | ``` 52 | 53 | - via global config: 54 | 55 | ```ts 56 | // .vuepress/config.js 57 | module.exports = { 58 | theme: "vt", 59 | themeConfig: { 60 | status: '<GlobalStatus />' 61 | }, 62 | }; 63 | ``` 64 | 65 | ## Closing Status 66 | 67 | You can use a global method `$closeCurrentStatus` to close status: 68 | 69 | ```vue 70 | <template> 71 | <span> 72 | This is page status   73 | <a style="cursor: pointer" @click="$closeCurrentStatus">x</a> 74 | </span> 75 | </template> 76 | ``` 77 | 78 | and using `statusVersion` to control the status version: 79 | 80 | - via page frontmatter config: 81 | 82 | ```md 83 | --- 84 | status: <GlobalStatus /> 85 | statusVersion: v2 86 | --- 87 | ``` 88 | 89 | - via global config: 90 | 91 | ```ts 92 | // .vuepress/config.js 93 | module.exports = { 94 | theme: "vt", 95 | themeConfig: { 96 | status: '<GlobalStatus />', 97 | statusVersion: 'v2' 98 | }, 99 | }; 100 | ``` 101 | 102 | You need bump `statusVersion` when you released new status, so that user can see the new status. -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/zh/guide/markdown-slot.md: -------------------------------------------------------------------------------- 1 | # Markdown 插槽 2 | 3 | VuePress 实现了一套针对 Markdown 的内容分发 API。通过这个特性,你可以将你的文档分割成多个片段,以便于在布局组件中灵活组合。 4 | 5 | ## 为什么需要 Markdown 插槽 6 | 7 | 首先,我们回顾一下布局组件和 Markdown 文件之间的关系: 8 | 9 | <diagram-markdown-slot-relationship/> 10 | 11 | Markdown 文件是元数据(页面内容、配置等)的提供者,而布局组件负责消费他们。我们可以通过 frontmatter 来定义一些普通数据类型的元数据,但对于 Markdown / HTML 这种涉及到编译前后差异的复杂元数据,frontmatter 却无能能力。 12 | 13 | Markdown 插槽便解决了这一类问题。 14 | 15 | ## 具名插槽 16 | 17 | 你可以通过下述的语法来定义一个具名 Markdown 插槽: 18 | 19 | ``` md 20 | ::: slot name 21 | 22 | ::: 23 | ``` 24 | 25 | 在布局组件中利用 `Content` 组件来使用该插槽: 26 | 27 | ``` vue 28 | <Content slot-key="name"/> 29 | ``` 30 | 31 | ::: tip 提示 32 | 这里我们使用的是 `slot-key` 而不是 `slot`,这是因为在 Vue 中,`slot` 是一个保留的 `prop` 名。 33 | ::: 34 | 35 | ## 插槽的默认内容 36 | 37 | 默认情况下,一个 Markdown 文件中的普通内容将会成为 Markdown 插槽的默认内容,你可以直接使用 `Content` 组件来访问它: 38 | 39 | ``` vue 40 | <Content/> 41 | ``` 42 | 43 | ## 例子 44 | 45 | 假设你的布局组件如下: 46 | 47 | ``` vue 48 | <template> 49 | <div class="container"> 50 | <header> 51 | <Content slot-key="header"/> 52 | </header> 53 | <main> 54 | <Content/> 55 | </main> 56 | <footer> 57 | <Content slot-key="footer"/> 58 | </footer> 59 | </div> 60 | </template> 61 | ``` 62 | 63 | 如果一个页面的 `markdown` 的内容是这样: 64 | 65 | ```md 66 | ::: slot header 67 | # Here might be a page title 68 | ::: 69 | 70 | - A Paragraph 71 | - Another Paragraph 72 | 73 | ::: slot footer 74 | Here's some contact info 75 | ::: 76 | ``` 77 | 78 | 那么这一页最终被渲染出的 HTML 将会是: 79 | 80 | ```html 81 | <div class="container"> 82 | <header> 83 | <div class="content header"> 84 | <h1>Here might be a page title</h1> 85 | </div> 86 | </header> 87 | <main> 88 | <div class="content default"> 89 | <ul> 90 | <li>A Paragraph</li> 91 | <li>Another Paragraph</li> 92 | </ul> 93 | </div> 94 | </main> 95 | <footer> 96 | <div class="content footer"> 97 | <p>Here's some contact info</p> 98 | </div> 99 | </footer> 100 | </div> 101 | ``` 102 | 103 | 请注意: 104 | 105 | 1. 和 Vue 本身提供的 slot 机制不太相同,每个 Content 分发的内容都会被一个 div 所包裹,其 class 是 content 和 slot 的名字。 106 | 2. 请确保所定义的 slot 的唯一性。 107 | -------------------------------------------------------------------------------- /packages/vuepress-theme-vt/components/Sidebar.vue: -------------------------------------------------------------------------------- 1 | <template> 2 | <aside class="sidebar"> 3 | <slot name="top" /> 4 | 5 | <NavLinks :showSearchBox="false" /> 6 | 7 | <SidebarNavLinks /> 8 | 9 | <SidebarLinks :depth="0" :items="items" /> 10 | <slot name="bottom" /> 11 | </aside> 12 | </template> 13 | 14 | <script> 15 | import SidebarLinks from "@theme/components/SidebarLinks.vue"; 16 | import NavLinks from "@theme/components/NavLinks.vue"; 17 | import SidebarNavLinks from "@theme/components/SidebarNavLinks.vue"; 18 | 19 | export default { 20 | name: "Sidebar", 21 | 22 | components: { SidebarLinks, NavLinks, SidebarNavLinks }, 23 | 24 | props: ["items"], 25 | }; 26 | </script> 27 | 28 | <style lang="stylus"> 29 | .sidebar { 30 | display: flex; 31 | flex-direction: column; 32 | 33 | ul { 34 | padding: 0; 35 | margin: 0; 36 | list-style-type: none; 37 | } 38 | 39 | a { 40 | display: inline-block; 41 | } 42 | 43 | .links { 44 | display: none; 45 | border-bottom: 1px solid var(--vp-c-divider-light); 46 | padding: 0.5rem 0 0.75rem 0; 47 | 48 | a { 49 | font-weight: 500; 50 | } 51 | 52 | .nav-item, .repo-link, .appearance { 53 | display: block; 54 | line-height: 1.25rem; 55 | font-size: 13px; 56 | padding: 0.5rem 0 0.5rem 0rem; 57 | } 58 | } 59 | 60 | & > .sidebar-links { 61 | padding: 2rem 0; 62 | padding-top: 1rem; 63 | 64 | & > li > a.sidebar-link { 65 | line-height: 1.7; 66 | font-weight: bold; 67 | color: inherit; 68 | font-size: 14px; 69 | } 70 | 71 | & > li:not(:first-child) { 72 | margin-top: 0.75rem; 73 | } 74 | } 75 | } 76 | 77 | @media (max-width: $MQMobile) { 78 | .sidebar { 79 | padding-left: 1rem; 80 | 81 | .links { 82 | display: block; 83 | padding-left: 0; 84 | 85 | .dropdown-wrapper .nav-dropdown .dropdown-item a.router-link-active::after { 86 | top: calc(1rem - 2px); 87 | } 88 | 89 | .nav-item, .repo-link, .mobile-dropdown-title { 90 | font-size: 15px; 91 | } 92 | } 93 | 94 | & > .sidebar-links { 95 | padding: 1rem 0; 96 | } 97 | } 98 | } 99 | </style> 100 | -------------------------------------------------------------------------------- /packages/docs/docs/examples/disable-sidebar.md: -------------------------------------------------------------------------------- 1 | --- 2 | sidebar: false 3 | --- 4 | 5 | # Disable Sidebar Example 6 | 7 | Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example 8 | 9 | ## Disable Sidebar Example 10 | 11 | Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example 12 | 13 | ## Disable Sidebar Example 14 | 15 | Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example 16 | 17 | ## Disable Sidebar Example 18 | 19 | Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example 20 | 21 | ## Disable Sidebar Example 22 | 23 | Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example 24 | 25 | ## Disable Sidebar Example 26 | 27 | Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example Disable Sidebar Example -------------------------------------------------------------------------------- /packages/docs/docs/api/config-frontmatter.md: -------------------------------------------------------------------------------- 1 | --- 2 | pageClass: 'config-frontmatter' 3 | lastUpdated: false 4 | --- 5 | 6 | # Config: Frontmatter 7 | 8 | ## home 9 | 10 | - **Type**: `boolean` 11 | - **Default**: `false` 12 | 13 | Declare that current page is homepage: 14 | 15 | ```md 16 | --- 17 | home: true 18 | --- 19 | ``` 20 | 21 | For more details please head [Guide > Homepage](../guide/home.md). 22 | 23 | ## api 24 | 25 | - **Type**: `boolean` 26 | - **Default**: `false` 27 | 28 | Declare that current page is api page: 29 | 30 | ```md 31 | --- 32 | api: true 33 | --- 34 | ``` 35 | 36 | For more details please head [Guide > API Page](../guide/api-page.md). 37 | 38 | ## toc 39 | 40 | - **Type**: `boolean` 41 | - **Default**: `true` 42 | 43 | Display table of content at right side, set `false` to hidden it: 44 | 45 | ```md 46 | --- 47 | toc: false 48 | --- 49 | ``` 50 | 51 | ## sidebar 52 | 53 | - **Type**: `boolean` 54 | - **Default**: `true` 55 | 56 | Display current sidebar at left side, set `false` to hidden sidebar: 57 | 58 | ```md 59 | --- 60 | sidebar: false 61 | --- 62 | ``` 63 | 64 | See [live example](../../../docs/docs/examples/disable-sidebar.md). 65 | 66 | ## sidebarDepth 67 | 68 | - **Type**: `number` 69 | - **Default**: `0` 70 | 71 | Set maximum depth of sidebar headers, set `1` to display nested header links at sidebar: 72 | 73 | ```md 74 | --- 75 | sidebarDepth: 1 76 | --- 77 | ``` 78 | 79 | ## navbar 80 | 81 | - **Type**: `boolean` 82 | - **Default**: `true` 83 | 84 | Display current navbar at the top, set `false` to hidden it: 85 | 86 | ```md 87 | --- 88 | navbar: false 89 | --- 90 | ``` 91 | 92 | ## pageEdit 93 | 94 | Display page edit at the bottom, set `false` to hidden it: 95 | 96 | ```md 97 | --- 98 | pageEdit: false 99 | --- 100 | ``` 101 | 102 | ## lastUpdated 103 | 104 | Display last edit at the bottom, set `false` to hidden it: 105 | 106 | ```md 107 | --- 108 | lastUpdated: false 109 | --- 110 | ``` 111 | 112 | ## extractApiHeaders 113 | 114 | - **Type**: `number[]` 115 | - **Default**: [2, 3] 116 | 117 | Extract headers of target levels from api page, by default it will extract `h2` and `h3` headers: 118 | 119 | ```md 120 | --- 121 | extractApiHeaders: [2] 122 | --- 123 | ``` 124 | -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/plugin/README.md: -------------------------------------------------------------------------------- 1 | # Plugin 2 | 3 | Plugins generally add global-level functionality to VuePress. There is no strictly defined scope for a plugin. You can find out more plugins at [Awesome VuePress](https://github.com/vuepressjs/awesome-vuepress#plugins). 4 | 5 | ## Examples 6 | 7 | There are typically several types of plugins: 8 | 9 | 1. Extend the page’s metadata generated at compile time. For example [@vuepress/plugin-last-updated](./official/plugin-last-updated.md); 10 | 2. Generate extra files before or after compilation. For example [@vuepress/plugin-pwa](./official/plugin-pwa.md); 11 | 3. Inject global UI. For example [@vuepress/plugin-back-to-top](./official/plugin-back-to-top.md); 12 | 4. Extend the CLI with custom commands. For example [vuepress-plugin-export](https://github.com/ulivz/vuepress-plugin-export). 13 | 14 | Here is also a little slightly complicated plugin example [@vuepress/plugin-blog](https://vuepress-plugin-blog.billyyyyy3320.com) that uses compile-time metadata to generate some dynamic modules and initialize them on the client-side by using `enhanceAppFiles`. 15 | 16 | ## Out of the Box 17 | 18 | To keep things at a minimum, not all of the official plugins are shipped with VuePress. Here is the list of plugins that are pre-installed in the VuePress and the default theme, **plugins that are not in the list below need to be installed manually**(for example [@vuepress/plugin-back-to-top](./official/plugin-back-to-top.md)). 19 | 20 | ### Plugins that come with VuePress 21 | 22 | - [@vuepress/plugin-last-updated](./official/plugin-last-updated.md) 23 | - [@vuepress/plugin-register-components](./official/plugin-register-components.md) 24 | 25 | ### Plugins that come with the default theme 26 | 27 | - [@vuepress/plugin-active-header-links](./official/plugin-active-header-links.md) 28 | - [@vuepress/plugin-nprogress](./official/plugin-nprogress.md) 29 | - [@vuepress/plugin-search](./official/plugin-search.md) 30 | - [vuepress-plugin-container](https://vuepress-community.netlify.app/en/plugins/container/#vuepress-plugin-container) 31 | - [vuepress-plugin-smooth-scroll](https://vuepress-community.netlify.app/en/plugins/smooth-scroll/#installation) 32 | 33 | ## Architecture 34 | 35 | The architecture of the whole plugin system is as follows: 36 | 37 | ![Architecture of VuePress](/architecture.png) 38 | -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/miscellaneous/glossary.md: -------------------------------------------------------------------------------- 1 | --- 2 | sidebar: auto 3 | --- 4 | 5 | # Glossary 6 | 7 | You may stumble upon some unfamiliar concepts in the documentation. This section lists the common terms in the documentation for easy access, learning and plugin/theme development. 8 | 9 | ## layout 10 | 11 | - Access: `$page.frontmatter.layout` 12 | 13 | Name of the layout component used by the current page. 14 | 15 | ## frontmatter 16 | 17 | - Access: `$page.frontmatter` 18 | 19 | Configuration wrapped by `---` in the `markdown` file of the current page, generally used to do some page-level configuration. For more details, please see [Frontmatter](../guide/frontmatter.md). 20 | 21 | ## permalink 22 | 23 | - Access: `$page.frontmatter.permalink` 24 | 25 | Permalinks. For more details, please head [permalinks](../guide/permalinks.md). 26 | 27 | ## regularPath 28 | 29 | - Access: `$page.regularPath` 30 | 31 | The current page is based on the URL generated by the directory structure. 32 | 33 | ::: tip 34 | When dynamically generating routes during the build period, a page’s URL (`$page.path`) will use `$page.frontmatter.permalink` first, and if it doesn’t exist, it will be downgraded to `$page.regularPath`. 35 | ::: 36 | 37 | ## headers 38 | 39 | - Access: `$page.headers` 40 | 41 | That is, those titles defined by one or more `#` in `markdown`. 42 | 43 | ## siteConfig 44 | 45 | - Access: `$site | Context.siteConfig` 46 | 47 | `.vuepress/config.js`, i.e., `site configuration`。 48 | 49 | ## themeConfig 50 | 51 | - Access: `$themeConfig | Context.themeConfig` 52 | 53 | Value of `themeConfig` in `.vuepress/config.js`, i.e., user’s theme configuration. 54 | 55 | ## themePath 56 | 57 | - Access: `Context.themeAPI.theme.path` 58 | 59 | Root path (absolute path) of the used theme. 60 | 61 | ## themeEntry 62 | 63 | - Access: `Context.themeAPI.theme.entry` 64 | 65 | Theme’s configuration file - `themePath/index.js`. 66 | 67 | ## parentThemePath 68 | 69 | - Access: `Context.themeAPI.parentTheme.path` 70 | 71 | If the current theme is a derived theme, `parentThemePath` refers to the absolute path of the parent theme. 72 | 73 | ## parentThemeEntry 74 | 75 | - Access: `Context.themeAPI.parentTheme.entry` 76 | 77 | If the current theme is a derived theme, `parentThemeEntry` refers to the theme configuration of the parent theme. 78 | 79 | -------------------------------------------------------------------------------- /packages/vuepress-theme-vt/components/VTSwitchAppearance.vue: -------------------------------------------------------------------------------- 1 | <script> 2 | import VTSwitch from "./VTSwitch.vue"; 3 | import VTIconSun from "./icons/VTIconSun.vue"; 4 | import VTIconMoon from "./icons/VTIconMoon.vue"; 5 | 6 | const storageKey = "--pia-theme-appearance--"; 7 | 8 | export default { 9 | components: { 10 | VTSwitch, 11 | VTIconSun, 12 | VTIconMoon, 13 | }, 14 | data() { 15 | return { 16 | isDark: false, 17 | }; 18 | }, 19 | created() { 20 | if (typeof window !== "undefined") { 21 | this.userPreference = localStorage.getItem(storageKey) || "auto"; 22 | this.query = window.matchMedia(`(prefers-color-scheme: dark)`); 23 | this.isDark = 24 | this.userPreference === "auto" 25 | ? this.query.matches 26 | : this.userPreference === "dark"; 27 | 28 | this.query.onchange = (e) => { 29 | if (this.userPreference === "auto") { 30 | this.setClass((this.isDark = e.matches)); 31 | } 32 | }; 33 | 34 | this.setClass(this.isDark); 35 | } 36 | }, 37 | methods: { 38 | setClass(dark) { 39 | console.log("dark", dark); 40 | 41 | const classList = document.documentElement.classList; 42 | classList[dark ? "add" : "remove"]("dark"); 43 | }, 44 | toggle() { 45 | this.setClass((this.isDark = !this.isDark)); 46 | localStorage.setItem( 47 | storageKey, 48 | (this.userPreference = this.isDark 49 | ? this.query.matches 50 | ? "auto" 51 | : "dark" 52 | : this.query.matches 53 | ? "light" 54 | : "auto") 55 | ); 56 | }, 57 | }, 58 | }; 59 | </script> 60 | 61 | <template> 62 | <VTSwitch 63 | class="vt-switch-appearance" 64 | aria-label="toggle dark mode" 65 | @click.native="toggle" 66 | > 67 | <VTIconSun class="vt-switch-appearance-sun" /> 68 | <VTIconMoon class="vt-switch-appearance-moon" /> 69 | </VTSwitch> 70 | </template> 71 | 72 | <style> 73 | .vt-switch-appearance-sun { 74 | opacity: 1; 75 | } 76 | .vt-switch-appearance-moon { 77 | opacity: 0; 78 | } 79 | 80 | .dark .vt-switch-appearance-sun { 81 | opacity: 0; 82 | } 83 | .dark .vt-switch-appearance-moon { 84 | opacity: 1; 85 | } 86 | 87 | .dark .vt-switch-appearance .vt-switch-check { 88 | transform: translateX(18px); 89 | } 90 | </style> -------------------------------------------------------------------------------- /packages/init/generator/saofile.js: -------------------------------------------------------------------------------- 1 | /** 2 | * @type {import('SAO').GeneratorConfig} 3 | */ 4 | module.exports = { 5 | prompts() { 6 | return [ 7 | { 8 | type: "input", 9 | name: "name", 10 | message: "What's the name of your VT Website.", 11 | default: this.outFolder, 12 | }, 13 | { 14 | type: "input", 15 | name: "description", 16 | message: "How would you describe your Website.", 17 | default: `my awesome VT project`, 18 | }, 19 | { 20 | type: "input", 21 | name: "username", 22 | message: "What's your git username", 23 | default: this.gitUser.username || this.gitUser.name, 24 | store: true, 25 | }, 26 | { 27 | type: "input", 28 | name: "email", 29 | message: "What's your email?", 30 | default: this.gitUser.email, 31 | store: true, 32 | }, 33 | { 34 | type: "select", 35 | choices: ["default", "i18n"], 36 | name: "type", 37 | message: "Select type", 38 | default: "react", 39 | store: true, 40 | }, 41 | { 42 | type: "select", 43 | choices: ["Y", "N"], 44 | name: "npmInstall", 45 | message: "Run `pnpm install` after project is created?", 46 | default: "N", 47 | store: true, 48 | }, 49 | ]; 50 | }, 51 | async actions() { 52 | const moveAction = { 53 | type: "move", 54 | patterns: { 55 | gitignore: ".gitignore", 56 | "_package.json": "package.json", 57 | }, 58 | }; 59 | if (this.answers.type === "default") { 60 | return [ 61 | { 62 | type: "add", 63 | files: "**", 64 | templateDir: "default", 65 | transformInclude: ['package.json'] 66 | }, 67 | moveAction, 68 | ]; 69 | } else if (this.answers.type === "i18n") { 70 | return [ 71 | { 72 | type: "add", 73 | files: "**", 74 | templateDir: "i18n", 75 | transformInclude: ['package.json'] 76 | }, 77 | moveAction, 78 | ]; 79 | } 80 | }, 81 | async completed() { 82 | this.gitInit(); 83 | if (this.answers.npmInstall === "Y") { 84 | await this.npmInstall(); 85 | } 86 | this.showProjectTips(); 87 | }, 88 | }; 89 | -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/zh/guide/directory-structure.md: -------------------------------------------------------------------------------- 1 | # 目录结构 2 | 3 | VuePress 遵循 **“约定优于配置”** 的原则,推荐的目录结构如下: 4 | 5 | ::: vue 6 | . 7 | ├── docs 8 | │   ├── .vuepress _(**可选的**)_ 9 | │   │   ├── `components` _(**可选的**)_ 10 | │   │   ├── `theme` _(**可选的**)_ 11 | │   │   │ └── Layout.vue 12 | │   │   ├── `public` _(**可选的**)_ 13 | │   │   ├── `styles` _(**可选的**)_ 14 | │   │   │   ├── index.styl 15 | │   │   │   └── palette.styl 16 | │   │   ├── `templates` _(**可选的, 谨慎配置**)_ 17 | │   │   │   ├── dev.html 18 | │   │   │   └── ssr.html 19 | │   │   ├── `config.js` _(**可选的**)_ 20 | │   │   └── `enhanceApp.js` _(**可选的**)_ 21 | │   │  22 | │   ├── README.md 23 | │   ├── guide 24 | │   │   └── README.md 25 | │   └── config.md 26 | │  27 | └── package.json 28 | ::: 29 | 30 | ::: warning 注意 31 | 请留意目录名的大写。 32 | ::: 33 | 34 | - `docs/.vuepress`: 用于存放全局的配置、组件、静态资源等。 35 | - `docs/.vuepress/components`: 该目录中的 Vue 组件将会被自动注册为全局组件。 36 | - `docs/.vuepress/theme`: 用于存放本地主题。 37 | - `docs/.vuepress/styles`: 用于存放样式相关的文件。 38 | - `docs/.vuepress/styles/index.styl`: 将会被自动应用的全局样式文件,会生成在最终的 CSS 文件结尾,具有比默认样式更高的优先级。 39 | - `docs/.vuepress/styles/palette.styl`: 用于重写默认颜色常量,或者设置新的 stylus 颜色常量。 40 | - `docs/.vuepress/public`: 静态资源目录。 41 | - `docs/.vuepress/templates`: 存储 HTML 模板文件。 42 | - `docs/.vuepress/templates/dev.html`: 用于开发环境的 HTML 模板文件。 43 | - `docs/.vuepress/templates/ssr.html`: 构建时基于 Vue SSR 的 HTML 模板文件。 44 | - `docs/.vuepress/config.js`: 配置文件的入口文件,也可以是 `YML` 或 `toml`。 45 | - `docs/.vuepress/enhanceApp.js`: 客户端应用的增强。 46 | 47 | ::: warning 注意 48 | 当你想要去自定义 `templates/ssr.html` 或 `templates/dev.html` 时,最好基于 [默认的模板文件](https://github.com/vuejs/vuepress/blob/master/packages/%40vuepress/core/lib/client/index.dev.html) 来修改,否则可能会导致构建出错。 49 | ::: 50 | 51 | **同时阅读:** 52 | 53 | - [配置](../config/README.md) 54 | - [主题](../theme/README.md) 55 | - [默认主题配置](../theme/default-theme-config.md) 56 | 57 | ## 默认的页面路由 58 | 59 | 此处我们把 `docs` 目录作为 `targetDir` (参考 [命令行接口](../api/cli.md#基本用法)),下面所有的“文件的相对路径”都是相对于 `docs` 目录的。在项目根目录下的 `package.json` 中添加 `scripts` : 60 | 61 | ```json 62 | { 63 | "scripts": { 64 | "dev": "vuepress dev docs", 65 | "build": "vuepress build docs" 66 | } 67 | } 68 | ``` 69 | 70 | 对于上述的目录结构,默认页面路由地址如下: 71 | 72 | | 文件的相对路径 | 页面路由地址 | 73 | |--------------------|----------------| 74 | | `/README.md` | `/` | 75 | | `/guide/README.md` | `/guide/` | 76 | | `/config.md` | `/config.html` | 77 | 78 | -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/api/node.md: -------------------------------------------------------------------------------- 1 | # Node.js API 2 | 3 | ## Usage 4 | 5 | ```js 6 | const { createApp, dev, build, eject } = require('vuepress') 7 | ``` 8 | 9 | ## Methods 10 | 11 | ### createApp(\[options]): Promise\<App> 12 | 13 | Create a VuePress application. 14 | 15 | #### App.prototype.process: () => Promise\<void> | never 16 | 17 | An asynchronous method used to prepare the context of the current app, and which contains loading pages and plugins, apply plugins, etc. 18 | 19 | #### App.prototype.dev: () => Promise\<App> | never 20 | 21 | Launch a dev process with current app context. 22 | 23 | #### App.prototype.build: () => Promise\<App> | never 24 | 25 | Launch a build process with current app context. 26 | 27 | 28 | ### dev(\[options]): Promise\<App> 29 | 30 | Start a development server, actually it’s implemented by `createApp`: 31 | 32 | ```js 33 | async function dev (options) { 34 | const app = createApp(options) 35 | await app.process() 36 | return app.dev() 37 | } 38 | ``` 39 | 40 | ### build(\[options]): Promise\<App> 41 | 42 | Build your source files as a static site, actually it’s implemented by `createApp`: 43 | 44 | ```js 45 | async function build (options) { 46 | const app = createApp(options) 47 | await app.process() 48 | return app.build() 49 | } 50 | ``` 51 | 52 | ### eject(targetDir): Promise\<void> 53 | 54 | Copy the default theme into `{targetDir}/.vuepress/theme` for customization. 55 | 56 | 57 | ## Options 58 | 59 | ### sourceDir 60 | 61 | - Type: `string` 62 | - Required: `true` 63 | 64 | Specify the source directory of your VuePress site. 65 | 66 | ### theme 67 | 68 | - Type: `string` 69 | - Required: `false` 70 | 71 | See [theme](../config/README.md#theme). 72 | 73 | ### plugins 74 | 75 | - Type: `array` 76 | - Required: `false` 77 | 78 | See [plugins](../config/README.md#plugins). 79 | 80 | ### temp 81 | 82 | - Type: `string` 83 | - Required: `false` 84 | 85 | See [temp](../config/README.md#temp). 86 | 87 | ### dest 88 | 89 | - Type: `string` 90 | - Required: `false` 91 | 92 | See [dest](../config/README.md#dest). 93 | 94 | ### siteConfig 95 | 96 | - Type: `object` 97 | - Required: `{}` 98 | 99 | It’s useful when you’re writing tests and don’t want to depend on actual config file, for all options please head [siteConfig](../config/README.md). 100 | -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/.vuepress/config/sidebar/shared.ts: -------------------------------------------------------------------------------- 1 | import fs from 'fs' 2 | import path from 'path' 3 | import { SidebarConfigArray } from 'vuepress/config' 4 | 5 | const officialPlugins = fs 6 | .readdirSync(path.resolve(__dirname, '../../../plugin/official')) 7 | .map(filename => 'official/' + filename.slice(0, -3)) 8 | .sort() 9 | 10 | export function getPluginSidebar ( 11 | pluginTitle: string, 12 | pluginIntro: string, 13 | officialPluginTitle: string 14 | ): SidebarConfigArray { 15 | const sidebar: SidebarConfigArray = [ 16 | { 17 | title: pluginTitle, 18 | collapsable: false, 19 | children: [ 20 | ['', pluginIntro], 21 | 'using-a-plugin', 22 | 'writing-a-plugin', 23 | 'life-cycle', 24 | 'option-api', 25 | 'context-api' 26 | ] 27 | }, 28 | { 29 | title: officialPluginTitle, 30 | collapsable: false, 31 | children: officialPlugins 32 | } 33 | ] 34 | return sidebar 35 | } 36 | 37 | export function getThemeSidebar ( 38 | groupA: string, 39 | introductionA: string 40 | ): SidebarConfigArray { 41 | const sidebar: SidebarConfigArray = [ 42 | { 43 | title: groupA, 44 | collapsable: false, 45 | sidebarDepth: 2, 46 | children: [ 47 | ['', introductionA], 48 | 'using-a-theme', 49 | 'writing-a-theme', 50 | 'option-api', 51 | 'default-theme-config', 52 | 'blog-theme', 53 | 'inheritance' 54 | ] 55 | } 56 | ] 57 | return sidebar 58 | } 59 | 60 | export function getApiSidebar (): SidebarConfigArray { 61 | return ['cli', 'node'] 62 | } 63 | 64 | export function getGuideSidebar (groupA, groupB): SidebarConfigArray { 65 | const sidebar: SidebarConfigArray = [ 66 | { 67 | title: groupA, 68 | collapsable: false, 69 | children: [ 70 | '', 71 | 'getting-started', 72 | 'directory-structure', 73 | 'basic-config', 74 | 'typescript-as-config', 75 | 'assets', 76 | 'markdown', 77 | 'using-vue', 78 | 'i18n', 79 | 'deploy' 80 | ] 81 | }, 82 | { 83 | title: groupB, 84 | collapsable: false, 85 | children: [ 86 | 'frontmatter', 87 | 'permalinks', 88 | 'markdown-slot', 89 | 'global-computed' 90 | ] 91 | } 92 | ] 93 | 94 | return sidebar 95 | } 96 | -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/guide/permalinks.md: -------------------------------------------------------------------------------- 1 | # Permalinks 2 | 3 | ## Background 4 | 5 | Prior to VuePress version 1.0.0, VuePress retrieved all Markdown files in the documents source directory and defined the page links based on the file hierarchy. For example, if you had the following file and directory structure: 6 | 7 | ``` 8 | ├── package.json 9 | └── source 10 | ├── _post 11 | │   └── intro-vuepress.md 12 | ├── index.md 13 | └── tags.md 14 | ``` 15 | 16 | You would then get the following pages: 17 | 18 | ``` 19 | /source/ 20 | /source/tags.html 21 | /source/_post/intro-vuepress.html 22 | ``` 23 | 24 | But for blogs, a customized link of a post would be highly preferrable. VuePress version 1.0.0 introduced support for this feature, known as a **permalink**. With version 1.0.0 or newer, you instead get the following pages: 25 | 26 | ``` 27 | /source/ 28 | /source/tags/ 29 | /source/2018/4/1/intro-vuepress.html 30 | ``` 31 | 32 | This describes the beginning of how VuePress can be used for a blog! 33 | 34 | ## Permalinks 35 | 36 | A permalink is a URL that is intended to remain unchanged for a long time, yielding a hyperlink that is less susceptible to what is known as [link rot](https://en.wikipedia.org/wiki/Link_rot). VuePress supports a flexible way to build permalinks, allowing you to use template variables. 37 | 38 | The default permalink is `/:regular`. 39 | 40 | ### Configure Permalinks 41 | 42 | You can enable permalinks globally for all pages: 43 | 44 | ```js 45 | // .vuepress/config.js 46 | module.exports = { 47 | permalink: '/:year/:month/:day/:slug' 48 | } 49 | ``` 50 | 51 | You can also set set a permalink for a single page only. This overrides the aforementioned global setting: 52 | 53 | 📝 **hello.md**: 54 | 55 | ```markdown 56 | --- 57 | title: Hello World 58 | permalink: /hello-world 59 | --- 60 | 61 | Hello! 62 | ``` 63 | 64 | ### Template Variables 65 | 66 | | Variable | Description | 67 | | --- | --- | 68 | | :year | Published year of post (4-digit) | 69 | | :month | Published month of post (2-digit) | 70 | | :i_month | Published month of post (without leading zeros) | 71 | | :day | Published day of post (2-digit) | 72 | | :i_day | Published day of post (without leading zeros) | 73 | | :slug | Slugified file path (without extension) | 74 | | :regular | Permalink generated by VuePress by default. See [fileToPath.ts](https://github.com/vuejs/vuepress/blob/master/packages/%40vuepress/shared-utils/src/fileToPath.ts) for details | 75 | -------------------------------------------------------------------------------- /packages/vuepress-theme-vt/global-components/VPLink.vue: -------------------------------------------------------------------------------- 1 | <template> 2 | <RouterLink 3 | v-if="isInternal" 4 | class="vp-link" 5 | :to="link" 6 | :exact="exact" 7 | @focusout.native="focusoutAction" 8 | > 9 | <slot name="before" /> 10 | {{ text }} 11 | <slot name="after" /> 12 | </RouterLink> 13 | <a 14 | v-else 15 | :href="link" 16 | class="vp-link external" 17 | :target="normalizedTarget" 18 | :rel="normalizedRel" 19 | @focusout="focusoutAction" 20 | > 21 | <slot name="before" /> 22 | {{ text }} 23 | <VPIconExternalLink v-if="isBlankTarget" /> 24 | <slot name="after" /> 25 | </a> 26 | </template> 27 | 28 | <script> 29 | import { isExternal, isMailto, isTel } from "../lib/util"; 30 | 31 | export default { 32 | name: "VPLink", 33 | 34 | props: { 35 | text: { 36 | type: String, 37 | required: true, 38 | }, 39 | link: { 40 | type: String, 41 | required: true, 42 | }, 43 | target: { 44 | type: String, 45 | }, 46 | rel: { 47 | type: String, 48 | }, 49 | }, 50 | 51 | computed: { 52 | exact() { 53 | if (this.$site.locales) { 54 | return Object.keys(this.$site.locales).some( 55 | (rootLink) => rootLink === this.link 56 | ); 57 | } 58 | return this.link === "/"; 59 | }, 60 | 61 | isNonHttpURI() { 62 | return isMailto(this.link) || isTel(this.link); 63 | }, 64 | 65 | isBlankTarget() { 66 | return this.target === "_blank"; 67 | }, 68 | 69 | isInternal() { 70 | return !isExternal(this.link) && !this.isBlankTarget; 71 | }, 72 | 73 | normalizedTarget() { 74 | if (this.isNonHttpURI) { 75 | return null; 76 | } 77 | if (this.target) { 78 | return this.target; 79 | } 80 | return isExternal(this.link) ? "_blank" : ""; 81 | }, 82 | 83 | normalizedRel() { 84 | if (this.isNonHttpURI) { 85 | return null; 86 | } 87 | if (this.rel === false) { 88 | return null; 89 | } 90 | if (this.rel) { 91 | return this.rel; 92 | } 93 | return this.isBlankTarget ? "noopener noreferrer" : null; 94 | }, 95 | }, 96 | 97 | methods: { 98 | focusoutAction() { 99 | this.$emit("focusout"); 100 | }, 101 | }, 102 | }; 103 | </script> 104 | -------------------------------------------------------------------------------- /packages/vuepress-theme-vt/src/types.ts: -------------------------------------------------------------------------------- 1 | /** @format */ 2 | 3 | import type { DefaultThemeConfig, NavItem } from "@vuepress/types"; 4 | 5 | export type EnhancedNavItem = NavItem & { 6 | /** 7 | * Specify the position of navbar item. 8 | * 9 | * @default "right" 10 | */ 11 | position?: "left" | "right"; 12 | }; 13 | 14 | export interface SidebarNavLink { 15 | /** 16 | * Nav link title 17 | */ 18 | title?: string; 19 | /** 20 | * When to display nav links (when current route match these routes conditions) 21 | */ 22 | include: string[]; 23 | /** 24 | * When to hidden nav links (only need it when you want to exclude some paths in "include".) 25 | */ 26 | exclude?: string[]; 27 | /** 28 | * Nav links config 29 | */ 30 | items: Array<{ 31 | /** 32 | * Nav link's text 33 | */ 34 | text: string; 35 | /** 36 | * Nav link's link, click behavior 37 | */ 38 | link: string; 39 | /** 40 | * Range route matcher for active behavior 41 | */ 42 | activeRange?: string | string[]; 43 | }>; 44 | } 45 | 46 | export type ThemeConfig = Omit<DefaultThemeConfig, "nav" | "locales"> & { 47 | /** 48 | * Locales config. 49 | */ 50 | locales?: Record<string, Omit<ThemeConfig, "locales">>; 51 | 52 | /** 53 | * Navbar Links. 54 | */ 55 | nav?: EnhancedNavItem[]; 56 | 57 | /** 58 | * Sidebar nav links. 59 | */ 60 | sidebarNav?: SidebarNavLink[]; 61 | 62 | /** 63 | * Status config, a plain text or a Vue component declaration ("e.g. <MyStatus />") 64 | */ 65 | status?: string; 66 | 67 | /** 68 | * Used to control status version, defaults to "v1". 69 | */ 70 | statusVersion?: string; 71 | 72 | /** 73 | * Enable dark mode 74 | * 75 | * @default false 76 | */ 77 | enableDarkMode?: boolean; 78 | /** 79 | * Transform document transformed by Google translate. 80 | * 81 | * @param content 82 | * @param sourceFile 83 | * @param targetFile 84 | */ 85 | transformTranslatedDocument?: ( 86 | content: string, 87 | sourceFile: string, 88 | targetFile: string 89 | ) => string; 90 | /** 91 | * Options for code switcher. 92 | */ 93 | codeSwitcher?: { 94 | groups?: Record<string, Record<string, string>>; 95 | }; 96 | /** 97 | * Scroll active sidebar link into view. 98 | */ 99 | sidebarActiveLinkScrollIntoView?: boolean; 100 | }; 101 | -------------------------------------------------------------------------------- /packages/docs/docs/guide/getting-started.md: -------------------------------------------------------------------------------- 1 | --- 2 | sidebarDepth: 0 3 | --- 4 | 5 | # Getting Started 6 | 7 | ## Prerequisites 8 | 9 | - [Node.js 10+](https://nodejs.org/en/) 10 | - [PNPM](https://pnpm.io/) (Optional)\* 11 | 12 | ## Quick Start 13 | 14 | The fastest way to use this theme is to use our [create-vt generator](https://github.com/vuepressjs/create-vuepress-site/), which will help scaffold a basic VuePress site with this theme for you. 15 | 16 | To use it, open up your terminal in the desired directory and run the following command: 17 | 18 | ```bash 19 | npm create vt@latest [optionalDirectoryName] 20 | ``` 21 | 22 | The command will interactively ask for details to configure your VuePress site’s metadata such as: 23 | 24 | - Project Name 25 | - Description 26 | - Maintainer Email 27 | - Maintainer Name 28 | 29 | To see it in action, navigate into newly scaffolded directory, install the dependencies and start the local server: 30 | 31 | ```bash 32 | pnpm run dev 33 | ``` 34 | 35 | ## Manual Installation 36 | 37 | If you prefer, you can build a basic VuePress documentation site from ground up instead of using the generator mentioned above. 38 | 39 | 1. Create and change into a new directory 40 | 41 | ```bash 42 | mkdir my-vt && cd my-vt 43 | ``` 44 | 45 | 2. Initialize with your preferred package manager 46 | 47 | ```bash 48 | pnpm init 49 | ``` 50 | 51 | 3. Install `vuepress-theme-vt` and `vuepress` locally 52 | 53 | ```bash 54 | pnpm i vuepress-theme-vt vuepress -D 55 | ``` 56 | 57 | 4. Create your first document 58 | 59 | ```bash 60 | mkdir docs && echo '# Hello VT' > docs/README.md 61 | ``` 62 | 63 | 5. Create config file and use this theme 64 | 65 | Creating [.vuepress/config.js](https://vuepress.vuejs.org/guide/basic-config.html) with following config: 66 | 67 | ```js 68 | // .vuepress/config.js 69 | module.exports = { 70 | theme: "vt", 71 | themeConfig: {}, 72 | }; 73 | ``` 74 | 75 | 5. Add npm scripts to `package.json` 76 | 77 | This step is optional but highly recommended, as the rest of the documentation will assume those scripts being present. 78 | 79 | ```json 80 | { 81 | "scripts": { 82 | "docs:dev": "vuepress dev docs", 83 | "docs:build": "vuepress build docs" 84 | } 85 | } 86 | ``` 87 | 88 | 6. Serve the documentation site in the local server 89 | 90 | ```bash 91 | npm run docs:dev 92 | ``` 93 | 94 | VuePress will start a hot-reloading development server at [http://localhost:8080](http://localhost:8080). 95 | 96 | By now, you should have a basic VuePress documentation site powered by VT. 97 | -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/plugin/using-a-plugin.md: -------------------------------------------------------------------------------- 1 | # Using a Plugin 2 | 3 | You can use plugins by doing some configuration at `.vuepress/config.js`: 4 | 5 | ``` js 6 | module.exports = { 7 | plugins: [ 8 | require('./my-plugin.js') 9 | ] 10 | } 11 | ``` 12 | 13 | ## Use plugins from a dependency 14 | 15 | A plugin can be published on npm in `CommonJS` format as `vuepress-plugin-xxx`. You can use it: 16 | 17 | ``` js 18 | module.exports = { 19 | plugins: [ 'vuepress-plugin-xxx' ] 20 | } 21 | ``` 22 | 23 | ## Plugin Shorthand 24 | 25 | If you prefix the plugin with `vuepress-plugin-`, you can use a shorthand to leave out that prefix: 26 | 27 | ``` js 28 | module.exports = { 29 | plugins: [ 'xxx' ] 30 | } 31 | ``` 32 | 33 | Same with: 34 | 35 | ``` js 36 | module.exports = { 37 | plugins: [ 'vuepress-plugin-xxx' ] 38 | } 39 | ``` 40 | 41 | This also works with [Scoped Packages](https://docs.npmjs.com/misc/scope): 42 | 43 | ``` js 44 | module.exports = { 45 | plugins: [ '@org/vuepress-plugin-xxx', '@vuepress/plugin-xxx' ] 46 | } 47 | ``` 48 | 49 | Shorthand: 50 | 51 | ``` js 52 | module.exports = { 53 | plugins: [ '@org/xxx', '@vuepress/xxx' ] 54 | } 55 | ``` 56 | 57 | ::: warning Note 58 | The plugin whose name starts with `@vuepress/plugin-` is an officially maintained plugin. 59 | ::: 60 | 61 | ## Plugin options 62 | 63 | ### Babel Style 64 | 65 | Plugins can have options specified by wrapping the name and an options object in an array inside your config: 66 | 67 | ``` js 68 | module.exports = { 69 | plugins: [ 70 | [ 71 | 'vuepress-plugin-xxx', 72 | { /* options */ } 73 | ] 74 | ] 75 | } 76 | ``` 77 | 78 | Since this style is consistent with [babel’s Plugin/Preset Options](https://babeljs.io/docs/en/plugins#plugin-preset-options), we call it `Babel Style`. 79 | 80 | ### Object Style 81 | 82 | VuePress also provides a simpler way to use plugins from a dependency: 83 | 84 | ``` js 85 | module.exports = { 86 | plugins: { 87 | 'xxx': { /* options */ } 88 | } 89 | } 90 | ``` 91 | 92 | ::: warning Note 93 | The plugin can be disabled when `false` is explicitly passed as option. 94 | 95 | - Babel style 96 | 97 | ``` js 98 | module.exports = { 99 | plugins: [ 100 | [ 'xxx', false ] // disabled. 101 | ] 102 | } 103 | ``` 104 | 105 | - Object style 106 | 107 | ``` js 108 | module.exports = { 109 | plugins: { 110 | 'xxx': false // disabled. 111 | } 112 | } 113 | ``` 114 | 115 | ::: 116 | -------------------------------------------------------------------------------- /packages/docs/docs/api/config-home.md: -------------------------------------------------------------------------------- 1 | --- 2 | pageClass: 'config-home' 3 | --- 4 | 5 | # Config: Home 6 | 7 | The following are all the frontmatter configurations for the [homepage](../guide/home.md). 8 | 9 | ## heroImage 10 | 11 | - **Type**: `string` 12 | - **Default**: `undefined` 13 | 14 | ::: tip 15 | In VT, for the style of the homepage, we do not recommend that you use this config, and this config is kept only for compatibility with [VuePress's Default Theme Config](https://vuepress.vuejs.org/theme/default-theme-config.html), 16 | ::: 17 | 18 | Config hero image. 19 | 20 | ```md 21 | --- 22 | heroImage: /logo.svg 23 | --- 24 | ``` 25 | 26 | ## actionText 27 | 28 | - **Type**: `string` 29 | - **Default**: `undefined` 30 | 31 | Main action button's text 32 | 33 | ```md 34 | --- 35 | actionText: Getting Started 36 | --- 37 | ``` 38 | 39 | ## actionLink 40 | 41 | - **Type**: `string` 42 | - **Default**: `undefined` 43 | 44 | Main action button's link 45 | 46 | ```md 47 | --- 48 | actionLink: /guide/ 49 | --- 50 | ``` 51 | 52 | ## subActionText 53 | 54 | - **Type**: `string` 55 | - **Default**: `undefined` 56 | 57 | Sub action button's text 58 | 59 | ```md 60 | --- 61 | subActionText: Install 62 | --- 63 | ``` 64 | 65 | ## subActionLink 66 | 67 | - **Type**: `string` 68 | - **Default**: `undefined` 69 | 70 | Sub action button's text 71 | 72 | ```md 73 | --- 74 | subActionLink: /guide/getting-started.html 75 | --- 76 | ``` 77 | 78 | ## features 79 | 80 | - **Type**: `array` 81 | - **Default**: `undefined` 82 | 83 | Features configurations, it's better to set **three or six items**: 84 | 85 | ```md 86 | --- 87 | features: 88 | - title: Full-text search 89 | details: Full-text search is supported by default, no server dependency, distinguishing locales. 90 | - title: Out of the box 91 | details: Compatible with VuePress' default theme, built-in common documentation features, e.g. i18n, Code Copy, TOC. 92 | - title: TypeScript 93 | details: It's easier to custom your own config with full TypeScript support. 94 | --- 95 | ``` 96 | 97 | ## sponsors 98 | 99 | - **Type**: `array` 100 | - **Default**: `undefined` 101 | 102 | ```md 103 | --- 104 | sponsors: 105 | - title: n8n.io 106 | img: https://avatars.githubusercontent.com/u/45487711?s=200&v=4 107 | link: https://n8n.io/ 108 | --- 109 | ``` 110 | 111 | ## sponsorsText 112 | 113 | - **Type**: `array` 114 | - **Default**: `'Special Sponsor'` 115 | 116 | Sponsor's intro text. 117 | -------------------------------------------------------------------------------- /packages/vuepress-theme-vt/components/SidebarLinks.vue: -------------------------------------------------------------------------------- 1 | <template> 2 | <ul v-if="items.length" class="sidebar-links"> 3 | <li v-for="(item, i) in items" :key="i"> 4 | <SidebarGroup 5 | v-if="item.type === 'group'" 6 | :item="item" 7 | :open="i === openGroupIndex" 8 | :collapsable="item.collapsable || item.collapsible" 9 | :depth="depth" 10 | @toggle="toggleGroup(i)" 11 | /> 12 | <SidebarLink v-else :sidebar-depth="sidebarDepth" :item="item" /> 13 | </li> 14 | </ul> 15 | </template> 16 | 17 | <script> 18 | import SidebarGroup from "@theme/components/SidebarGroup.vue"; 19 | import SidebarLink from "@theme/components/SidebarLink.vue"; 20 | import { isActive } from "../lib/util"; 21 | 22 | export default { 23 | name: "SidebarLinks", 24 | 25 | components: { SidebarGroup, SidebarLink }, 26 | 27 | props: [ 28 | "items", 29 | "depth", // depth of current sidebar links 30 | "sidebarDepth", // depth of headers to be extracted 31 | "initialOpenGroupIndex", 32 | ], 33 | 34 | data() { 35 | return { 36 | openGroupIndex: this.initialOpenGroupIndex || 0, 37 | }; 38 | }, 39 | 40 | watch: { 41 | $route() { 42 | this.refreshIndex(); 43 | }, 44 | }, 45 | 46 | created() { 47 | this.refreshIndex(); 48 | }, 49 | 50 | methods: { 51 | refreshIndex() { 52 | const index = resolveOpenGroupIndex(this.$route, this.items); 53 | if (index > -1) { 54 | this.openGroupIndex = index; 55 | } 56 | }, 57 | 58 | toggleGroup(index) { 59 | this.openGroupIndex = index === this.openGroupIndex ? -1 : index; 60 | }, 61 | 62 | isActive(page) { 63 | return isActive(this.$route, page.regularPath); 64 | }, 65 | }, 66 | }; 67 | 68 | function resolveOpenGroupIndex(route, items) { 69 | for (let i = 0; i < items.length; i++) { 70 | const item = items[i]; 71 | if (descendantIsActive(route, item)) { 72 | return i; 73 | } 74 | } 75 | return -1; 76 | } 77 | 78 | function descendantIsActive(route, item) { 79 | if (item.type === "group") { 80 | const childIsActive = item.path && isActive(route, item.path); 81 | const grandChildIsActive = item.children.some((child) => { 82 | if (child.type === "group") { 83 | return descendantIsActive(route, child); 84 | } else { 85 | return child.type === "page" && isActive(route, child.path); 86 | } 87 | }); 88 | 89 | return childIsActive || grandChildIsActive; 90 | } 91 | return false; 92 | } 93 | </script> 94 | -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/zh/miscellaneous/local-development.md: -------------------------------------------------------------------------------- 1 | --- 2 | sidebar: auto 3 | --- 4 | 5 | # 本地开发 6 | 7 | ## 摘要 8 | 9 | 如果你看到此处,你可能会对改进 VuePress 核心感兴趣。 10 | 11 | VuePress 正在使用包含了 [Yarn Workspaces](https://yarnpkg.com/zh-Hans/docs/workspaces/) 和 [Lerna](https://github.com/lerna/lerna) 的一个组合。 12 | 13 | ## 初始化 package 14 | 15 | ```bash 16 | yarn // 它将安装所有 package 的依赖 17 | ``` 18 | 19 | `yarn` 将使用 `hoist`。它对你意味着什么? 20 | 21 | 它将重组工作空间根目录中的所有依赖项并链接所有 package。 22 | 23 | 通过运行以下命令来检查链接: 24 | 25 | ```bash 26 | ls -la node_modules/@vuepress 27 | ``` 28 | 29 | ::: warning 30 | 你必须注意应在子文件夹的 package.json 中声明所有依赖项。如果未声明 package 的 dependencies,则在发布到 npm 时将无法正常工作。 31 | ::: 32 | 33 | ::: warning 34 | 你应该留意一个特殊的 package `@vuepress/shared-utils`,它是由 Typescript 编写的。 35 | ::: 36 | 37 | 安装完所有依赖后,它将运行 `yarn tsc` 。该命令将告诉 workspace 的 `@vuepress/shared-utils` 来编译他的 js。 38 | 39 | ::: warning 40 | 从这里开始,如果你要在此 package 中进行更改,则必须始终运行 `yarn tsc` 或在单独的终端中运行 `yarn run tsc -w` 。当检测到 shared-utils 有任何更改时,它将重新运行 tsc。 41 | ::: 42 | 43 | ## 链接 44 | 45 | 从这里开始就很不错了,你已经准备就绪。你需要将 VuePress 链接到你的项目。 46 | 47 | ```bash 48 | yarn register-vuepress 49 | ``` 50 | 51 | 你将看到类似这样的内容:`success Registered "vuepress".` 52 | 53 | 它将链接来自 `packages/vuepress` 的 VuePress 包。 你将可以访问 VuePress 脚手架和其他内部的 packages,他们在 `packages/vuepress/package.json` 被声明。 54 | 55 | ```js 56 | { 57 | "main": "index.js", 58 | /// 59 | "bin": { 60 | "vuepress": "cli.js" 61 | } 62 | /// 63 | } 64 | ``` 65 | 66 | 现在转到你的项目并运行 `yarn link vuepress`。 67 | 68 | 你应该得到 `success Using linked package for "vuepress".` 69 | 70 | ## 取消链接 71 | 72 | 你可能想要取消所有链接。在工作区根文件夹中,运行: 73 | 74 | ```bash 75 | yarn unregister-vuepress 76 | ``` 77 | 78 | 现在你可以在你的项目文件夹中运行 `yarn unlink vuepress` 。 79 | 80 | 如果一切运行正常,当你在你的项目文件夹中再次运行 `yarn link vuepress` ,你应该获得一个错误提示你找不到名为 vuepress 的软件包。 81 | 82 | ## BUGS / 问答 83 | 84 | 你可能会发现链接有些困难。如果你触发了一些类似 `There's already a package called "vuepress" registered` 之类的内容,你已经注册了 VuePress : 85 | 86 | - 如果你已经从[链接](#链接)链接了 VuePress ,就已经很好了。如果你进行更改,由于它是 symbolic link,你不必重新运行任何指令。只有当你更新 shared-utils 软件包时,才必须重新运行 `yarn tsc` ,仅此而已。 87 | - 如果你什么也没做。那么你已经将 VuePress 链接到某处。你要做的就是删除你运行 `yarn link` 或 `yarn unlink` 的文件夹。 88 | 89 | ## 更多相关 90 | 91 | 你可以使用更多有趣的命令: 92 | 93 | - `yarn packages:list` 将列出所有存在的 packages 及其版本 [更多](https://github.com/lerna/lerna/tree/master/commands/list#readme) 94 | - `yarn packages:changed` 会告诉你哪些 packages 将受到下一个 lerna 的 发布/版本 的影响 [更多](https://github.com/lerna/lerna/tree/master/commands/changed#readme) 95 | - `yarn packages:diff` 将显示上一个版本依赖所有差异 [更多](https://github.com/lerna/lerna/tree/master/commands/diff#readme) 96 | -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/guide/assets.md: -------------------------------------------------------------------------------- 1 | # Asset Handling 2 | 3 | ## Relative URLs 4 | 5 | All Markdown files are compiled into Vue components and processed by [webpack](http://webpack.js.org/). You can, **and should**, reference any assets using relative URLs: 6 | 7 | ``` md 8 | ![An image](./image.png) 9 | ``` 10 | 11 | This would work the same way as in `*.vue` file templates. The image will be processed with `url-loader` and `file-loader`, and copied to appropriate locations in the generated static build. 12 | 13 | You can also use the `~` prefix to explicitly specify this is a webpack module request, allowing you to reference files with webpack aliases or from npm dependencies: 14 | 15 | ``` md 16 | ![Image from alias](~@alias/image.png) 17 | ![Image from dependency](~some-dependency/image.png) 18 | ``` 19 | 20 | One alias that is added by default is `@source`, if you follow the recommended [Directory Structure](./directory-structure.md) this is the `docs` folder. 21 | 22 | ``` md 23 | ![Image from images folder](~@source/images/image.png) 24 | ``` 25 | 26 | Webpack aliases can be configured via [configureWebpack](../config/README.md#configurewebpack) in `.vuepress/config.js`. Example: 27 | 28 | ``` js 29 | module.exports = { 30 | configureWebpack: { 31 | resolve: { 32 | alias: { 33 | '@alias': 'path/to/some/dir' 34 | } 35 | } 36 | } 37 | } 38 | ``` 39 | 40 | ## Public Files 41 | 42 | Sometimes you may need to provide static assets that are not directly referenced in any of your Markdown or theme components (for example, favicons and PWA icons). In such cases, you can put them inside `.vuepress/public` and they will be copied to the root of the generated directory. 43 | 44 | ## Base URL 45 | 46 | If your site is deployed to a non-root URL, you will need to set the `base` option in `.vuepress/config.js`. For example, if you plan to deploy your site to `https://foo.github.io/bar/`, then `base` should be set to `"/bar/"` (it should always start and end with a slash). 47 | 48 | With a base URL, to reference an image in `.vuepress/public`, you’d have to use URLs like `/bar/image.png`. But this is brittle if you ever decide to change the `base`. To help with that, VuePress provides a built-in helper `$withBase` (injected onto Vue’s prototype) that generates the correct path: 49 | 50 | ``` vue 51 | <img :src="$withBase('/foo.png')" alt="foo"> 52 | ``` 53 | 54 | Note you can use the above syntax not only in theme components, but in your Markdown files as well. 55 | 56 | Also, if a `base` is set, it’s automatically prepended to all asset URLs in `.vuepress/config.js` options. 57 | -------------------------------------------------------------------------------- /packages/vuepress-theme-vt/styles/custom-blocks.styl: -------------------------------------------------------------------------------- 1 | .custom-block { 2 | margin: 28px 0; 3 | padding: 20px 24px 4px 42px; 4 | border-radius: 8px; 5 | overflow-x: auto; 6 | transition: color 0.5s, background-color 0.5s; 7 | position: relative; 8 | font-size: 14px; 9 | line-height: 1.6; 10 | font-weight: 500; 11 | color: rgba(0, 0, 0, 0.55); 12 | background-color: var(--vp-c-bg-soft); 13 | 14 | &:before { 15 | position: absolute; 16 | font-weight: 500; 17 | font-size: 15px; 18 | top: 20px; 19 | left: 17px; 20 | } 21 | } 22 | 23 | .dark .custom-block { 24 | color: var(--vp-c-text-2); 25 | } 26 | 27 | .custom-block.tip:before { 28 | content: 'ⓘ'; 29 | } 30 | 31 | .custom-block.warning:before, .custom-block.danger:before { 32 | content: '⚠'; 33 | font-size: 17px; 34 | top: 19px; 35 | left: 16ppx; 36 | } 37 | 38 | .custom-block .custom-block-title { 39 | margin-top: 0px; 40 | margin-bottom: 8px; 41 | font-size: 15px; 42 | font-weight: 500; 43 | color: var(--vp-c-text-1); 44 | transition: color 0.5s; 45 | } 46 | 47 | .custom-block.tip { 48 | border: 1px solid var(--vp-c-brand); 49 | } 50 | 51 | .custom-block.tip:before { 52 | color: var(--vp-c-brand); 53 | } 54 | 55 | .custom-block.warning { 56 | border: 1px solid var(--vp-c-yellow); 57 | } 58 | 59 | .custom-block.warning:before { 60 | color: var(--vp-c-yellow); 61 | } 62 | 63 | .custom-block.danger { 64 | border: 1px solid var(--vp-c-red); 65 | } 66 | 67 | .custom-block.danger .custom-block-title, .custom-block.danger:before { 68 | color: var(--vp-c-red); 69 | } 70 | 71 | .custom-block ul li:before { 72 | top: 0.55rem; 73 | } 74 | 75 | .custom-block ol li:before { 76 | top: 1px; 77 | font-size: 13px; 78 | } 79 | 80 | .custom-block :not(pre) > code { 81 | font-size: 13px; 82 | background-color: rgba(27, 31, 35, 0.05); 83 | } 84 | 85 | .dark .custom-block :not(pre) > code { 86 | background-color: rgba(0, 0, 0, 0.2); 87 | } 88 | 89 | .custom-block.danger a, .custom-block.warning a { 90 | color: var(--vp-c-text-code); 91 | } 92 | 93 | .custom-block.details { 94 | display: block; 95 | position: relative; 96 | border-radius: 2px; 97 | margin: 1.6em 0; 98 | padding: 1.6em; 99 | background-color: var(--vp-c-bg-soft); 100 | 101 | h4 { 102 | margin-top: 0; 103 | } 104 | 105 | figure, p { 106 | &:last-child { 107 | margin-bottom: 0; 108 | padding-bottom: 0; 109 | } 110 | } 111 | 112 | summary { 113 | outline: none; 114 | cursor: pointer; 115 | } 116 | } -------------------------------------------------------------------------------- /packages/vuepress-docs/docs/zh/guide/i18n.md: -------------------------------------------------------------------------------- 1 | # 多语言支持 2 | 3 | ## 站点多语言配置 4 | 5 | 要启用 VuePress 的多语言支持,首先需要使用如下的文件结构: 6 | 7 | ``` 8 | docs 9 | ├─ README.md 10 | ├─ foo.md 11 | ├─ nested 12 | │  └─ README.md 13 | └─ zh 14 | ├─ README.md 15 | ├─ foo.md 16 | └─ nested 17 |    └─ README.md 18 | ``` 19 | 20 | 然后,在 `.vuepress/config.js` 中提供 `locales` 选项: 21 | 22 | ``` js 23 | module.exports = { 24 | locales: { 25 | // 键名是该语言所属的子路径 26 | // 作为特例,默认语言可以使用 '/' 作为其路径。 27 | '/': { 28 | lang: 'en-US', // 将会被设置为 <html> 的 lang 属性 29 | title: 'VuePress', 30 | description: 'Vue-powered Static Site Generator' 31 | }, 32 | '/zh/': { 33 | lang: 'zh-CN', 34 | title: 'VuePress', 35 | description: 'Vue 驱动的静态网站生成器' 36 | } 37 | } 38 | } 39 | ``` 40 | 41 | 如果一个语言没有声明 `title` 或者 `description`,VuePress 将会尝试使用配置顶层的对应值。如果每个语言都声明了 `title` 和 `description`,则顶层的这两个值可以被省略。 42 | 43 | ## 默认主题多语言配置 44 | 45 | 默认主题也内置了多语言支持,可以通过 `themeConfig.locales` 来配置。该选项接受同样的 `{ path: config }` 格式的值。每个语言除了可以配置一些站点中用到的文字之外,还可以拥有自己的 [导航栏](../theme/default-theme-config.md#导航栏) 和 [侧边栏](../theme/default-theme-config.md#侧边栏) 配置: 46 | 47 | ``` js 48 | module.exports = { 49 | locales: { /* ... */ }, 50 | themeConfig: { 51 | locales: { 52 | '/': { 53 | selectText: 'Languages', 54 | label: 'English', 55 | ariaLabel: 'Languages', 56 | editLinkText: 'Edit this page on GitHub', 57 | serviceWorker: { 58 | updatePopup: { 59 | message: "New content is available.", 60 | buttonText: "Refresh" 61 | } 62 | }, 63 | algolia: {}, 64 | nav: [ 65 | { text: 'Nested', link: '/nested/', ariaLabel: 'Nested' } 66 | ], 67 | sidebar: { 68 | '/': [/* ... */], 69 | '/nested/': [/* ... */] 70 | } 71 | }, 72 | '/zh/': { 73 | // 多语言下拉菜单的标题 74 | selectText: '选择语言', 75 | // 该语言在下拉菜单中的标签 76 | label: '简体中文', 77 | // 编辑链接文字 78 | editLinkText: '在 GitHub 上编辑此页', 79 | // Service Worker 的配置 80 | serviceWorker: { 81 | updatePopup: { 82 | message: "发现新内容可用.", 83 | buttonText: "刷新" 84 | } 85 | }, 86 | // 当前 locale 的 algolia docsearch 选项 87 | algolia: {}, 88 | nav: [ 89 | { text: '嵌套', link: '/zh/nested/' } 90 | ], 91 | sidebar: { 92 | '/zh/': [/* ... */], 93 | '/zh/nested/': [/* ... */] 94 | } 95 | } 96 | } 97 | } 98 | } 99 | ``` 100 | --------------------------------------------------------------------------------