MDX (Markdown + JSX) позволяет сочетать текстовую разметку Markdown с компонентами React, что делает его идеальным инструментом для создания технической документации, учебников и интерактивных гайдов. Одним из ключевых аспектов при работе с MDX является правильное отображение и управление блоками кода, включая возможность их копирования.
В MDX поддерживается стандартный Markdown-синтаксис для блоков кода:
```javascript
console.log('Hello, MDX!');
В этом примере:
- Тройные обратные апострофы (\`\`\`) обозначают начало и конец блока кода.
- Язык (`javascript`) используется для подсветки синтаксиса.
- Содержимое между апострофами рендерится как код с сохранением форматирования и отступов.
Ключевой момент: MDX автоматически обрабатывает такие блоки как JSX-элементы, поэтому их можно стилизовать и оборачивать дополнительными компонентами.
---
### Использование компонента `pre` и `code`
Для более точного контроля над отображением кода можно использовать нативные HTML-элементы `pre` и `code` внутри MDX:
```jsx
<pre>
<code className="language-js">
{`function greet(name) {
return \`Hello, \${name}!\`;
}`}
</code>
</pre>
Особенности:
pre сохраняет форматирование и переносы строк.code может содержать атрибут className для
подсветки синтаксиса через библиотеки, такие как Prism или
Highlight.js.MDX позволяет интегрировать интерактивные компоненты React, что делает возможным создание кнопки для копирования кода в буфер обмена. Пример реализации:
import { useState } from 'react';
function CopyButton({ code }) {
const [copied, setCopied] = useState(false);
const handleCopy = () => {
navigator.clipboard.writeText(code).then(() => {
setCopied(true);
setTimeout(() => setCopied(false), 2000);
});
};
return (
<button onCl ick={handleCopy}>
{copied ? 'Скопировано!' : 'Копировать'}
</button>
);
}
Интеграция с блоком кода:
<pre>
<code className="language-js">
{`const sum = (a, b) => a + b;`}
</code>
<CopyButton code={`const sum = (a, b) => a + b;`} />
</pre>
Особенности подхода:
navigator.clipboard для безопасного
копирования текста.CopyButton является универсальным и может
применяться к любому коду.copied обеспечивает динамическую обратную
связь пользователю.Для документации с большим количеством блоков кода удобно создать обёртку, объединяющую отображение и кнопку копирования:
export function CodeBlock({ language, children }) {
return (
<div className="code-block">
<pre>
<code className={`language-${language}`}>
{children}
</code>
</pre>
<CopyButton code={children} />
</div>
);
}
Использование в MDX:
<CodeBlock language="js">
{`function multiply(a, b) {
return a * b;
}`}
</CodeBlock>
Преимущества:
Для подсветки синтаксиса кода чаще всего используют Prism или Highlight.js. Интеграция с MDX:
import Prism from 'prismjs';
import 'prismjs/themes/prism-tomorrow.css';
import { useEffect } from 'react';
function HighlightedCode({ language, children }) {
useEffect(() => {
Prism.highlightAll();
}, []);
return (
<pre className={`language-${language}`}>
<code>{children}</code>
</pre>
);
}
Особенности:
useEffect гарантирует, что подсветка применяется после
рендера.HighlightedCode.navigator.clipboard.CodeBlock с подсветкой и копированием.MDX предоставляет гибкие возможности для работы с кодом в документации, включая подсветку синтаксиса, форматирование и удобное копирование. Комбинация стандартных Markdown-блоков, React-компонентов и библиотек для подсветки синтаксиса позволяет создавать интерактивные учебники и технические руководства без потери качества и удобства использования.