-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathcode-block-elements.tsx
More file actions
78 lines (70 loc) · 2.22 KB
/
Copy pathcode-block-elements.tsx
File metadata and controls
78 lines (70 loc) · 2.22 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
import type { ComponentPropsWithoutRef } from "react"
import { cn } from "~/utils/css"
import { createLineData } from "./code-block-parser"
import { getTokenColor, isTokenType, type tokenize } from "./code-block-syntax-highlighter"
const TokenElement = ({ token }: { token: ReturnType<typeof tokenize>[0] }) => {
const { type, value } = token
const color = isTokenType(type) ? getTokenColor(type) : ""
return <span style={{ color }}>{value}</span>
}
const DiffIndicator = ({ indicator }: { indicator: string }) => (
<span className="absolute top-0 left-0 w-4 select-none text-center font-medium text-[var(--color-diff-indicator)]">
{indicator}
</span>
)
const LineElement = ({ line }: { line: string }) => {
const { tokens, styles, isNormalDiff } = createLineData(line)
return (
<div className="relative">
<div
className="flex min-h-6 items-center pr-4 pl-4"
style={{
backgroundColor: styles.backgroundColor,
borderLeft: styles.borderLeft,
borderLeftColor: styles.borderLeftColor,
}}
>
{!isNormalDiff && <DiffIndicator indicator={styles.indicator} />}
<span className="block">
{tokens.map((token, index) => (
<TokenElement
key={`${token.value}-${
// biome-ignore lint/suspicious/noArrayIndexKey: lets keep this key for now
index
}`}
token={token}
/>
))}
</span>
</div>
</div>
)
}
const CodeElement = ({ lines }: { lines: string[] }) => (
<code className="relative block">
{lines.map((line, index) => (
<LineElement
key={`${
// biome-ignore lint/suspicious/noArrayIndexKey: lets keep this key for now
index
}-${line}`}
line={line}
/>
))}
</code>
)
interface PreElementProps extends Omit<ComponentPropsWithoutRef<"pre">, "children"> {
lines: string[]
className?: string
}
export const PreElement = ({ lines, className = "", ...props }: PreElementProps) => (
<pre
{...props}
className={cn(
"scrollbar scrollbar-thin relative overflow-x-auto rounded-lg border border-(--color-border) bg-(--color-code-block-bg) py-4 font-mono text-(--color-code-block-text) text-sm leading-relaxed md:text-base [&::-webkit-scrollbar-thumb:hover]:cursor-pointer",
className
)}
>
<CodeElement lines={lines} />
</pre>
)