feat: mermaid diagram integration (#202)
This commit is contained in:
@@ -1,17 +1,34 @@
|
||||
import { NodeViewContent, NodeViewProps, NodeViewWrapper } from "@tiptap/react";
|
||||
import { ActionIcon, CopyButton, Group, Select, Tooltip } from "@mantine/core";
|
||||
import { useState } from "react";
|
||||
import classes from "./code-block.module.css";
|
||||
import { useEffect, useState } from "react";
|
||||
import { IconCheck, IconCopy } from "@tabler/icons-react";
|
||||
import { useHover } from "@mantine/hooks";
|
||||
import MermaidView from "@/features/editor/components/code-block/mermaid-view.tsx";
|
||||
import classes from "./code-block.module.css";
|
||||
|
||||
export default function CodeBlockView(props: NodeViewProps) {
|
||||
const { node, updateAttributes, extension, editor, selected } = props;
|
||||
const { node, updateAttributes, extension, editor, getPos } = props;
|
||||
const { language } = node.attrs;
|
||||
const [languageValue, setLanguageValue] = useState<string | null>(
|
||||
language || null,
|
||||
);
|
||||
const { hovered, ref } = useHover();
|
||||
const [isSelected, setIsSelected] = useState(false);
|
||||
|
||||
useEffect(() => {
|
||||
const updateSelection = () => {
|
||||
const { state } = editor;
|
||||
const { from, to } = state.selection;
|
||||
// Check if the selection intersects with the node's range
|
||||
const isNodeSelected =
|
||||
(from >= getPos() && from < getPos() + node.nodeSize) ||
|
||||
(to > getPos() && to <= getPos() + node.nodeSize);
|
||||
setIsSelected(isNodeSelected);
|
||||
};
|
||||
|
||||
editor.on("selectionUpdate", updateSelection);
|
||||
return () => {
|
||||
editor.off("selectionUpdate", updateSelection);
|
||||
};
|
||||
}, [editor, getPos(), node.nodeSize]);
|
||||
|
||||
function changeLanguage(language: string) {
|
||||
setLanguageValue(language);
|
||||
@@ -21,10 +38,10 @@ export default function CodeBlockView(props: NodeViewProps) {
|
||||
}
|
||||
|
||||
return (
|
||||
<NodeViewWrapper className="codeBlock" ref={ref}>
|
||||
<Group justify="flex-end">
|
||||
<NodeViewWrapper className="codeBlock">
|
||||
<Group justify="flex-end" contentEditable={false}>
|
||||
<Select
|
||||
placeholder="Auto"
|
||||
placeholder="auto"
|
||||
checkIconPosition="right"
|
||||
data={extension.options.lowlight.listLanguages()}
|
||||
value={languageValue}
|
||||
@@ -54,9 +71,18 @@ export default function CodeBlockView(props: NodeViewProps) {
|
||||
</CopyButton>
|
||||
</Group>
|
||||
|
||||
<pre spellCheck="false">
|
||||
<pre
|
||||
spellCheck="false"
|
||||
hidden={
|
||||
((language === "mermaid" && !editor.isEditable) ||
|
||||
(language === "mermaid" && !isSelected)) &&
|
||||
node.textContent.length > 0
|
||||
}
|
||||
>
|
||||
<NodeViewContent as="code" className={`language-${language}`} />
|
||||
</pre>
|
||||
|
||||
{language === "mermaid" && <MermaidView props={props} />}
|
||||
</NodeViewWrapper>
|
||||
);
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user