如何使用react-markdown将Markdown转HTML并导出可复制的HTML代码
实现Markdown转HTML并导出代码的方案
核心问题
ReactMarkdown是直接把Markdown渲染成React元素,不会直接给出原始的HTML字符串,所以要实现展示和导出HTML的功能,得额外处理:要么用专门的Markdown转HTML字符串的库,要么从渲染后的DOM里提取内容。
方案一:用Markdown转HTML库(推荐)
1. 安装依赖
选markdown-it这个轻量库,命令行执行:
npm install markdown-it
2. 修改组件代码
import React, { useState } from 'react'; import ReactMarkdown from 'react-markdown'; import MarkdownIt from 'markdown-it'; // 初始化markdown-it实例 const mdParser = new MarkdownIt(); function App() { const [markdown, setMarkdown] = useState(''); const [rawHtml, setRawHtml] = useState(''); const handleInputChange = (e) => { const inputContent = e.target.value; setMarkdown(inputContent); // 把输入的Markdown转成HTML字符串 setRawHtml(mdParser.render(inputContent)); }; // 复制HTML代码到剪贴板 const copyToClipboard = () => { navigator.clipboard.writeText(rawHtml) .then(() => alert('HTML代码已复制')) .catch(err => console.log('复制失败:', err)); }; return ( <div className="App"> <textarea placeholder='输入Markdown文本' className="textarea" value={markdown} onChange={handleInputChange} /> <ReactMarkdown className='reactMarkdownBox' children={markdown} /> <div className="htmlbox"> <h3>原始HTML代码</h3> <pre><code>{rawHtml}</code></pre> <button onClick={copyToClipboard}>复制HTML</button> </div> </div> ); } export default App;
3. 说明
- 用
markdown-it直接转Markdown为HTML字符串,状态同步更新,稳定性高 <pre><code>标签能保留HTML的格式,让代码显示更清晰- 利用浏览器原生的
navigator.clipboardAPI实现复制,不需要额外装复制库
方案二:从渲染后的DOM提取HTML(无额外依赖)
如果不想加新依赖,可以通过ref获取ReactMarkdown渲染后的DOM元素,提取它的innerHTML:
import React, { useState, useRef } from 'react'; import ReactMarkdown from 'react-markdown'; function App() { const [markdown, setMarkdown] = useState(''); const [rawHtml, setRawHtml] = useState(''); const markdownRenderRef = useRef(null); const handleInputChange = (e) => { const inputContent = e.target.value; setMarkdown(inputContent); // 延迟获取DOM内容,确保React完成渲染更新 setTimeout(() => { if (markdownRenderRef.current) { setRawHtml(markdownRenderRef.current.innerHTML); } }, 0); }; const copyToClipboard = () => { navigator.clipboard.writeText(rawHtml) .then(() => alert('HTML代码已复制')) .catch(err => console.log('复制失败:', err)); }; return ( <div className="App"> <textarea placeholder='输入Markdown文本' className="textarea" value={markdown} onChange={handleInputChange} /> <ReactMarkdown className='reactMarkdownBox' children={markdown} ref={markdownRenderRef} /> <div className="htmlbox"> <h3>原始HTML代码</h3> <pre><code>{rawHtml}</code></pre> <button onClick={copyToClipboard}>复制HTML</button> </div> </div> ); } export default App;
注意点
- 因为React的状态更新是异步的,所以加了
setTimeout确保DOM渲染完成后再提取内容 - 这种方式依赖ReactMarkdown的DOM结构,如果组件内部有更新,可能会影响结果
内容的提问来源于stack exchange,提问作者WltMr
相关产品推荐
相关产品推荐

