({
code,
lang,
theme = "github-dark",
}: UseHighlightedCodeOptions)
| 97 | } |
| 98 | |
| 99 | export function useHighlightedCode({ |
| 100 | code, |
| 101 | lang, |
| 102 | theme = "github-dark", |
| 103 | }: UseHighlightedCodeOptions): string | null { |
| 104 | const [html, setHtml] = useState<string | null>(null); |
| 105 | const lastKey = useRef<string>(""); |
| 106 | const key = `${lang}:${theme}:${code}`; |
| 107 | |
| 108 | useEffect(() => { |
| 109 | if (lastKey.current === key) return; |
| 110 | lastKey.current = key; |
| 111 | |
| 112 | let cancelled = false; |
| 113 | getHighlighter().then((hl) => { |
| 114 | if (cancelled) return; |
| 115 | try { |
| 116 | const highlighted = hl.codeToHtml(code, { lang, theme }); |
| 117 | if (!cancelled) setHtml(highlighted); |
| 118 | } catch { |
| 119 | // Language not supported — fall back to plain |
| 120 | if (!cancelled) setHtml(null); |
| 121 | } |
| 122 | }); |
| 123 | return () => { |
| 124 | cancelled = true; |
| 125 | }; |
| 126 | }, [key, code, lang, theme]); |
| 127 | |
| 128 | return html; |
| 129 | } |
| 130 | |
| 131 | interface SyntaxHighlightProps { |
| 132 | code: string; |
no test coverage detected