support mermaid
This commit is contained in:
@@ -1,17 +1,16 @@
|
||||
import React, { memo, useMemo, useEffect } from 'react';
|
||||
import ReactMarkdown from 'react-markdown';
|
||||
import { Prism as SyntaxHighlighter } from 'react-syntax-highlighter';
|
||||
import { Box, Flex, useColorModeValue } from '@chakra-ui/react';
|
||||
import { useCopyData, formatLinkText } from '@/utils/tools';
|
||||
import Icon from '@/components/Icon';
|
||||
import { formatLinkText } from '@/utils/tools';
|
||||
import remarkGfm from 'remark-gfm';
|
||||
import remarkMath from 'remark-math';
|
||||
import remarkBreaks from 'remark-breaks';
|
||||
import rehypeKatex from 'rehype-katex';
|
||||
import MermaidCodeBlock from './MermaidCodeBlock';
|
||||
|
||||
import 'katex/dist/katex.min.css';
|
||||
import styles from './index.module.scss';
|
||||
import { codeLight } from './codeLight';
|
||||
import CodeLight from './codeLight';
|
||||
import Loading from './Loading';
|
||||
import MermaidCodeBlock from './MermaidCodeBlock';
|
||||
|
||||
const Markdown = ({
|
||||
source,
|
||||
@@ -22,8 +21,6 @@ const Markdown = ({
|
||||
formatLink?: boolean;
|
||||
isChatting?: boolean;
|
||||
}) => {
|
||||
const { copyData } = useCopyData();
|
||||
|
||||
const formatSource = useMemo(() => {
|
||||
return formatLink ? formatLinkText(source) : source;
|
||||
}, [source, formatLink]);
|
||||
@@ -31,53 +28,25 @@ const Markdown = ({
|
||||
return (
|
||||
<ReactMarkdown
|
||||
className={`markdown ${styles.markdown}
|
||||
${
|
||||
isChatting
|
||||
? source === ""
|
||||
? styles.waitingAnimation
|
||||
: styles.animation
|
||||
: ""
|
||||
}
|
||||
${isChatting ? (source === '' ? styles.waitingAnimation : styles.animation) : ''}
|
||||
`}
|
||||
remarkPlugins={[remarkMath]}
|
||||
rehypePlugins={[remarkGfm, rehypeKatex]}
|
||||
remarkPlugins={[remarkGfm, remarkMath, remarkBreaks]}
|
||||
rehypePlugins={[rehypeKatex]}
|
||||
components={{
|
||||
pre: "div",
|
||||
pre: 'div',
|
||||
code({ node, inline, className, children, ...props }) {
|
||||
const match = /language-(\w+)/.exec(className ||'');
|
||||
const code = String(children);
|
||||
const match = /language-(\w+)/.exec(className || '');
|
||||
|
||||
if (match && match[1] === "mermaid") {
|
||||
return <MermaidCodeBlock code={code} />;
|
||||
if (match?.[1] === 'mermaid') {
|
||||
return isChatting ? <Loading /> : <MermaidCodeBlock code={String(children)} />;
|
||||
}
|
||||
|
||||
return !inline && match ? (
|
||||
<Box my={3} borderRadius={"md"} overflow={"overlay"} backgroundColor={"#222"}>
|
||||
<Flex
|
||||
className="code-header"
|
||||
py={2}
|
||||
px={5}
|
||||
backgroundColor={useColorModeValue("#323641", "gray.600")}
|
||||
color={"#fff"}
|
||||
fontSize={"sm"}
|
||||
userSelect={"none"}
|
||||
>
|
||||
<Box flex={1}>{match?.[1]}</Box>
|
||||
<Flex cursor={"pointer"} onClick={() => copyData(code)} alignItems={"center"}>
|
||||
<Icon name={"copy"} width={15} height={15} fill={"#fff"}></Icon>
|
||||
<Box ml={1}>复制代码</Box>
|
||||
</Flex>
|
||||
</Flex>
|
||||
<SyntaxHighlighter style={codeLight as any} language={match?.[1]} PreTag="pre" {...props}>
|
||||
{code}
|
||||
</SyntaxHighlighter>
|
||||
</Box>
|
||||
) : (
|
||||
<code className={className} {...props}>
|
||||
return (
|
||||
<CodeLight className={className} inline={inline} match={match} {...props}>
|
||||
{children}
|
||||
</code>
|
||||
</CodeLight>
|
||||
);
|
||||
},
|
||||
}
|
||||
}}
|
||||
linkTarget="_blank"
|
||||
>
|
||||
|
||||
Reference in New Issue
Block a user