Getting Started
Installation
ZynText is a self-contained plugin. Copy the zyntext/ folder into your project and include the two dist files.
Option A: Use pre-built files
Include the CSS and JS from the dist/ directory:
<!-- In your <head> -->
<link rel="stylesheet" href="path/to/zyntext/dist/zyntext.css">
<!-- Before </body> -->
<script src="path/to/zyntext/dist/zyntext.js"></script>
Option B: Build from source
If you want to customize or extend the source, build it with Vite:
# Install dependencies (from the project root)
npm install
# Build ZynText
npm run build:zyntext
# Or with the Vite CLI directly
npx vite build --config public/assets/plugins/zyntext/vite.config.js
This produces dist/zyntext.js (IIFE bundle) and dist/zyntext.css.
Option C: Laravel integration
In a Laravel project, use the asset() helper:
<link rel="stylesheet" href="{{ asset('assets/plugins/zyntext/dist/zyntext.css') }}">
<script src="{{ asset('assets/plugins/zyntext/dist/zyntext.js') }}"></script>
Your First Editor
ZynText enhances a standard <textarea> element. The textarea is hidden and replaced with a rich-text editing surface. Content is automatically synced back to the textarea on every change and on form submission.
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>ZynText Demo</title>
<link rel="stylesheet" href="zyntext/dist/zyntext.css">
</head>
<body>
<form method="post" action="/save">
<textarea id="content" name="content">
<p>Hello, <strong>world</strong>!</p>
</textarea>
<button type="submit">Save</button>
</form>
<script src="zyntext/dist/zyntext.js"></script>
<script>
const editor = new ZynText(document.getElementById('content'), {
toolbar: 'standard',
height: 400,
placeholder: 'Start writing...'
});
</script>
</body>
</html>
Note
The textarea's existing HTML content is loaded into the editor automatically. When the form is submitted, the editor's content (with portable inline styles) is synced back to the textarea.
Multiple Editors
You can create as many editors as you need on the same page. Each operates independently:
document.querySelectorAll('textarea.wysiwyg').forEach(textarea => {
new ZynText(textarea, {
toolbar: textarea.dataset.toolbar || 'standard',
height: parseInt(textarea.dataset.height) || 300,
lang: document.documentElement.lang || 'en'
});
});
Destroying an Editor
Call destroy() to restore the original textarea and clean up all DOM elements and event listeners:
const editor = new ZynText(textarea, { toolbar: 'minimal' });
// Later...
editor.destroy(); // Textarea is visible again with final content
File Structure
zyntext/
├── dist/
│ ├── zyntext.js ← Include this (IIFE, ~94 KB)
│ └── zyntext.css ← Include this (~19 KB)
├── src/
│ ├── js/
│ │ ├── index.js ← Entry point
│ │ ├── core/ ← Editor, ContentManager, SelectionManager, CommandBus, EventEmitter
│ │ ├── toolbar/ ← Toolbar, ToolbarItem, presets
│ │ ├── icons/ ← BootstrapIconProvider, SvgIconProvider, SVG paths
│ │ ├── plugins/ ← 13 plugins (Format, Link, Image, Table, etc.)
│ │ └── i18n/ ← Translations (14 languages)
│ └── scss/
│ ├── zyntext.scss
│ └── _*.scss ← Partials (variables, toolbar, content, modals, etc.)
├── docs/ ← This documentation
└── vite.config.js ← Build config (Vite library mode)
Requirements
- A modern browser (Chrome/Edge 90+, Firefox 90+, Safari 15+)
- Optional: Bootstrap Icons CSS if using the
bootstrapicon provider (default). Not needed if using thesvgicon provider. - For building from source: Node.js 18+ and npm
Next Steps
- Configuration: Explore all available options
- Toolbar Presets: Choose the right toolbar for your use case
- Image Uploads: Set up server-side image handling
- Internationalization: Switch languages