React Router应用中跨页面传递TinyMCE富文本内容的方案咨询
跨页面TinyMCE富文本内容传递解决方案
核心问题分析
你遇到的是React Router多页面间的状态共享问题:两个编辑器属于不同路由页面,没有直接的组件层级关系,因此普通props传递或同一父组件内的状态提升无法直接生效。以下是几种从简单到进阶的实现方案,按需选择。
一、最简单方案:URL参数传递(适合短文本场景)
利用路由URL的查询参数传递内容,无需额外状态管理,适合内容长度较短的场景。
Page1(编辑器页面)修改:
提交时将富文本内容编码后拼入跳转URL:
import { useNavigate } from 'react-router-dom'; function Page1() { const editorRef = useRef(); const navigate = useNavigate(); const log = () => { if (editorRef.current) { const content = editorRef.current.getContent(); // 编码内容避免URL特殊字符冲突 const encodedContent = encodeURIComponent(content); // 跳转到Page2并携带参数 navigate(`/page2?content=${encodedContent}`); } }; return ( <> <Editor apiKey='your-api-key' ref={editorRef} init={{ /* 你的编辑器配置 */ }} /> <button onClick={log}>提交跳转</button> </> ); }
Page2(展示页面)修改:
读取URL参数并设置编辑器内容:
import { useLocation } from 'react-router-dom'; import { Editor } from '@tinymce/tinymce-react'; function Page2() { const location = useLocation(); const editorRef = useRef(); React.useEffect(() => { const params = new URLSearchParams(location.search); const content = params.get('content'); if (editorRef.current) { // 解码内容并设置 editorRef.current.setContent(content ? decodeURIComponent(content) : "EMPTY ENTRY"); } }, [location.search, editorRef]); return ( <Editor apiKey='your-api-key' disabled={true} ref={editorRef} init={{ /* 你的编辑器配置 */ }} /> ); }
注意:URL参数有长度限制(不同浏览器约2KB-8KB),长内容场景请使用下面的方案。
二、通用方案:Context API全局状态共享
将状态提升到根组件(App),通过React Context实现全局共享,适合任意长度内容,且支持多组件同步状态。
1. 创建全局Context
新建EditorContext.js文件:
import React from 'react'; // 初始化Context默认值 const EditorContext = React.createContext({ editorContent: "", setEditorContent: () => {} }); export default EditorContext;
2. 根组件(App)提供Context
import { BrowserRouter as Router, Routes, Route } from 'react-router-dom'; import EditorContext from './EditorContext'; import Page1 from './Page1'; import Page2 from './Page2'; export default function App() { // 全局状态存储编辑器内容 const [editorContent, setEditorContent] = React.useState(""); return ( <EditorContext.Provider value={{ editorContent, setEditorContent }}> <Router> <Routes> <Route path="/page1" element={<Page1 />} /> <Route path="/page2" element={<Page2 />} /> </Routes> </Router> </EditorContext.Provider> ); }
3. Page1更新全局状态
import { useContext } from 'react'; import { useNavigate } from 'react-router-dom'; import { Editor } from '@tinymce/tinymce-react'; import EditorContext from './EditorContext'; function Page1() { const editorRef = useRef(); const { setEditorContent } = useContext(EditorContext); const navigate = useNavigate(); const log = () => { if (editorRef.current) { const content = editorRef.current.getContent(); // 更新全局状态 setEditorContent(content); navigate('/page2'); } }; return ( <> <Editor apiKey='your-api-key' ref={editorRef} init={{ /* 你的编辑器配置 */ }} /> <button onClick={log}>提交跳转</button> </> ); }
4. Page2读取全局状态
import { useContext, useEffect } from 'react'; import { Editor } from '@tinymce/tinymce-react'; import EditorContext from './EditorContext'; function Page2() { const { editorContent } = useContext(EditorContext); const editorRef = useRef(); useEffect(() => { if (editorRef.current) { editorRef.current.setContent(editorContent || "EMPTY ENTRY"); } }, [editorContent]); return ( <Editor apiKey='your-api-key' disabled={true} ref={editorRef} init={{ /* 你的编辑器配置 */ }} /> ); }
三、持久化方案:localStorage存储
如果需要页面刷新后内容不丢失,可以结合localStorage实现持久化:
Page1提交时存储:
const log = () => { if (editorRef.current) { const content = editorRef.current.getContent(); localStorage.setItem('editorContent', content); navigate('/page2'); } };
Page2读取并设置:
useEffect(() => { const content = localStorage.getItem('editorContent'); if (editorRef.current) { editorRef.current.setContent(content || "EMPTY ENTRY"); } }, []);
对你疑问的解答
状态提升是否可行?
状态提升本身可行,但需要将状态提升到所有路由页面的共同父组件(比如App),再通过Context或props传递。直接在小范围内提升状态无法跨路由页面生效。useReducer/Redux是否必要?
- useReducer是useState的替代方案,适合复杂状态逻辑(比如多动作修改状态),你的场景仅需存储一个富文本内容,用useState+Context足够,没必要用useReducer。
- Redux适合大型应用多组件共享复杂状态,你的场景用Context已经足够简单,无需引入Redux增加复杂度。
内容的提问来源于stack exchange,提问作者CreativeDesign
相关产品推荐
相关产品推荐

