mirror of
https://github.com/kunkunsh/kunkun.git
synced 2025-04-11 17:29:44 +00:00
feat: add markdown renderer
This commit is contained in:
parent
c2a75082f9
commit
db5d3d2f6c
@ -32,6 +32,10 @@
|
|||||||
"./animation": {
|
"./animation": {
|
||||||
"types": "./src/components/animation/index.ts",
|
"types": "./src/components/animation/index.ts",
|
||||||
"svelte": "./src/components/animation/index.ts"
|
"svelte": "./src/components/animation/index.ts"
|
||||||
|
},
|
||||||
|
"./markdown": {
|
||||||
|
"types": "./src/components/markdown/index.ts",
|
||||||
|
"svelte": "./src/components/markdown/index.ts"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"scripts": {
|
"scripts": {
|
||||||
@ -76,15 +80,21 @@
|
|||||||
"@internationalized/date": "^3.7.0",
|
"@internationalized/date": "^3.7.0",
|
||||||
"@kksh/supabase": "workspace:*",
|
"@kksh/supabase": "workspace:*",
|
||||||
"@shikijs/langs": "^2.3.2",
|
"@shikijs/langs": "^2.3.2",
|
||||||
|
"@shikijs/rehype": "^3.2.1",
|
||||||
"@shikijs/themes": "^2.3.2",
|
"@shikijs/themes": "^2.3.2",
|
||||||
"@std/semver": "npm:@jsr/std__semver@^1.0.3",
|
"@std/semver": "npm:@jsr/std__semver@^1.0.3",
|
||||||
"@tanstack/svelte-virtual": "^3.13.2",
|
"@tanstack/svelte-virtual": "^3.13.2",
|
||||||
"dompurify": "^3.2.3",
|
"dompurify": "^3.2.3",
|
||||||
"fuse.js": "^7.1.0",
|
"fuse.js": "^7.1.0",
|
||||||
"gsap": "^3.12.7",
|
"gsap": "^3.12.7",
|
||||||
|
"katex": "^0.16.21",
|
||||||
"moment": "^2.30.1",
|
"moment": "^2.30.1",
|
||||||
"pretty-bytes": "^6.1.1",
|
"pretty-bytes": "^6.1.1",
|
||||||
|
"rehype-class-names": "^2.0.0",
|
||||||
|
"rehype-katex": "^7.0.1",
|
||||||
|
"remark-math": "^6.0.0",
|
||||||
"shiki-magic-move": "^0.5.2",
|
"shiki-magic-move": "^0.5.2",
|
||||||
|
"svelte-exmarkdown": "^4.0.3",
|
||||||
"svelte-inspect-value": "^0.3.0",
|
"svelte-inspect-value": "^0.3.0",
|
||||||
"svelte-markdown": "^0.4.1",
|
"svelte-markdown": "^0.4.1",
|
||||||
"svelte-motion": "^0.12.2",
|
"svelte-motion": "^0.12.2",
|
||||||
|
48
packages/ui/src/components/markdown/Markdown.svelte
Normal file
48
packages/ui/src/components/markdown/Markdown.svelte
Normal file
@ -0,0 +1,48 @@
|
|||||||
|
<script lang="ts">
|
||||||
|
import Markdown from "svelte-exmarkdown"
|
||||||
|
import type { Plugin } from "svelte-exmarkdown"
|
||||||
|
import rehypeShikiFromHighlighter from "@shikijs/rehype/core"
|
||||||
|
import { createHighlighterCoreSync } from "shiki/core"
|
||||||
|
import { createJavaScriptRegexEngine } from "shiki/engine/javascript"
|
||||||
|
import ts from "shiki/langs/typescript.mjs"
|
||||||
|
import svelte from "shiki/langs/svelte.mjs"
|
||||||
|
import vitesseDark from "shiki/themes/vitesse-dark.mjs"
|
||||||
|
import rehypeKatex from "rehype-katex"
|
||||||
|
import remarkMath from "remark-math"
|
||||||
|
import rehypeClassNames from "rehype-class-names"
|
||||||
|
import Pre from "./Pre.svelte"
|
||||||
|
|
||||||
|
const addClass: Plugin = {
|
||||||
|
rehypePlugin: [
|
||||||
|
rehypeClassNames,
|
||||||
|
{
|
||||||
|
pre: "p-4 rounded-md overflow-auto"
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}
|
||||||
|
|
||||||
|
const shikiPlugin = {
|
||||||
|
rehypePlugin: [
|
||||||
|
rehypeShikiFromHighlighter,
|
||||||
|
createHighlighterCoreSync({
|
||||||
|
themes: [vitesseDark],
|
||||||
|
langs: [ts, svelte],
|
||||||
|
engine: createJavaScriptRegexEngine()
|
||||||
|
}),
|
||||||
|
{
|
||||||
|
theme: "vitesse-dark"
|
||||||
|
}
|
||||||
|
]
|
||||||
|
} satisfies Plugin
|
||||||
|
|
||||||
|
const plugins: Plugin[] = [
|
||||||
|
shikiPlugin,
|
||||||
|
{ remarkPlugin: [remarkMath], rehypePlugin: [rehypeKatex] },
|
||||||
|
addClass,
|
||||||
|
{ renderer: { pre: Pre } }
|
||||||
|
]
|
||||||
|
|
||||||
|
let { md }: { md: string } = $props()
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<Markdown {md} {plugins} />
|
25
packages/ui/src/components/markdown/Pre.svelte
Normal file
25
packages/ui/src/components/markdown/Pre.svelte
Normal file
@ -0,0 +1,25 @@
|
|||||||
|
<script lang="ts">
|
||||||
|
import { Button } from '@kksh/svelte5';
|
||||||
|
import { CopyIcon } from 'lucide-svelte';
|
||||||
|
import type { Snippet } from 'svelte';
|
||||||
|
|
||||||
|
let pre: HTMLPreElement;
|
||||||
|
|
||||||
|
let {
|
||||||
|
children,
|
||||||
|
class: className,
|
||||||
|
style
|
||||||
|
}: { children: Snippet; class?: string; style?: string } = $props();
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<div class="relative">
|
||||||
|
<pre class={className} {style} bind:this={pre}>{@render children()}</pre>
|
||||||
|
<Button
|
||||||
|
size="icon"
|
||||||
|
variant="outline"
|
||||||
|
onclick={() => navigator.clipboard.writeText(pre.textContent ?? '')}
|
||||||
|
class="absolute right-2 top-2"
|
||||||
|
>
|
||||||
|
<CopyIcon />
|
||||||
|
</Button>
|
||||||
|
</div>
|
1
packages/ui/src/components/markdown/index.ts
Normal file
1
packages/ui/src/components/markdown/index.ts
Normal file
@ -0,0 +1 @@
|
|||||||
|
export {default as Markdown} from './Markdown.svelte';
|
946
pnpm-lock.yaml
generated
946
pnpm-lock.yaml
generated
File diff suppressed because it is too large
Load Diff
Loading…
x
Reference in New Issue
Block a user