mirror of
https://github.com/pacnpal/thrilltrack-explorer.git
synced 2025-12-22 08:11:13 -05:00
feat: Migrate markdown editor to MDXEditor
This commit is contained in:
@@ -1,10 +1,36 @@
|
||||
import { useEffect, useState } from 'react';
|
||||
import MDEditor from '@uiw/react-md-editor';
|
||||
import { useEffect, useState, useRef } from 'react';
|
||||
import {
|
||||
MDXEditor,
|
||||
headingsPlugin,
|
||||
listsPlugin,
|
||||
quotePlugin,
|
||||
thematicBreakPlugin,
|
||||
markdownShortcutPlugin,
|
||||
linkPlugin,
|
||||
linkDialogPlugin,
|
||||
imagePlugin,
|
||||
tablePlugin,
|
||||
codeBlockPlugin,
|
||||
codeMirrorPlugin,
|
||||
diffSourcePlugin,
|
||||
toolbarPlugin,
|
||||
UndoRedo,
|
||||
BoldItalicUnderlineToggles,
|
||||
CodeToggle,
|
||||
ListsToggle,
|
||||
BlockTypeSelect,
|
||||
CreateLink,
|
||||
InsertImage,
|
||||
InsertTable,
|
||||
InsertThematicBreak,
|
||||
DiffSourceToggleWrapper,
|
||||
type MDXEditorMethods
|
||||
} from '@mdxeditor/editor';
|
||||
import '@mdxeditor/editor/style.css';
|
||||
import { useTheme } from '@/components/theme/ThemeProvider';
|
||||
import { useAutoSave } from '@/hooks/useAutoSave';
|
||||
import { CheckCircle2, Loader2, AlertCircle } from 'lucide-react';
|
||||
import { cn } from '@/lib/utils';
|
||||
import rehypeSanitize from 'rehype-sanitize';
|
||||
|
||||
interface MarkdownEditorProps {
|
||||
value: string;
|
||||
@@ -26,6 +52,7 @@ export function MarkdownEditor({
|
||||
const { theme } = useTheme();
|
||||
const [mounted, setMounted] = useState(false);
|
||||
const [resolvedTheme, setResolvedTheme] = useState<'light' | 'dark'>('light');
|
||||
const editorRef = useRef<MDXEditorMethods>(null);
|
||||
|
||||
// Resolve "system" theme to actual theme based on OS preference
|
||||
useEffect(() => {
|
||||
@@ -85,22 +112,68 @@ export function MarkdownEditor({
|
||||
|
||||
return (
|
||||
<div className="space-y-2">
|
||||
<div data-color-mode={resolvedTheme}>
|
||||
<div className="wmde-markdown-var" />
|
||||
<MDEditor
|
||||
value={value}
|
||||
onChange={(val) => onChange(val || '')}
|
||||
height={height}
|
||||
preview="live"
|
||||
hideToolbar={false}
|
||||
enableScroll={true}
|
||||
textareaProps={{
|
||||
placeholder
|
||||
}}
|
||||
previewOptions={{
|
||||
rehypePlugins: [[rehypeSanitize]],
|
||||
className: 'prose dark:prose-invert max-w-none p-4'
|
||||
}}
|
||||
<div
|
||||
className={cn(
|
||||
'border border-input rounded-lg overflow-hidden',
|
||||
resolvedTheme === 'dark' && 'dark'
|
||||
)}
|
||||
style={{ minHeight: height }}
|
||||
>
|
||||
<MDXEditor
|
||||
ref={editorRef}
|
||||
markdown={value}
|
||||
onChange={onChange}
|
||||
placeholder={placeholder}
|
||||
contentEditableClassName="prose dark:prose-invert max-w-none p-4 min-h-[500px]"
|
||||
plugins={[
|
||||
headingsPlugin(),
|
||||
listsPlugin(),
|
||||
quotePlugin(),
|
||||
thematicBreakPlugin(),
|
||||
markdownShortcutPlugin(),
|
||||
linkPlugin(),
|
||||
linkDialogPlugin(),
|
||||
imagePlugin({
|
||||
imageUploadHandler: async () => {
|
||||
return Promise.resolve('https://placeholder.com/image.jpg');
|
||||
}
|
||||
}),
|
||||
tablePlugin(),
|
||||
codeBlockPlugin({ defaultCodeBlockLanguage: 'js' }),
|
||||
codeMirrorPlugin({
|
||||
codeBlockLanguages: {
|
||||
js: 'JavaScript',
|
||||
ts: 'TypeScript',
|
||||
tsx: 'TypeScript (React)',
|
||||
jsx: 'JavaScript (React)',
|
||||
css: 'CSS',
|
||||
html: 'HTML',
|
||||
python: 'Python',
|
||||
bash: 'Bash',
|
||||
json: 'JSON',
|
||||
sql: 'SQL'
|
||||
}
|
||||
}),
|
||||
diffSourcePlugin({ viewMode: 'rich-text', diffMarkdown: '' }),
|
||||
toolbarPlugin({
|
||||
toolbarContents: () => (
|
||||
<>
|
||||
<UndoRedo />
|
||||
<BoldItalicUnderlineToggles />
|
||||
<CodeToggle />
|
||||
<BlockTypeSelect />
|
||||
<ListsToggle />
|
||||
<CreateLink />
|
||||
<InsertImage />
|
||||
<InsertTable />
|
||||
<InsertThematicBreak />
|
||||
<DiffSourceToggleWrapper>
|
||||
<span className="text-sm">Source</span>
|
||||
</DiffSourceToggleWrapper>
|
||||
</>
|
||||
)
|
||||
})
|
||||
]}
|
||||
/>
|
||||
</div>
|
||||
|
||||
|
||||
Reference in New Issue
Block a user