这是一个演示如何在React应用中使用UEditor Plus Designer组件的示例项目。
- React 18 - 前端框架
- TypeScript - 类型安全
- Vite - 构建工具
- Veaury - Vue与React组件互操作桥接库
本示例使用Veaury库将Vue 3编写的Designer组件桥接到React应用中。Veaury提供了无缝的Vue-React互操作能力,允许我们:
- 在React项目中直接导入和使用Vue组件
- 保持完整的类型安全支持
- 正常传递props和处理事件
- 访问组件的方法(通过ref)
examples/react/
├── src/
│ ├── UEditorPlusDesigner.tsx # Vue组件的React包装器
│ ├── App.tsx # 示例应用
│ ├── App.css # 应用样式
│ ├── main.tsx # 应用入口
│ └── index.css # 全局样式
├── public/ # 静态资源
├── index.html # HTML模板
├── vite.config.ts # Vite配置
├── tsconfig.json # TypeScript配置
└── package.json # 项目依赖
在项目根目录运行:
npm run build:vue这将在dist/vue/目录下生成Vue组件库的构建产物。
进入React示例目录:
cd examples/react
npm installnpm run dev这将启动开发服务器,默认地址为 http://localhost:3001
npm run buildimport React, { useRef } from 'react'
import { UEditorPlusDesigner } from '../../../src/react/UEditorPlusDesigner'
import 'ueditor-plus-designer/style'
function App() {
const designerRef = useRef(null)
const config = {
ueditorPath: '/ueditor-plus',
ueditorConfig: {}
}
const handleReady = () => {
console.log('Designer ready')
// Now you can safely access component methods
if (designerRef.current) {
const content = designerRef.current.getContent()
console.log('Initial content:', content)
}
}
const handleChange = (content: string) => {
console.log('Content changed:', content)
}
return (
<UEditorPlusDesigner
ref={designerRef}
config={config}
onReady={handleReady}
onChange={handleChange}
/>
)
}| 属性 | 类型 | 默认值 | 描述 |
|---|---|---|---|
config |
DesignerConfig |
{} |
编辑器配置对象 |
isIframe |
boolean |
false |
是否在iframe模式下运行 |
onReady |
() => void |
- | 编辑器就绪时的回调 |
onChange |
(content: string) => void |
- | 内容变化时的回调 |
onConfirm |
(content: string) => void |
- | 确认时的回调(iframe模式) |
interface DesignerConfig {
/** UEditor路径 */
ueditorPath?: string
/** UEditor配置 */
ueditorConfig?: Record<string, any>
/** 分类加载器 */
categoryLoader?: () => Promise<any[]>
/** 素材加载器 */
styleLoader?: (params?: any) => Promise<any>
}通过ref可以访问以下方法:
interface DesignerRef {
/** 获取编辑器内容 */
getContent: () => string
/** 设置编辑器内容 */
setContent: (content: string) => void
}示例:
const designerRef = useRef(null)
// 在组件ready后访问方法
const handleReady = () => {
// Veaury包装后,ref直接指向Vue组件实例
if (designerRef.current) {
const content = designerRef.current.getContent()
console.log('Content:', content)
designerRef.current.setContent('<div>New content</div>')
}
}
<UEditorPlusDesigner
ref={designerRef}
onReady={handleReady}
/>重要:
- Ref访问: 由于使用Veaury桥接,ref通过
__veauryVueRef__属性访问Vue组件实例。包装器已处理此细节,你可以直接调用designerRef.current.getContent()等方法。 - 时机要求: 确保在组件ready后(onReady回调触发后)再调用这些方法。
- 详细说明: 参见REF_ACCESS_FIX.md了解ref访问的实现细节。
确保UEditor资源文件可访问。本示例通过Vite代理配置从unpkg CDN获取UEditor文件:
// vite.config.ts
server: {
proxy: {
'/ueditor-plus': {
target: 'https://unpkg.com/ueditor-plus-main@2.0.0/dist-min/',
changeOrigin: true,
rewrite: (path) => path.replace(/^\/ueditor-plus/, ''),
}
}
}生产环境中,你应该将UEditor文件放在public/ueditor-plus/目录中。
确保导入组件样式:
import 'ueditor-plus-designer/style'
// 或本地开发时
import '../../../dist/vue/vue-style.css'本示例同时需要React和Vue依赖:
react>= 18.0.0react-dom>= 18.0.0vue>= 3.4.0veaury>= 2.2.0
Veaury负责桥接两个框架,因此两者都是必需的。
使用Veaury时,Vite配置必须同时包含React和Vue插件:
import react from '@vitejs/plugin-react'
import vue from '@vitejs/plugin-vue'
export default defineConfig({
plugins: [react(), vue()]
})由于使用桥接方案,React应用会同时包含Vue和React运行时。这会增加大约100KB左右的bundle大小(gzip后约40KB)。如果对bundle大小有严格要求,可以考虑:
- 使用代码分割,按需加载Designer组件
- 完全用React重写Designer组件(需要更多开发时间)
你可以通过config传递自定义的素材加载器:
const config = {
ueditorPath: '/ueditor-plus',
categoryLoader: async () => {
const response = await fetch('/api/categories')
return response.json()
},
styleLoader: async (params) => {
const response = await fetch('/api/materials', {
method: 'POST',
body: JSON.stringify(params)
})
return response.json()
}
}
<UEditorPlusDesigner config={config} />确保已经:
- 构建了Vue组件库(
npm run build:vue) - 安装了所有依赖(包括veaury)
- 正确配置了Vite插件(react + vue)
检查:
- UEditor路径配置是否正确
- 网络代理配置是否生效
- 浏览器控制台是否有资源加载错误
确保TypeScript配置正确:
tsconfig.json中包含正确的jsx设置- 安装了
@types/react和@types/react-dom
Apache License 2.0 - 压缩版免费使用,商用或源码需授权。详见项目根目录 LICENSE 文件。