editor-text-rich
v1.0.64
Published
A premium Google Docs-style rich text editor for React with comments and mentions.
Maintainers
Readme
Editor Text Rich 🖋️
A professional, high-performance rich text editor for React. Designed for collaborative environments with integrated commenting systems, @mentions, seamless media management, and advanced document export capabilities.
✨ Latest Features
- ⚡ High Performance: Built with React & Vite for lightning-fast editing.
- � DOCX & Document Import: Seamlessly insert content from
.docxfiles directly into your cursor position. - 🖼️ High-Res Export: Combined export dropdown to download your document as professional PDF (multi-page, WYSIWYG) or high-resolution JPG.
- �💬 Collaborative Comments: Optional gutter-based comment system. Simply omit the
commentsprop to disable. - 🔄 Threaded Conversations: Support for infinite nested replies within comments.
- 👤 User Mentions: Robust @mention engine with customizable dropdowns and avatars.
- � Fully Responsive: Modern, touch-friendly Toolbar and MenuBar with smooth horizontal scrolling for mobile devices.
- �📁 Media Powerhouse: Drag & drop support for Images, Videos, and PDFs.
- 📏 Interactive Resizers: Real-time resizing handles for images and tables with alignment controls.
- 🗂️ Global Item Inserter: Built-in support for searching and inserting items/cards from a global data source with a premium picker dialog.
- ⌨️ Keyboard Navigation: Robust
Escapekey support to instantly close all overlays (Search, TOC, Link Editor, Item Picker). - 🎨 Premium Design: Clean, modern aesthetics with smooth animations and high-contrast accessibility.
📦 Installation
npm install editor-text-rich
# or
yarn add editor-text-rich🚀 Getting Started
import React, { useState, useRef } from "react";
import {
EditorTextRich,
type Comment,
type MentionUser,
type EditorRef,
} from "editor-text-rich";
// Import CSS styles
import "editor-text-rich/style.css";
const USERS: MentionUser[] = [
{
id: "1",
username: "samsul",
fullName: "Samsul Arifin",
avatar: "https://i.pravatar.cc/150?u=samsul",
},
];
export default function MyEditor() {
const [html, setHtml] = useState("<h1>Start writing...</h1>");
const [comments, setComments] = useState<Comment[]>([]);
const editorRef = useRef<EditorRef>(null);
return (
<div style={{ height: "800px" }}>
<EditorTextRich
ref={editorRef}
value={html}
comments={comments} // Pass empty array [] to enable comments, or omit to hide
onChange={(newHtml, newComments) => {
setHtml(newHtml);
setComments(newComments);
}}
onUploadFile={async (file) => URL.createObjectURL(file)}
mentions={USERS}
currentUser={USERS[0]}
/>
</div>
);
}📑 API Reference
EditorTextRich Props
| Property | Type | Default | Description |
| :---------------- | :-------------------------------------------- | :------------------- | :----------------------------------------------------------------------- |
| value | string | "" | The initial HTML content. |
| comments | Comment[] | undefined | Array of comment data. Omit this prop completely to hide Comment UI. |
| onChange | (html: string, comments: Comment[]) => void | undefined | Callback for every content/comment update. |
| onUploadFile | (file: File) => Promise<string> | undefined | Function to handle external file uploads. |
| mentions | MentionUser[] | [] | List of users for the @mention dropdown. |
| currentUser | MentionUser | undefined | The user currently active for commenting/mentions. |
| placeholder | string | "Tulis sesuatu..." | Text to display when empty. |
| disabled | boolean | false | If true, the editor becomes read-only. |
| minHeight | string \| number | undefined | Minimum height of the content area. |
| maxHeight | string \| number | undefined | Maximum height of the content area. |
| toolbar | ToolbarConfig | undefined | Custom toolbar tool selection and grouping. |
| hideMenuBar | boolean | false | If true, the top menu bar (File, Edit, etc) is hidden. |
| textColor | string | undefined | Default text color for the content. |
| fontSize | string \| number | undefined | Default font size for the content. |
| onInsertCard | () => Promise<string \| null> | undefined | Custom fallback function to provide the HTML for the "Insert Card" tool. |
| insertCardsData | CardData[] | undefined | List of items to show in the built-in global picker dialog. |
Data Models
Comment Object
interface Comment {
id: string;
authorName: string;
authorAvatar?: string;
text: string;
timestamp: number;
selectedText: string;
resolved: boolean;
replies: Reply[];
}MentionUser Object
interface MentionUser {
id: string | number;
username: string;
fullName: string;
avatar?: string;
}CardData Object (for Global Inserter)
interface CardData {
id: string;
title: string; // Main display text (can include IDs or Project names)
description?: string; // Optional context shown below title
link?: string; // If provided, the title/description becomes a clickable link
}Custom Toolbar Tools
Available tool identifiers for your ToolbarConfig.items:
- General:
undo,redo,clearFormat,code,maximize,toc,search - Typography:
fontSize,h1,h2,bold,italic,underline,strikethrough,subscript,superscript,textColor,highlight - Alignment:
alignment(Dropdown containing Left, Center, Right, Justify) - Lists & Indent:
bulletList,orderedList,indent,outdent - Insertion:
link,image,table,quote,importDocx,insertCard - Export:
export(Combined Dropdown for JPG and PDF download)
🎨 Styling
The editor appearance can be easily customized using CSS variables:
:root {
--editor-primary: #3b82f6; /* Primary action color */
--editor-bg: #ffffff; /* Surface color */
--editor-font: "Inter", sans-serif;
--comment-icon-bg: #2563eb; /* Icon color in gutter */
}📄 License
This project is licensed under the MIT License - see the LICENSE file for details.
Developed with ❤️ by Samsul Arifin
