获取type-challenges
使用git,拉取type-challenges代码
git clone https://github.com/type-challenges/type-challenges
生成playground
npm run generate
将playground中的ts文件转成markdown
cd playground
npm init -y
npm install -D gulp gulp-rename through2
在package.json中的scripts添加
"build": "gulp"
在playground根目录下新建gulpfile.js。将下面内容复制到文件中:
const { src, dest } = require('gulp')
const rename = require('gulp-rename')
const through2 = require('through2')
exports.default = function () {
return src('./**/*.ts', { ignore: 'node_modules/**' })
.pipe(through2.obj(function (file, _, cb) {
if (file.isBuffer()) {
let content = file.contents.toString()
content = content.replace(/\/\*|\*\//g, '')
content = content.split(/_*\s*(?:Your Code Here|Test Cases|Further Steps)\s*_*/g)
let str = '# ' + content[0].replace(/(Parameters|Intersection|MutableKeys|PercentageParser|Unique|DeepMutable)<T/g, '$1<T').replace(/^[\s\r\n]+/, '')
str += '\r\n\r\n### Answer\r\n' + ('```ts\r\n' + content[1] + '\r\n```').replace(/^\s*$(?:\n|\r\n)/mg, '')
file.contents = Buffer.from(str)
}
cb(null, file)
}))
.pipe(rename({ extname: '.md' }))
.pipe(dest('../dist/docs'))
}
运行命令在上级目录生成dist文件夹。
生成网站
切换到dist目录
npm init -y
npm install -D vitepress
npx vitepress init
// Theme 选择 Default Theme + Customization
npm install -D vite-plugin-vitepress-auto-sidebar vue
在.vitepress/theme新建compponents/HeroPage.vue。文件内容:
<script setup lang="ts">
import { defineOptions } from "vue";
defineOptions({ name: "HeroPage" });
</script>
<template>
<main class="hero-page-wrapper">
<div class="content">
<a href="https://github.com/type-challenges/type-challenges">
<img src="/logo.svg" width="500" alt="type-challenges" />
</a>
<div>
<h1>Collection of TypeScript type challenges with online judge</h1>
<p>
<a href="/warm/00013-warm-hello-world.html" class="button"> 快速开始 </a>
</p>
</div>
</div>
</main>
</template>
<style scoped>
.hero-page-wrapper {
position: fixed;
top: 50%;
left: 50%;
transform: translate(-50%, -50%);
}
.content {
justify-content: center;
align-items: center;
width: 100%;
margin-bottom: 5rem;
text-align: center;
}
div {
text-align: center;
}
h1 {
font-weight: 400;
margin: 0;
font-size: 1.5em;
color: #273849;
opacity: 0.7;
}
a img {
margin: 0 auto;
}
a.button {
padding: 0.75em 2em;
border-radius: 2em;
display: inline-block;
color: #fff;
background-color: #304455;
transition: all 0.15s ease;
box-sizing: border-box;
border: 1px solid #304455;
text-decoration: none;
margin: 2em 0;
font-size: 0.9em;
font-weight: 600;
letter-spacing: 0.1em;
min-width: 8em;
text-align: center;
text-transform: uppercase;
}
</style>
修改theme/index.ts,注册HeroPage组件:
enhanceApp({ app, router, siteData }) {
app.component(HeroPage.name, HeroPage);
}
修改.vitepress/config.mts:
import { defineConfig } from 'vitepress'
// @ts-ignore
import AutoSidebar from 'vite-plugin-vitepress-auto-sidebar'
// https://vitepress.dev/reference/site-config
export default defineConfig({
base: '/',
srcDir: './docs',
outDir: './.vitepress/tsch',
title: 'Tsch',
lang: 'zh-CN',
description: "type-challenges ",
lastUpdated: true,
cleanUrls: false,
metaChunk: true,
head: [
['meta', { name: 'theme-color', content: '#5f67ee' }],
['meta', { property: 'og:type', content: 'website' }],
['meta', { property: 'og:locale', content: 'zh' }]
],
themeConfig: {
// https://vitepress.dev/reference/default-theme-config
nav: [
{ text: 'Home', link: '/' },
{ text: 'Warm', link: '/warm/00013-warm-hello-world' },
{ text: 'Easy', link: '/easy/00004-easy-pick' },
{ text: 'Medium', link: '/medium/00002-medium-get-return-type' },
{ text: 'Hard', link: '/hard/00006-hard-simple-vue' },
{ text: 'Extreme', link: '/extreme/00005-extreme-get-readonly-keys' }
],
sidebar: [
{
text: 'Examples',
items: [
{ text: 'Markdown Examples', link: '/markdown-examples' },
{ text: 'Runtime API Examples', link: '/api-examples' }
]
}
],
socialLinks: [
{ icon: 'github', link: 'https://github.com/vuejs/vitepress' }
],
outline: false,
search: {
provider: 'local'
}
},
vite: {
plugins: [
// add plugin
AutoSidebar({
path: '/docs',
ignoreList: ['node_modules', 'public'],
sideBarResolved: (data) => Object.entries(data).reduce((p, [k, v]) => {
return {
...p,
// @ts-ignore
[k]: v.map((s) => ({
items: [...s.items]
.sort((a, b) => a.text.split('-')[0] - (b.text).split('-')[0])
.map(s => ({ text: s.text.replace(new RegExp('\\d+\\-[A-Za-z]+\\-', 'g'), ''), link: s.link }))
}))
}
}, {})
})
]
}
})
新建或者修改docs/index.md:
---
layout: page
---
<HeroPage />
最后,将type-challenges的logo.svg复制到docs/public。