diff --git a/docs/guide/markdown.md b/docs/guide/markdown.md index 3756235d..8c9fb44e 100644 --- a/docs/guide/markdown.md +++ b/docs/guide/markdown.md @@ -80,7 +80,7 @@ For more details, see [Frontmatter](../reference/frontmatter-config). **Input** -``` +```md | Tables | Are | Cool | | ------------- | :-----------: | ----: | | col 3 is | right-aligned | $1600 | @@ -265,7 +265,7 @@ Wraps in a
## Syntax Highlighting in Code Blocks -VitePress uses [Shiki](https://shiki.matsu.io/) to highlight language syntax in Markdown code blocks, using coloured text. Shiki supports a wide variety of programming languages. All you need to do is append a valid language alias to the beginning backticks for the code block: +VitePress uses [Shikiji](https://github.com/antfu/shikiji) (an improved version of [Shiki](https://shiki.matsu.io/)) to highlight language syntax in Markdown code blocks, using coloured text. Shiki supports a wide variety of programming languages. All you need to do is append a valid language alias to the beginning backticks for the code block: **Input** diff --git a/docs/reference/site-config.md b/docs/reference/site-config.md index c6838c50..a5386f57 100644 --- a/docs/reference/site-config.md +++ b/docs/reference/site-config.md @@ -454,7 +454,7 @@ When using the default theme, enabling this option will display each page's last - Type: `MarkdownOption` -Configure Markdown parser options. VitePress uses [Markdown-it](https://github.com/markdown-it/markdown-it) as the parser, and [Shiki](https://shiki.matsu.io/) to highlight language syntax. Inside this option, you may pass various Markdown related options to fit your needs. +Configure Markdown parser options. VitePress uses [Markdown-it](https://github.com/markdown-it/markdown-it) as the parser, and [Shikiji](https://github.com/antfu/shikiji) (an improved version of [Shiki](https://shiki.matsu.io/)) to highlight language syntax. Inside this option, you may pass various Markdown related options to fit your needs. ```js export default { @@ -472,15 +472,19 @@ interface MarkdownOptions extends MarkdownIt.Options { // Or add your own theme. // See: https://github.com/shikijs/shiki/blob/main/docs/themes.md#loading-theme theme?: - | Shiki.IThemeRegistration - | { light: Shiki.IThemeRegistration; dark: Shiki.IThemeRegistration } + | Shikiji.BuiltInTheme + | Shikiji.ThemeRegistration + | { + light: Shikiji.BuiltInTheme | Shikiji.ThemeRegistration; + dark: Shikiji.BuiltInTheme | Shikiji.ThemeRegistration + } // Enable line numbers in code block. lineNumbers?: boolean // Add support for your own languages. // https://github.com/shikijs/shiki/blob/main/docs/languages.md#supporting-your-own-languages-with-shiki - languages?: Shiki.ILanguageRegistration[] + languages?: (Shikiji.BuiltInLanguage | Shikiji.LanguageRegistration)[] // markdown-it-anchor plugin options. // See: https://github.com/valeriangalliat/markdown-it-anchor#usage diff --git a/package.json b/package.json index 61bfb544..0b3490a7 100644 --- a/package.json +++ b/package.json @@ -101,7 +101,8 @@ "mark.js": "8.11.1", "minisearch": "^6.2.0", "mrmime": "^1.0.1", - "shiki": "^0.14.5", + "shikiji": "^0.7.0-beta.0", + "shikiji-transformers": "^0.7.0-beta.0", "vite": "^5.0.0", "vue": "^3.3.8" }, @@ -187,7 +188,6 @@ "rollup-plugin-dts": "^6.1.0", "rollup-plugin-esbuild": "^6.1.0", "semver": "^7.5.4", - "shiki-processor": "^0.1.3", "simple-git-hooks": "^2.9.0", "sirv": "^2.0.3", "sitemap": "^7.1.1", diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index f8016659..316b9482 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -44,9 +44,12 @@ importers: mrmime: specifier: ^1.0.1 version: 1.0.1 - shiki: - specifier: ^0.14.5 - version: 0.14.5 + shikiji: + specifier: ^0.7.0-beta.0 + version: 0.7.0-beta.0 + shikiji-transformers: + specifier: ^0.7.0-beta.0 + version: 0.7.0-beta.0 vite: specifier: ^5.0.0 version: 5.0.0(@types/node@20.9.1) @@ -261,9 +264,6 @@ importers: semver: specifier: ^7.5.4 version: 7.5.4 - shiki-processor: - specifier: ^0.1.3 - version: 0.1.3(shiki@0.14.5) simple-git-hooks: specifier: ^2.9.0 version: 2.9.0 @@ -1121,6 +1121,12 @@ packages: '@types/node': 20.9.1 dev: true + /@types/hast@3.0.3: + resolution: {integrity: sha512-2fYGlaDy/qyLlhidX42wAH0KBi2TCjKMH8CHmBXgRlJ3Y+OXTiqsPQ6IWarZKwF1JoUcAJdPogv1d4b0COTpmQ==} + dependencies: + '@types/unist': 3.0.2 + dev: false + /@types/http-errors@2.0.4: resolution: {integrity: sha512-D0CFMMtydbJAegzOyHjtiKPLlvnm3iTZyZRSZoLq2mRhDdmLfIWOCYPfQJ4cu2erKghU++QvjcUjp/5h7hESpA==} dev: true @@ -1180,6 +1186,12 @@ packages: '@types/linkify-it': 3.0.5 '@types/mdurl': 1.0.5 + /@types/mdast@4.0.3: + resolution: {integrity: sha512-LsjtqsyF+d2/yFOYaN22dHZI1Cpwkrj+g06G8+qtUKlhovPW89YhqSnfKtMbkgmEtYpH2gydRNULd6y8mciAFg==} + dependencies: + '@types/unist': 3.0.2 + dev: false + /@types/mdurl@1.0.5: resolution: {integrity: sha512-6L6VymKTzYSrEf4Nev4Xa1LCHKrlTlYCBMTlQKFuddo1CvQcE52I0mwfOJayueUC7MJuXOeHTcIU683lzd0cUA==} @@ -1268,10 +1280,18 @@ packages: resolution: {integrity: sha512-m04Om5Gz6kbjUwAQ7XJJQ30OdEFsSmAVsvn4NYwcTRyMVpKKa1aPuESw1n2CxS5fYkOQv3nHgDKeNa8e76fUkw==} dev: true + /@types/unist@3.0.2: + resolution: {integrity: sha512-dqId9J8K/vGi5Zr7oo212BGii5m3q5Hxlkwy3WpYuKPklmBEvsbMYYyLxAQpSffdLl/gdW0XUpKWFvYmyoWCoQ==} + dev: false + /@types/web-bluetooth@0.0.20: resolution: {integrity: sha512-g9gZnnXVq7gM7v3tJCWV/qw7w+KeOlSHAhgF9RytFyifW6AF61hdT2ucrYhPq9hLs5JIryeupHV3qGk95dH9ow==} dev: false + /@ungap/structured-clone@1.2.0: + resolution: {integrity: sha512-zuVdFrMJiuCDQUMCzQaD6KL28MjnqqN8XnAqiEq9PNm/hCPTSGfrXCOfwj1ow4LFb/tNymJPwsNbVePc1xFqrQ==} + dev: false + /@vitejs/plugin-vue@4.5.0(vite@5.0.0)(vue@3.3.8): resolution: {integrity: sha512-a2WSpP8X8HTEww/U00bU4mX1QpLINNuz/2KMNpLsdu3BzOpak3AGI1CJYBTXcc4SPhaD0eNRUp7IyQK405L5dQ==} engines: {node: ^14.18.0 || >=16.0.0} @@ -1590,9 +1610,6 @@ packages: engines: {node: '>=12'} dev: true - /ansi-sequence-parser@1.1.1: - resolution: {integrity: sha512-vJXt3yiaUL4UU546s3rPXlsry/RnM730G1+HkpKE012AN0sx1eOrxSu95oKDIonskeLTijMgqWZ3uDEe3NFvyg==} - /ansi-styles@3.2.1: resolution: {integrity: sha512-VT0ZI6kZRdTh8YyJw3SMbYm/u+NqfsAxEpWO0Pf9sq8/e94WxxOpPKx9FR1FlyCtOVDNOQ+8ntlqFxiRc+r5qA==} engines: {node: '>=4'} @@ -1761,6 +1778,10 @@ packages: set-function-length: 1.1.1 dev: true + /ccount@2.0.1: + resolution: {integrity: sha512-eyrF0jiFpY+3drT6383f1qhkbGsLSifNAjA61IUjZjmLCWjItY6LB9ft9YhoDgwfmclB2zhu51Lc7+95b8NRAg==} + dev: false + /chai@4.3.10: resolution: {integrity: sha512-0UXG04VuVbruMUYbJ6JctvH0YnC/4q3/AkT18q4NaITo91CUm0liMS9VqzT9vZhVQ/1eqPanMWjBM+Juhfb/9g==} engines: {node: '>=4'} @@ -1788,6 +1809,14 @@ packages: engines: {node: ^12.17.0 || ^14.13 || >=16.0.0} dev: true + /character-entities-html4@2.1.0: + resolution: {integrity: sha512-1v7fgQRj6hnSwFpq1Eu0ynr/CDEw0rXo2B61qXrLNdHZmPKgb7fqS1a2JwF0rISo9q77jDI8VMEHoApn8qDoZA==} + dev: false + + /character-entities-legacy@3.0.0: + resolution: {integrity: sha512-RpPp0asT/6ufRm//AJVwpViZbGM/MkjQFxJccQRHmISF/22NBtsHqAWmL+/pmkPWoIUJdWyeVleTl1wydHATVQ==} + dev: false + /check-error@1.0.3: resolution: {integrity: sha512-iKEoDYaRmd1mxM90a2OEfWhjsjPpYPuQ+lMYsoxB126+t8fw7ySEO48nmDg5COTjxDI65/Y2OWpeEHk3ZOe8zg==} dependencies: @@ -1884,6 +1913,10 @@ packages: delayed-stream: 1.0.0 dev: true + /comma-separated-tokens@2.0.3: + resolution: {integrity: sha512-Fu4hJdvzeylCfQPp9SGWidpzrMs7tTrlu6Vb8XGaRGck8QSNZJJp538Wrb60Lax4fPwR64ViY468OIUTbRlGZg==} + dev: false + /commander@11.1.0: resolution: {integrity: sha512-yPVavfyCcRhmorC7rWlkHn15b4wDVgVmBA7kV4QVBsF7kv/9TKJAbAXVTxvTnwP8HHKjRCJDClKbciiYS7p0DQ==} engines: {node: '>=16'} @@ -2177,6 +2210,17 @@ packages: engines: {node: '>=0.4.0'} dev: true + /dequal@2.0.3: + resolution: {integrity: sha512-0je+qPKHEMohvfRTCEo3CrPG6cAzAYgmzKyxRiYSSDkS6eGJdyVJm7WaYA5ECaAD9wLB2T4EEeymA5aFVcYXCA==} + engines: {node: '>=6'} + dev: false + + /devlop@1.1.0: + resolution: {integrity: sha512-RWmIqhcFf1lRYBvNmr7qTNuyCt/7/ns2jbpp1+PalgE/rDQcBT0fioSMUpJ93irlUhC5hrg4cYqe6U+0ImW0rA==} + dependencies: + dequal: 2.0.3 + dev: false + /diff-sequences@29.6.3: resolution: {integrity: sha512-EjePK1srD3P08o2j4f0ExnylqRs5B9tJjcp9t1krH2qRi8CCdsYfwe9JgSLurFBWwq4uOlipzfk5fHNvwFKr8Q==} engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0} @@ -2244,6 +2288,11 @@ packages: engines: {node: '>=0.12'} dev: true + /entities@4.5.0: + resolution: {integrity: sha512-V0hjH4dGPh9Ao5p0MoRY6BVqtwCjhz6vI5LT8AJ55H+4g9/4vbHx1I54fS0XuclLhDHArPQCiMjDxjaL8fPxhw==} + engines: {node: '>=0.12'} + dev: false + /error-ex@1.3.2: resolution: {integrity: sha512-7dFHNmqeFSEt2ZBsCriorKnn3Z2pj+fd9kmI6QoWw4//DL+icEBfc0U7qJCisqrTsKTjw4fNFy2pW9OqStD84g==} dependencies: @@ -2681,6 +2730,88 @@ packages: function-bind: 1.1.2 dev: true + /hast-util-from-parse5@8.0.1: + resolution: {integrity: sha512-Er/Iixbc7IEa7r/XLtuG52zoqn/b3Xng/w6aZQ0xGVxzhw5xUFxcRqdPzP6yFi/4HBYRaifaI5fQ1RH8n0ZeOQ==} + dependencies: + '@types/hast': 3.0.3 + '@types/unist': 3.0.2 + devlop: 1.1.0 + hastscript: 8.0.0 + property-information: 6.4.0 + vfile: 6.0.1 + vfile-location: 5.0.2 + web-namespaces: 2.0.1 + dev: false + + /hast-util-parse-selector@4.0.0: + resolution: {integrity: sha512-wkQCkSYoOGCRKERFWcxMVMOcYE2K1AaNLU8DXS9arxnLOUEWbOXKXiJUNzEpqZ3JOKpnha3jkFrumEjVliDe7A==} + dependencies: + '@types/hast': 3.0.3 + dev: false + + /hast-util-raw@9.0.1: + resolution: {integrity: sha512-5m1gmba658Q+lO5uqL5YNGQWeh1MYWZbZmWrM5lncdcuiXuo5E2HT/CIOp0rLF8ksfSwiCVJ3twlgVRyTGThGA==} + dependencies: + '@types/hast': 3.0.3 + '@types/unist': 3.0.2 + '@ungap/structured-clone': 1.2.0 + hast-util-from-parse5: 8.0.1 + hast-util-to-parse5: 8.0.0 + html-void-elements: 3.0.0 + mdast-util-to-hast: 13.0.2 + parse5: 7.1.2 + unist-util-position: 5.0.0 + unist-util-visit: 5.0.0 + vfile: 6.0.1 + web-namespaces: 2.0.1 + zwitch: 2.0.4 + dev: false + + /hast-util-to-html@9.0.0: + resolution: {integrity: sha512-IVGhNgg7vANuUA2XKrT6sOIIPgaYZnmLx3l/CCOAK0PtgfoHrZwX7jCSYyFxHTrGmC6S9q8aQQekjp4JPZF+cw==} + dependencies: + '@types/hast': 3.0.3 + '@types/unist': 3.0.2 + ccount: 2.0.1 + comma-separated-tokens: 2.0.3 + hast-util-raw: 9.0.1 + hast-util-whitespace: 3.0.0 + html-void-elements: 3.0.0 + mdast-util-to-hast: 13.0.2 + property-information: 6.4.0 + space-separated-tokens: 2.0.2 + stringify-entities: 4.0.3 + zwitch: 2.0.4 + dev: false + + /hast-util-to-parse5@8.0.0: + resolution: {integrity: sha512-3KKrV5ZVI8if87DVSi1vDeByYrkGzg4mEfeu4alwgmmIeARiBLKCZS2uw5Gb6nU9x9Yufyj3iudm6i7nl52PFw==} + dependencies: + '@types/hast': 3.0.3 + comma-separated-tokens: 2.0.3 + devlop: 1.1.0 + property-information: 6.4.0 + space-separated-tokens: 2.0.2 + web-namespaces: 2.0.1 + zwitch: 2.0.4 + dev: false + + /hast-util-whitespace@3.0.0: + resolution: {integrity: sha512-88JUN06ipLwsnv+dVn+OIYOvAuvBMy/Qoi6O7mQHxdPXpjy+Cd6xRkWwux7DKO+4sYILtLBRIKgsdpS2gQc7qw==} + dependencies: + '@types/hast': 3.0.3 + dev: false + + /hastscript@8.0.0: + resolution: {integrity: sha512-dMOtzCEd3ABUeSIISmrETiKuyydk1w0pa+gE/uormcTpSYuaNJPbX1NU3JLyscSLjwAQM8bWMhhIlnCqnRvDTw==} + dependencies: + '@types/hast': 3.0.3 + comma-separated-tokens: 2.0.3 + hast-util-parse-selector: 4.0.0 + property-information: 6.4.0 + space-separated-tokens: 2.0.2 + dev: false + /he@1.2.0: resolution: {integrity: sha512-F/1DnUGPopORZi0ni+CvrCgHQ5FyEAHRLSApuYWMmrbSwoN2Mn/7k+Gl38gJnR7yyDZk6WLXwiGod1JOWNDKGw==} hasBin: true @@ -2697,6 +2828,10 @@ packages: lru-cache: 10.0.2 dev: true + /html-void-elements@3.0.0: + resolution: {integrity: sha512-bEqo66MRXsUGxWHV5IP0PUiAWwoEjba4VCzg0LjFJBpchPaTfyfCKTG6bc5F8ucKec3q5y6qOdGyYTSBEvhCrg==} + dev: false + /htmlparser2@5.0.1: resolution: {integrity: sha512-vKZZra6CSe9qsJzh0BjBGXo8dvzNsq/oGvsjfRdOrrryfeD9UOBEEQdeoqCRmKZchF5h2zOBMQ6YuQ0uRUmdbQ==} dependencies: @@ -2979,6 +3114,7 @@ packages: /jsonc-parser@3.2.0: resolution: {integrity: sha512-gfFQZrcTc8CnKXp6Y4/CBT3fTc0OVuDofpre4aEeEpSBPV5X5v4+Vmx+8snU7RLPrNHPKSgLxGo9YuQzz20o+w==} + dev: true /jsonfile@6.1.0: resolution: {integrity: sha512-5dgndWOriYSm5cnYaJNhalLNDKOqFwyDB/rr1E9ZsGciGvKPs8R2xYGCacuf3z6K1YKDz182fd+fY3cn3pMqXQ==} @@ -3215,6 +3351,19 @@ packages: speech-rule-engine: 4.0.7 dev: true + /mdast-util-to-hast@13.0.2: + resolution: {integrity: sha512-U5I+500EOOw9e3ZrclN3Is3fRpw8c19SMyNZlZ2IS+7vLsNzb2Om11VpIVOR+/0137GhZsFEF6YiKD5+0Hr2Og==} + dependencies: + '@types/hast': 3.0.3 + '@types/mdast': 4.0.3 + '@ungap/structured-clone': 1.2.0 + devlop: 1.1.0 + micromark-util-sanitize-uri: 2.0.0 + trim-lines: 3.0.1 + unist-util-position: 5.0.0 + unist-util-visit: 5.0.0 + dev: false + /mdurl@1.0.1: resolution: {integrity: sha512-/sKlQJCBYVY9Ers9hqzKou4H6V5UWc/M59TH2dvkt+84itfnq7uFOMLpOiOS4ujvHP4etln18fmIxA5R5fll0g==} dev: true @@ -3246,6 +3395,33 @@ packages: resolution: {integrity: sha512-kYmyrCirqJf3zZ9t/0wGgRZ4/ZJw//VwaRVGA75C4nhE60vtnIzhl9J9ndkX/h6hxSN7pjg/cE0VxbnNM+bnDQ==} dev: true + /micromark-util-character@2.0.1: + resolution: {integrity: sha512-3wgnrmEAJ4T+mGXAUfMvMAbxU9RDG43XmGce4j6CwPtVxB3vfwXSZ6KhFwDzZ3mZHhmPimMAXg71veiBGzeAZw==} + dependencies: + micromark-util-symbol: 2.0.0 + micromark-util-types: 2.0.0 + dev: false + + /micromark-util-encode@2.0.0: + resolution: {integrity: sha512-pS+ROfCXAGLWCOc8egcBvT0kf27GoWMqtdarNfDcjb6YLuV5cM3ioG45Ys2qOVqeqSbjaKg72vU+Wby3eddPsA==} + dev: false + + /micromark-util-sanitize-uri@2.0.0: + resolution: {integrity: sha512-WhYv5UEcZrbAtlsnPuChHUAsu/iBPOVaEVsntLBIdpibO0ddy8OzavZz3iL2xVvBZOpolujSliP65Kq0/7KIYw==} + dependencies: + micromark-util-character: 2.0.1 + micromark-util-encode: 2.0.0 + micromark-util-symbol: 2.0.0 + dev: false + + /micromark-util-symbol@2.0.0: + resolution: {integrity: sha512-8JZt9ElZ5kyTnO94muPxIGS8oyElRJaiJO8EzV6ZSyGQ1Is8xwl4Q45qU5UOg+bGH4AikWziz0iN4sFLWs8PGw==} + dev: false + + /micromark-util-types@2.0.0: + resolution: {integrity: sha512-oNh6S2WMHWRZrmutsRmDDfkzKtxF+bc2VxLC9dvtrDIRFln627VsFP6fLMgTryGDljgLPjkrzQSDcPrjPyDJ5w==} + dev: false + /micromatch@4.0.5: resolution: {integrity: sha512-DMy+ERcEW2q8Z2Po+WNXuw3c5YaUSFjAO5GsJqfEl7UjvtIuFKO6ZrKvcItdy98dwFI2N1tg3zNIdKaQT+aNdA==} engines: {node: '>=8.6'} @@ -3542,6 +3718,12 @@ packages: resolution: {integrity: sha512-Ofn/CTFzRGTTxwpNEs9PP93gXShHcTq255nzRYSKe8AkVpZY7e1fpmTfOyoIvjP5HG7Z2ZM7VS9PPhQGW2pOpw==} dev: true + /parse5@7.1.2: + resolution: {integrity: sha512-Czj1WaSVpaoj0wbhMzLmWD69anp2WH7FXMB9n1Sy8/ZFF9jolSQVMu1Ij5WIyGmcBmhk7EOndpO4mIpihVqAXw==} + dependencies: + entities: 4.5.0 + dev: false + /path-browserify@1.0.1: resolution: {integrity: sha512-b7uo2UCUOYZcnF/3ID0lulOJi/bafxa1xPe7ZPsammBSpjSWQkjNxlt635YGS2MiR9GjvuXCtz2emr3jbsz98g==} dev: true @@ -3704,6 +3886,10 @@ packages: sisteransi: 1.0.5 dev: true + /property-information@6.4.0: + resolution: {integrity: sha512-9t5qARVofg2xQqKtytzt+lZ4d1Qvj8t5B8fEwXK6qOfgRLgH/b13QlgEyDh033NOS31nXeFbYv7CLUDG1CeifQ==} + dev: false + /proxy-from-env@1.1.0: resolution: {integrity: sha512-D+zkORCbA9f1tdWRK0RaCR3GPv50cMxcrz4X8k5LTSUD1Dkw47mKJEZQNunItRTkWwgtaUSo1RVFRIG9ZXiFYg==} dev: true @@ -3977,21 +4163,17 @@ packages: resolution: {integrity: sha512-6j1W9l1iAs/4xYBI1SYOVZyFcCis9b4KCLQ8fgAGG07QvzaRLVVRQvAy85yNmmZSjYjg4MWh4gNvlPujU/5LpA==} dev: true - /shiki-processor@0.1.3(shiki@0.14.5): - resolution: {integrity: sha512-oZqVFKweklwt+fj6yUPb+ffrCpYYoJ4RYxNt7w1+aoHetHq5ZaN6oX6+4HrypOi0s/O6A2neBpn+Xf6bM4KfsQ==} - peerDependencies: - shiki: 0.x + /shikiji-transformers@0.7.0-beta.0: + resolution: {integrity: sha512-+OnswF5j56004W39YZUB2sR/joUX+TRVgKqtx0T5bkb8E+QJH7FLkv3jUHLtSrYHfPMV1d3jd948TjVwQTbU5w==} dependencies: - shiki: 0.14.5 - dev: true + shikiji: 0.7.0-beta.0 + dev: false - /shiki@0.14.5: - resolution: {integrity: sha512-1gCAYOcmCFONmErGTrS1fjzJLA7MGZmKzrBNX7apqSwhyITJg2O102uFzXUeBxNnEkDA9vHIKLyeKq0V083vIw==} + /shikiji@0.7.0-beta.0: + resolution: {integrity: sha512-IfKmgxCxwFWJykS+kI1Hj9QvzszYic64Vqyk+gBTNrD6lVXoayKjc7zPLDFswJLAVZy1F50iYLnAjBGGb5s17Q==} dependencies: - ansi-sequence-parser: 1.1.1 - jsonc-parser: 3.2.0 - vscode-oniguruma: 1.7.0 - vscode-textmate: 8.0.0 + hast-util-to-html: 9.0.0 + dev: false /side-channel@1.0.4: resolution: {integrity: sha512-q5XPytqFEIKHkGdiMIrY10mvLRvnQh42/+GoBlFW3b2LXLE2xxJpZFdm94we0BaoV3RwJyGqg5wS7epxTv0Zvw==} @@ -4070,6 +4252,10 @@ packages: engines: {node: '>=0.10.0'} dev: true + /space-separated-tokens@2.0.2: + resolution: {integrity: sha512-PEGlAwrG8yXGXRjW32fGbg66JAlOAwbObuqVoJpv/mRgoWDQfgH1wDPvtzWyUSNAXBGSk8h755YDbbcEy3SH2Q==} + dev: false + /spdx-correct@3.2.0: resolution: {integrity: sha512-kN9dJbvnySHULIluDHy32WHRUu3Og7B9sbY7tsFLctQkIqnMh3hErYgdMjTYuqmcXX+lK5T1lnUt3G7zNswmZA==} dependencies: @@ -4188,6 +4374,13 @@ packages: safe-buffer: 5.2.1 dev: true + /stringify-entities@4.0.3: + resolution: {integrity: sha512-BP9nNHMhhfcMbiuQKCqMjhDP5yBCAxsPu4pHFFzJ6Alo9dZgY4VLDPutXqIjpRiMoKdp7Av85Gr73Q5uH9k7+g==} + dependencies: + character-entities-html4: 2.1.0 + character-entities-legacy: 3.0.0 + dev: false + /strip-ansi@6.0.1: resolution: {integrity: sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A==} engines: {node: '>=8'} @@ -4299,6 +4492,10 @@ packages: resolution: {integrity: sha512-N3WMsuqV66lT30CrXNbEjx4GEwlow3v6rr4mCcv6prnfwhS01rkgyFdjPNBYd9br7LpXV1+Emh01fHnq2Gdgrw==} dev: true + /trim-lines@3.0.1: + resolution: {integrity: sha512-kRj8B+YHZCc9kQYdWfJB2/oUl9rA99qbowYYBtr4ui4mZyAQ2JpvVBd/6U2YloATfqBhBTSMhTpgBHtU0Mf3Rg==} + dev: false + /trouter@3.2.1: resolution: {integrity: sha512-oY3CmIiEYOe1YMEzh++I67lrNOUldtCeuLL0vRPydvQLHZpSJ03B5dgDFlpFsiriMq6e//NDjjopjUzXOztHow==} engines: {node: '>=6'} @@ -4401,6 +4598,39 @@ packages: /undici-types@5.26.5: resolution: {integrity: sha512-JlCMO+ehdEIKqlFxk6IfVoAUVmgz7cU7zD/h9XZ0qzeosSHmUJVOzSQvvYSYWXkFXC+IfLKSIffhv0sVZup6pA==} + /unist-util-is@6.0.0: + resolution: {integrity: sha512-2qCTHimwdxLfz+YzdGfkqNlH0tLi9xjTnHddPmJwtIG9MGsdbutfTc4P+haPD7l7Cjxf/WZj+we5qfVPvvxfYw==} + dependencies: + '@types/unist': 3.0.2 + dev: false + + /unist-util-position@5.0.0: + resolution: {integrity: sha512-fucsC7HjXvkB5R3kTCO7kUjRdrS0BJt3M/FPxmHMBOm8JQi2BsHAHFsy27E0EolP8rp0NzXsJ+jNPyDWvOJZPA==} + dependencies: + '@types/unist': 3.0.2 + dev: false + + /unist-util-stringify-position@4.0.0: + resolution: {integrity: sha512-0ASV06AAoKCDkS2+xw5RXJywruurpbC4JZSm7nr7MOt1ojAzvyyaO+UxZf18j8FCF6kmzCZKcAgN/yu2gm2XgQ==} + dependencies: + '@types/unist': 3.0.2 + dev: false + + /unist-util-visit-parents@6.0.1: + resolution: {integrity: sha512-L/PqWzfTP9lzzEa6CKs0k2nARxTdZduw3zyh8d2NVBnsyvHjSX4TWse388YrrQKbvI8w20fGjGlhgT96WwKykw==} + dependencies: + '@types/unist': 3.0.2 + unist-util-is: 6.0.0 + dev: false + + /unist-util-visit@5.0.0: + resolution: {integrity: sha512-MR04uvD+07cwl/yhVuVWAtw+3GOR/knlL55Nd/wAdblk27GCVt3lqpTivy/tkJcZoNPzTwS1Y+KMojlLDhoTzg==} + dependencies: + '@types/unist': 3.0.2 + unist-util-is: 6.0.0 + unist-util-visit-parents: 6.0.1 + dev: false + /universalify@2.0.1: resolution: {integrity: sha512-gptHNQghINnc/vTGIk0SOFGFNXw7JVrlRUtConJRlvaw6DuX0wO5Jeko9sWrMBhh+PsYAZ7oXAiOnf/UKogyiw==} engines: {node: '>= 10.0.0'} @@ -4427,6 +4657,28 @@ packages: engines: {node: '>= 0.8'} dev: true + /vfile-location@5.0.2: + resolution: {integrity: sha512-NXPYyxyBSH7zB5U6+3uDdd6Nybz6o6/od9rk8bp9H8GR3L+cm/fC0uUTbqBmUTnMCUDslAGBOIKNfvvb+gGlDg==} + dependencies: + '@types/unist': 3.0.2 + vfile: 6.0.1 + dev: false + + /vfile-message@4.0.2: + resolution: {integrity: sha512-jRDZ1IMLttGj41KcZvlrYAaI3CfqpLpfpf+Mfig13viT6NKvRzWZ+lXz0Y5D60w6uJIBAOGq9mSHf0gktF0duw==} + dependencies: + '@types/unist': 3.0.2 + unist-util-stringify-position: 4.0.0 + dev: false + + /vfile@6.0.1: + resolution: {integrity: sha512-1bYqc7pt6NIADBJ98UiG0Bn/CHIVOoZ/IyEkqIruLg0mE1BKzkOXY2D6CSqQIcKqgadppE5lrxgWXJmXd7zZJw==} + dependencies: + '@types/unist': 3.0.2 + unist-util-stringify-position: 4.0.0 + vfile-message: 4.0.2 + dev: false + /vite-node@1.0.0-beta.5(@types/node@20.9.1)(supports-color@9.4.0): resolution: {integrity: sha512-iXm+GTJbR9R6V/bCM1+LQqIohL/tncZVNGIcTtzpYThBD8yiTkDPvEjy1Mf7KFACtG3qY/0VDMrkuMtqG/JFhg==} engines: {node: ^18.0.0 || >=20.0.0} @@ -4540,12 +4792,6 @@ packages: - terser dev: true - /vscode-oniguruma@1.7.0: - resolution: {integrity: sha512-L9WMGRfrjOhgHSdOYgCt/yRMsXzLDJSL7BPrOZt73gU0iWO4mpqzqQzOz5srxqTvMBaR0XZTSrVWo4j55Rc6cA==} - - /vscode-textmate@8.0.0: - resolution: {integrity: sha512-AFbieoL7a5LMqcnOF04ji+rpXadgOXnZsxQr//r83kLPr7biP7am3g9zbaZIaBGwBRWeSvoMD4mgPdX3e4NWBg==} - /vue-demi@0.14.6(vue@3.3.8): resolution: {integrity: sha512-8QA7wrYSHKaYgUxDA5ZC24w+eHm3sYCbp0EzcDwKqN3p6HqtTCGR/GVsPyZW92unff4UlcSh++lmqDWN3ZIq4w==} engines: {node: '>=12'} @@ -4610,6 +4856,10 @@ packages: - debug dev: true + /web-namespaces@2.0.1: + resolution: {integrity: sha512-bKr1DkiNa2krS7qxNtdrtHAmzuYGFQLiQ13TsorsdT6ULTkPLKuu5+GsFpDlg6JFjUTwX2DyhMPG2be8uPrqsQ==} + dev: false + /web-resource-inliner@6.0.1: resolution: {integrity: sha512-kfqDxt5dTB1JhqsCUQVFDj0rmY+4HLwGQIsLPbyrsN9y9WV/1oFDSx3BQ4GfCv9X+jVeQ7rouTqwK53rA/7t8A==} engines: {node: '>=10.0.0'} @@ -4728,3 +4978,7 @@ packages: resolution: {integrity: sha512-9bnSc/HEW2uRy67wc+T8UwauLuPJVn28jb+GtJY16iiKWyvmYJRXVT4UamsAEGQfPohgr2q4Tq0sQbQlxTfi1g==} engines: {node: '>=12.20'} dev: true + + /zwitch@2.0.4: + resolution: {integrity: sha512-bXE4cR/kVZhKZX/RjPEflHaKVhUVl85noU3v6b8apfQEc1x4A+zBxjZ4lN8LqGd6WZ3dl98pY4o717VFmoPp+A==} + dev: false diff --git a/src/client/theme-default/styles/components/vp-code.css b/src/client/theme-default/styles/components/vp-code.css index ee74e5b2..1ff9429b 100644 --- a/src/client/theme-default/styles/components/vp-code.css +++ b/src/client/theme-default/styles/components/vp-code.css @@ -1,7 +1,7 @@ -.dark .vp-code-light { - display: none; +.dark .vp-code span { + color: var(--shiki-dark, inherit); } -html:not(.dark) .vp-code-dark { - display: none; +html:not(.dark) .vp-code span { + color: var(--shiki-light, inherit); } diff --git a/src/node/markdown/markdown.ts b/src/node/markdown/markdown.ts index 3ec80b9c..d83e2cca 100644 --- a/src/node/markdown/markdown.ts +++ b/src/node/markdown/markdown.ts @@ -18,7 +18,6 @@ import MarkdownIt from 'markdown-it' import anchorPlugin from 'markdown-it-anchor' import attrsPlugin from 'markdown-it-attrs' import emojiPlugin from 'markdown-it-emoji' -import type { ILanguageRegistration, IThemeRegistration } from 'shiki' import type { Logger } from 'vite' import { containerPlugin, type ContainerOptions } from './plugins/containers' import { highlight } from './plugins/highlight' @@ -28,12 +27,22 @@ import { lineNumberPlugin } from './plugins/lineNumbers' import { linkPlugin } from './plugins/link' import { preWrapperPlugin } from './plugins/preWrapper' import { snippetPlugin } from './plugins/snippet' +import type { + ThemeRegistration, + BuiltinTheme, + LanguageInput, + ShikijiTransformer +} from 'shikiji' export type { Header } from '../shared' export type ThemeOptions = - | IThemeRegistration - | { light: IThemeRegistration; dark: IThemeRegistration } + | ThemeRegistration + | BuiltinTheme + | { + light: ThemeRegistration | BuiltinTheme + dark: ThemeRegistration | BuiltinTheme + } export interface MarkdownOptions extends MarkdownIt.Options { lineNumbers?: boolean @@ -51,13 +60,18 @@ export interface MarkdownOptions extends MarkdownIt.Options { headers?: HeadersPluginOptions | boolean sfc?: SfcPluginOptions theme?: ThemeOptions - languages?: ILanguageRegistration[] + languages?: LanguageInput[] toc?: TocPluginOptions externalLinks?: Record cache?: boolean component?: ComponentPluginOptions math?: boolean | any container?: ContainerOptions + + /** + * Shikiji transformers + */ + transformers?: ShikijiTransformer[] } export type MarkdownRenderer = MarkdownIt @@ -80,7 +94,8 @@ export const createMarkdownRenderer = async ( theme, options.languages, options.defaultHighlightLang, - logger + logger, + options.transformers )), ...options }) diff --git a/src/node/markdown/plugins/highlight.ts b/src/node/markdown/plugins/highlight.ts index 52463286..c0809288 100644 --- a/src/node/markdown/plugins/highlight.ts +++ b/src/node/markdown/plugins/highlight.ts @@ -1,23 +1,21 @@ import { customAlphabet } from 'nanoid' import c from 'picocolors' +import type { LanguageInput, ShikijiTransformer } from 'shikiji' import { - BUNDLED_LANGUAGES, - type HtmlRendererOptions, - type ILanguageRegistration, - type IThemeRegistration -} from 'shiki' -import { - addClass, - createDiffProcessor, - createFocusProcessor, - createHighlightProcessor, - createRangeProcessor, - defineProcessor, + bundledLanguages, getHighlighter, - type Processor -} from 'shiki-processor' + isPlaintext as isPlainLang +} from 'shikiji' import type { Logger } from 'vite' import type { ThemeOptions } from '../markdown' +import { + transformerCompactLineOptions, + transformerNotationDiff, + transformerNotationErrorLevel, + transformerNotationFocus, + transformerNotationHighlight, + type TransformerCompactLineOption +} from 'shikiji-transformers' const nanoid = customAlphabet('abcdefghijklmnopqrstuvwxyz', 10) @@ -29,7 +27,7 @@ const nanoid = customAlphabet('abcdefghijklmnopqrstuvwxyz', 10) * 2. convert line numbers into line options: * [{ line: number, classes: string[] }] */ -const attrsToLines = (attrs: string): HtmlRendererOptions['lineOptions'] => { +const attrsToLines = (attrs: string): TransformerCompactLineOption[] => { attrs = attrs.replace(/^(?:\[.*?\])?.*?([\d,-]+).*/, '$1').trim() const result: number[] = [] if (!attrs) { @@ -53,37 +51,31 @@ const attrsToLines = (attrs: string): HtmlRendererOptions['lineOptions'] => { })) } -const errorLevelProcessor = defineProcessor({ - name: 'error-level', - handler: createRangeProcessor({ - error: ['highlighted', 'error'], - warning: ['highlighted', 'warning'] - }) -}) - export async function highlight( theme: ThemeOptions, - languages: ILanguageRegistration[] = [], + languages?: LanguageInput[], defaultLang: string = '', - logger: Pick = console + logger: Pick = console, + userTransformers: ShikijiTransformer[] = [] ): Promise<(str: string, lang: string, attrs: string) => string> { - const hasSingleTheme = typeof theme === 'string' || 'name' in theme - const getThemeName = (themeValue: IThemeRegistration) => - typeof themeValue === 'string' ? themeValue : themeValue.name - - const processors: Processor[] = [ - createFocusProcessor(), - createHighlightProcessor({ hasHighlightClass: 'highlighted' }), - createDiffProcessor(), - errorLevelProcessor - ] - const highlighter = await getHighlighter({ - themes: hasSingleTheme ? [theme] : [theme.dark, theme.light], - langs: [...BUNDLED_LANGUAGES, ...languages], - processors + themes: + typeof theme === 'string' || 'name' in theme + ? [theme] + : [theme.light, theme.dark], + langs: languages?.length ? languages : Object.keys(bundledLanguages) }) + const transformers = [ + transformerNotationDiff(), + transformerNotationFocus({ + classFocused: 'has-focus', + classRootActive: 'has-focused-lines' + }), + transformerNotationHighlight(), + transformerNotationErrorLevel() + ] + const styleRE = /]*(style=".*?")/ const preRE = /^/ const vueRE = /-vue$/ @@ -102,7 +94,7 @@ export async function highlight( if (lang) { const langLoaded = highlighter.getLoadedLanguages().includes(lang as any) - if (!langLoaded && !['ansi', 'plaintext', 'txt', 'text'].includes(lang)) { + if (!langLoaded && !isPlainLang(lang) && lang !== 'ansi') { logger.warn( c.yellow( `\nThe language '${lang}' is not loaded, falling back to '${ @@ -155,24 +147,26 @@ export async function highlight( str = removeMustache(str).trimEnd() - const codeToHtml = (theme: IThemeRegistration) => { - const res = - lang === 'ansi' - ? highlighter.ansiToHtml(str, { - lineOptions, - theme: getThemeName(theme) - }) - : highlighter.codeToHtml(str, { - lang, - lineOptions, - theme: getThemeName(theme) - }) - return fillEmptyHighlightedLine(cleanup(restoreMustache(res))) - } + const result = highlighter.codeToHtml(str, { + lang, + ...(typeof theme === 'string' || 'name' in theme + ? { theme } + : { + themes: theme, + defaultColor: false + }), + transformers: [ + ...transformers, + transformerCompactLineOptions(lineOptions), + { + pre(node) { + node.properties.class = 'vp-code' + } + }, + ...userTransformers + ] + }) - if (hasSingleTheme) return codeToHtml(theme) - const dark = addClass(codeToHtml(theme.dark), 'vp-code-dark', 'pre') - const light = addClass(codeToHtml(theme.light), 'vp-code-light', 'pre') - return dark + light + return fillEmptyHighlightedLine(cleanup(restoreMustache(result))) } } diff --git a/src/node/markdown/plugins/preWrapper.ts b/src/node/markdown/plugins/preWrapper.ts index 9e79a4e1..b224d742 100644 --- a/src/node/markdown/plugins/preWrapper.ts +++ b/src/node/markdown/plugins/preWrapper.ts @@ -44,5 +44,4 @@ function extractLang(info: string) { .replace(/:(no-)?line-numbers({| |$|=\d*).*/, '') .replace(/(-vue|{| ).*$/, '') .replace(/^vue-html$/, 'template') - .replace(/^ansi$/, '') } diff --git a/template/markdown-examples.md b/template/markdown-examples.md index 8e55eb8a..3ea9aa9f 100644 --- a/template/markdown-examples.md +++ b/template/markdown-examples.md @@ -4,11 +4,11 @@ This page demonstrates some of the built-in markdown extensions provided by Vite ## Syntax Highlighting -VitePress provides Syntax Highlighting powered by [Shiki](https://github.com/shikijs/shiki), with additional features like line-highlighting: +VitePress provides Syntax Highlighting powered by [Shikiji](https://github.com/antfu/shikiji), with additional features like line-highlighting: **Input** -```` +````md ```js{4} export default { data () {