How To Add A Text Editor In An HTML Form
Posted on By Mehreen Saeed | Last updated on | In Editor,
Table of contents
- Key Takeaways
- What Does "Adding a Text Editor to an HTML Form" Actually Mean?
- Method 1: CDN Setup (No Build Tool Required)
- Step 1: Add Froala's Stylesheet and Script
- Step 2: Build the Form
- Step 3: Initialise Froala and Sync to the Form
- The Complete HTML File
- Method 2: npm Install
- Method 3: React
- Froala's Key Formatting Shortcuts
- Extending with Plugins
- Framework Support at a Glance
- A Note on Content Security
- Conclusion
WYSIWYG, what you see is what you get, editors have become a standard expectation in modern web apps. Whether you’re building a CMS, a blog platform, a support system, or a customer-facing form, embedding a rich text editor gives users the formatting power they need without forcing them to write HTML by hand.
Froala is one of the most widely deployed WYSIWYG editors on the web, and for good reason. It’s fast, developer-friendly, ships with 30+ official plugins, and has first-class support for every major framework, including React, Vue, and Angular. With version 5.2 now on npm, it’s also never been easier to embed directly in an HTML form.
This guide walks you through exactly that: how to add Froala to an HTML form, how to capture its output correctly, and how to extend it with plugins for your specific use case.
Key Takeaways
- Froala turns a basic HTML
<textarea>into a rich text editor with formatting, media, and editing tools. - The easiest setup uses a CDN, requiring only a few lines of HTML and JavaScript.
- Editor content can be captured as clean HTML using
editor.html.get()and submitted with your form. - Froala supports modern frameworks like React, Vue, and Angular, along with npm-based installations.
- You can extend functionality with 30+ plugins for features like images, tables, code view, character counting, and more.
What Does “Adding a Text Editor to an HTML Form” Actually Mean?
A standard HTML <textarea> is plain text. No formatting, no toolbar, no media. When you embed Froala, you’re replacing that bare textarea with a rich editing surface that:
- Renders formatted content visually as the user types.
- Stores clean HTML output that you can persist to your database.
- Submits its content alongside your other form fields.
Method 1: CDN Setup (No Build Tool Required)
The fastest way to get Froala running is via CDN. That means you don’t need npm, bundler, or configuration files. Froala recommends the jsDelivr CDN, which mirrors the npm package.
Step 1: Add Froala’s Stylesheet and Script
In your HTML <head>, add the Froala stylesheet:
<link href="<https://cdn.jsdelivr.net/npm/froala-editor@latest/css/froala_editor.pkgd.min.css>" rel="stylesheet" type="text/css" />
Before the closing </body> tag, add the bundled Froala script (this includes all core plugins):
<script type="text/javascript" src="<https://cdn.jsdelivr.net/npm/froala-editor@latest/js/froala_editor.pkgd.min.js>"> </script>
Step 2: Build the Form
A common setup is a <textarea> where Froala loads the editor, along with a hidden <input> that stores the editor’s HTML content when the form is submitted.
<form id="contentForm" action="/submit" method="POST"> <div class="form-group"> <label for="title">Title</label> <input type="text" id="title" name="title" placeholder="Enter a title..." /> </div> <div class="form-group"> <label>Body</label> <!-- Froala mounts here --> <textarea id="froalaEditor"></textarea> <!-- Hidden field receives the HTML on submit --> <input type="hidden" id="bodyContent" name="body" /> </div> <button type="submit">Publish</button> </form>
Step 3: Initialise Froala and Sync to the Form
Now, let’s write JavaScript to initialise Froala and sync to the form:
<script>
var editor = new FroalaEditor('#froalaEditor', {
placeholderText: 'Write something...',
toolbarButtons: {
moreText: {
buttons: ['bold', 'italic', 'underline', 'strikeThrough',
'subscript', 'superscript', 'fontFamily', 'fontSize',
'textColor', 'backgroundColor', 'clearFormatting'],
buttonsVisible: 5
},
moreParagraph: {
buttons: ['alignLeft', 'alignCenter', 'alignRight', 'alignJustify',
'formatOL', 'formatUL', 'paragraphFormat', 'lineHeight'],
buttonsVisible: 4
},
moreRich: {
buttons: ['insertLink', 'insertImage', 'insertTable',
'insertHR', 'specialCharacters'],
buttonsVisible: 3
},
moreMisc: {
buttons: ['undo', 'redo', 'fullscreen', 'html'],
align: 'right',
buttonsVisible: 2
}
}
});
// Sync Froala's HTML to the hidden input before the form submits
document.getElementById('contentForm').addEventListener('submit', function () {
document.getElementById('bodyContent').value = editor.html.get();
});
</script> editor.html.get() is Froala’s API method for retrieving the current editor content as clean HTML; this is what you persist to your backend.
The Complete HTML File
Here’s the complete code for adding a text editor to an HTML form:
<!doctype html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<title>Froala Form</title>
<link
href="<https://cdn.jsdelivr.net/npm/froala-editor@latest/css/froala_editor.pkgd.min.css>"
rel="stylesheet"
type="text/css"
/>
<style>
body {
font-family: system-ui, sans-serif;
max-width: 800px;
margin: 48px auto;
padding: 0 24px;
color: #1a1a1a;
}
h1 {
margin-bottom: 28px;
font-size: 1.5rem;
}
.form-group {
margin-bottom: 20px;
}
label {
display: block;
font-weight: 600;
margin-bottom: 6px;
font-size: 14px;
}
input[type="text"] {
width: 100%;
padding: 10px 14px;
font-size: 1rem;
border: 1px solid #d1d5db;
border-radius: 6px;
}
button[type="submit"] {
margin-top: 20px;
background: #0082e6;
color: white;
padding: 10px 28px;
border: none;
border-radius: 6px;
font-size: 1rem;
cursor: pointer;
}
</style>
</head>
<body>
<h1>New Article</h1>
<form id="contentForm" action="/submit" method="POST">
<div class="form-group">
<label for="title">Title</label>
<input
type="text"
id="title"
name="title"
placeholder="Enter a title..."
required
/>
</div>
<div class="form-group">
<label>Body</label>
<textarea id="froalaEditor"></textarea>
<input type="hidden" id="bodyContent" name="body" />
</div>
<button type="submit">Publish</button>
</form>
<script
type="text/javascript"
src="<https://cdn.jsdelivr.net/npm/froala-editor@latest/js/froala_editor.pkgd.min.js>"
></script>
<script>
var editor = new FroalaEditor("#froalaEditor", {
placeholderText: "Write something...",
heightMin: 300,
});
document
.getElementById("contentForm")
.addEventListener("submit", function () {
document.getElementById("bodyContent").value = editor.html.get();
});
</script>
</body>
</html> Open this in a browser, and you have a fully functional Froala-powered rich text form with no build toolchain.
Method 2: npm Install
If you’re working on a project with a bundler (Vite, webpack, Rollup), install Froala via npm:
npm install froala-editor
Then import and initialise it in your JS/TS file:
import FroalaEditor from 'froala-editor';
import 'froala-editor/css/froala_editor.pkgd.min.css';
// Optionally import only the plugins you need
import 'froala-editor/js/plugins/image.min.js';
import 'froala-editor/js/plugins/link.min.js';
import 'froala-editor/js/plugins/table.min.js';
const editor = new FroalaEditor('#froalaEditor', {
placeholderText: 'Start writing...',
heightMin: 300,
}); Loading individual plugins instead of the bundled pkgd file keeps your bundle leaner; only pull in what your form actually needs.
Method 3: React
The React wrapper react-froala-wysiwyg is available on npm at version 5.1.0, maintained in sync with the core editor.
npm install react-froala-wysiwyg froala-editor
import React, { useRef } from 'react';
import FroalaEditorComponent from 'react-froala-wysiwyg';
import 'froala-editor/css/froala_style.min.css';
import 'froala-editor/css/froala_editor.pkgd.min.css';
import 'froala-editor/js/plugins.pkgd.min.js';
function ArticleForm() {
const [model, setModel] = React.useState('');
const config = {
placeholderText: 'Write your article...',
heightMin: 300,
toolbarButtons: {
moreText: { buttons: ['bold', 'italic', 'underline', 'fontSize', 'textColor'] },
moreParagraph: { buttons: ['alignLeft', 'alignCenter', 'formatOL', 'formatUL'] },
moreRich: { buttons: ['insertLink', 'insertImage', 'insertTable'] },
moreMisc: { buttons: ['undo', 'redo', 'fullscreen'], align: 'right' }
}
};
const handleSubmit = (e) => {
e.preventDefault();
// `model` holds the current HTML content
console.log(model);
};
return (
<form onSubmit={handleSubmit}>
<FroalaEditorComponent
tag="textarea"
config={config}
model={model}
onModelChange={setModel}
/>
<button type="submit">Publish</button>
</form>
);
} In React, Froala’s onModelChange keeps your state in sync automatically; no manual sync on submit needed.
Froala’s Key Formatting Shortcuts
Once embedded, Froala supports the standard shortcuts users already expect:
| Action | Windows / Linux | macOS |
| Select All | Ctrl + A | ⌘ + A |
| Bold | Ctrl + B | ⌘ + B |
| Italic | Ctrl + I | ⌘ + I |
| Underline | Ctrl + U | ⌘ + U |
| Strikethrough | Ctrl + S | ⌘ + S |
| Indent | Ctrl + ] | ⌘ + ] |
| Outdent | Ctrl + [ | ⌘ + [ |
For images, you can paste directly from the clipboard or use the toolbar’s “More Rich” section to insert, resize, and align images without leaving the editor.
Extending with Plugins
Froala ships with 30+ official plugins that you can selectively load, keeping only what your form needs. Some commonly used ones:
- image — Upload, resize, align, and manage images inline. Pairs with Froala’s server-side SDKs (Node.js, PHP, Python, Java) for handling file storage.
- table — Insert and edit full HTML tables with row/column controls.
- codeView — Toggle between the rich editor and raw HTML source, useful for developer-facing forms.
- wordPaste — Cleans up formatting when users paste content from Microsoft Word or Google Docs, stripping out messy inline styles.
- charCounter — Shows a live character count, useful for content forms with limits (meta descriptions, social posts, etc.).
- findReplace (introduced in 4.5.2) — A Find & Replace panel for long-form content editing.
To load a specific plugin via CDN, add it after the main script:
<script src="<https://cdn.jsdelivr.net/npm/froala-editor@latest/js/plugins/image.min.js>"></script> <script src="<https://cdn.jsdelivr.net/npm/froala-editor@latest/js/plugins/char_counter.min.js>"></script>
Or, if using npm, import just the plugins you need:
import 'froala-editor/js/plugins/image.min.js'; import 'froala-editor/js/plugins/char_counter.min.js';
Framework Support at a Glance
Froala has dedicated wrappers for React, Vue, Angular, and more, including Ruby on Rails, Django, Ember, Ionic, Gatsby, WordPress, Symfony, and CakePHP. All are maintained by the Froala team and updated in sync with the core editor. Whether you’re embedding in a vanilla HTML form today or migrating to a React app next quarter, the same configuration options carry across.
A Note on Content Security
When you receive Froala’s HTML output on your backend, treat it as untrusted user input. Always sanitise before storing or rendering server-side to prevent XSS vulnerabilities. Froala’s output is clean and semantic, but user-provided content can still be crafted maliciously. Use your backend’s sanitisation library, bleach in Python, sanitize-html in Node.js, or equivalent, between editor.html.get() and your database write.
Conclusion
Adding Froala to an HTML form takes under 10 minutes via CDN and only a few more via npm. The core pattern: mount on a textarea, call editor.html.get() on submit, write to a hidden input, stays the same whether you’re in vanilla HTML, React, or any other stack.
The real power comes once you’re set up: 30+ plugins, granular toolbar control, framework-native components, and server-side SDKs for handling file uploads. Froala is built to grow with your project, not just get you started.
To explore further, the Froala Developer Hub has ready-to-use configurations for common use cases: comments, LMS editors, email clients, and more, with live previews and copy-paste setup code.
Mehreen Saeed
Mehreen Saeed is an expert technical writer focusing on JavaScript WYSIWYG HTML Editors.
- Whats on this page hide
No comment yet, add your voice below!