Including CKEditor 5 in a React and TypeScript Project with Vite

Example: We’ll use CKEditor 5 within a ReactJS + TypeScript project generated with ViteJS.

CKEditor is an open-source HTML/WYSIWYG text editor that adds word processor-like features to web pages.

New Project

Create a new project with Vite using the following command:

				
					npm create vite

				
			

Framework and Template

Select React and TypeScript.

Installing Dependencies

Enter the project directory and install initial packages and dependencies:

				
					cd project-name
npm install

				
			

Install CKEditor 5

Install CKEditor 5 via NPM with this command:

				
					npm install --save @ckeditor/ckeditor5-react @ckeditor/ckeditor5-build-classic


				
			

This installs the latest CKEditor 5 and a preconfigured version of the Classic Editor.

Configure CKEditor in a React App

In the Vite configuration file, import and set up CKEditor 5 to use it in the React app. Modify vite.config.ts:

				
					import { createRequire } from 'node:module';
const require = createRequire(import.meta.url);
import { defineConfig } from 'vite';
import ckeditor5 from '@ckeditor/vite-plugin-ckeditor5';

export default defineConfig({
    plugins: [
        ckeditor5({ theme: require.resolve('@ckeditor/ckeditor5-theme-lark') })
    ]
});
				
			

Import Necessary Modules

				
					import React, { useState } from 'react';
import ClassicEditor from '@ckeditor/ckeditor5-build-classic';
import { CKEditor } from '@ckeditor/ckeditor5-react';
				
			

Include the <CKEditor> Component

				
					function App() {
  const [editorData, setEditorData] = useState('');

  const handleEditorDataChange = (event: any, editor: any) => {
    const data = editor.getData();
    setEditorData(data);
  };

  return (
    <div>
      <h2>Text Editor</h2>
      <CKEditor
        editor={ClassicEditor}
        data={editorData}
        onChange={handleEditorDataChange}
      />
    </div>
  );
}
				
			

In the code above, we import CKEditor modules and configure the CKEditor component with these properties:

  • editor: The CKEditor 5 instance, in this case, ClassicEditor.
  • data: Initial editor content (empty string).
  • onChange: Updates the editor state whenever the content changes.

Example Plugins and Full Code in App.tsx

Install specific plugins:

				
					npm i @ckeditor/ckeditor5-editor-classic @ckeditor/ckeditor5-basic-styles @ckeditor/ckeditor5-essentials @ckeditor/ckeditor5-paragraph @ckeditor/ckeditor5-block-quote @ckeditor/ckeditor5-link @ckeditor/ckeditor5-image @ckeditor/ckeditor5-media-embed

				
			

Full Example Code:

				
					import React, { Component } from 'react';
import { CKEditor } from '@ckeditor/ckeditor5-react';
import ClassicEditor from '@ckeditor/ckeditor5-editor-classic/src/classiceditor';
import Bold from '@ckeditor/ckeditor5-basic-styles/src/bold';
import Italic from '@ckeditor/ckeditor5-basic-styles/src/italic';
import Essentials from '@ckeditor/ckeditor5-essentials/src/essentials';
import Paragraph from '@ckeditor/ckeditor5-paragraph/src/paragraph';
import BlockQuotePlugin from '@ckeditor/ckeditor5-block-quote/src/blockquote';
import LinkPlugin from '@ckeditor/ckeditor5-link/src/link';
import ImageInsert from '@ckeditor/ckeditor5-image/src/imageinsert';
import MediaEmbed from '@ckeditor/ckeditor5-media-embed/src/mediaembed';

class App extends Component {
    render() {
        return (
            <div className="App">
                <CKEditor
                    editor={ClassicEditor}
                    config={{
                        plugins: [
                            Paragraph, Bold, Italic, Essentials, BlockQuotePlugin,
                            LinkPlugin, ImageInsert, MediaEmbed
                        ],
                        toolbar: {
                            items: [
                                'bold', 'italic', 'link', 'blockQuote', 
                                'insertImage', 'mediaEmbed', 'undo', 'redo'
                            ]
                        }
                    }}
                    data="<p>Hello from the first CKEditor working with React!</p>"
                    onReady={(editor: any) => {
                        console.log('Editor1 is ready to use!', editor);
                    }}
                    onChange={(event, editor) => {
                        const data = editor.getData();
                        console.log({ event, editor, data });
                    }}
                />
            </div>
        );
    }
}

export default App;

				
			

CKEditor Error Solution

If you encounter an error like:

				
					ckeditor.js:5 Uncaught CKEditorError: ckeditor-duplicated-modules

				
			

Fix it by creating vite-env.d.ts in the src directory:

				
					declare module '@ckeditor/ckeditor5-react';
declare module '@ckeditor/ckeditor5-build-classic';
declare module '@ckeditor/*' {
    const classes: any;
    export default classes;
}

				
			

Finally, run the React app with Vite:

				
					npm run dev
				
			

Result

Facebook
Twitter
LinkedIn