写项目中遇到了富文本编辑器的需求,我找了好多插件发现还是react-quill.js更好用,整理了一下React+TypeScript实现富文本编辑器React-quill,前端进行操作上传信息,可以提供给后端生成信息流,代码如下:
1. 安装react-quill组件,使用npm命令安装:
npm install react-quill --save
2. 安装react-dropzone和axios组件,使用npm命令安装:
npm install react-dropzone axios --save
3.创建一个新的React函数组件,定义富文本编辑器需要的 state,并引入React-quill、axios和react-dropzone组件,其中React state中主要包括编辑器的内容(value)、编辑器是否聚焦(isFocused)和上传图片的url(imageUrl):
import React, { useState, useCallback } from 'react';
import ReactQuill from 'react-quill';
import 'react-quill/dist/quill.snow.css';
import Dropzone from 'react-dropzone';
import axios from 'axios';
interface Props {}
const RichTextEditor: React.FC<Props> = () => {
const [value, setValue] = useState<string>('');
const [isFocused, setIsFocused] = useState<boolean>(false);
const [imageUrl, setImageUrl] = useState<string>('');
const handleChange = useCallback(
(value: string) => {
setValue(value);
},
[setValue],
);
const handleFocus = useCallback(() => {
setIsFocused(true);
}, [setIsFocused]);
const handleBlur = useCallback(() => {
setIsFocused(false);
}, [setIsFocused]);
const handleUpload = useCallback(
async (acceptedFiles: Blob[]) => {
try {
const formData = new FormData();
formData.append('file', acceptedFiles[0]);
const res = await axios.post('/upload', formData, {
headers: {
'Content-Type': 'multipart/form-data',
},
});
setImageUrl(res.data.url);
} catch (error) {
console.error(error);
}
},
[setImageUrl],
);
return (
<div>
<ReactQuill
value={value}
onChange={handleChange}
onFocus={handleFocus}
onBlur={handleBlur}
modules={modules}
/>
<Dropzone onDrop={handleUpload}>
{({ getRootProps, getInputProps, isDragActive }) => {
return (
<div {...getRootProps()}>
<input {...getInputProps()} />
{isDragActive ? (
<p>请拖动您的文件到这个区域或者点击以上传文件!</p>
) : (
<p>请拖动您的文件到这个区域或者点击以上传文件!</p>
)}
</div>
);
}}
</Dropzone>
{imageUrl ? <img src={imageUrl} alt="Preview" /> : null}
<button onClick={() => handleSubmit(value, imageUrl)}>提交</button>
</div>
);
};
export default RichTextEditor;
4. 在React组件中定义富文本编辑器需要的modules(需要emoji表情或者其他操作可自行加上):
const modules = {
toolbar: {
container: [
[
{ font: [] },
{ size: [] },
{ color: [] },
{ background: [] },
{ align: [] },
],
['bold', 'italic', 'underline', 'strike', 'blockquote'],
[{ list: 'ordered' }, { list: 'bullet' }, { indent: '-1' }, { indent: '+1' }],
['link', 'image', 'video'],
['clean'],
],
},
clipboard: {
matchVisual: false,
},
};
5. 在React组件中定义提交函数handleSubmit(),将编辑器的内容和上传的图片url提交到后端处理:
const handleSubmit = async (value: string, imageUrl: string) => {
try {
const response = await axios.post('/api/add-news', {
content: value,
cover: imageUrl,
});
console.log(response.data);
} catch (error) {
console.error(error);
}
};
大致效果如下,样式可根据情况做写调整
以上就是实现富文本编辑器的过程了,handleSubmit里可以打印出信息流,保存这个传给后端即可。
如果帮到你解决了这个问题,可以点个赞哦~