Skip to content

notectl

The rich text editor that gets out of your way. Zero framework lock-in, full control over every feature, and an architecture built for the real world.

Most rich text editors force you into their world. notectl works in yours. Ship a <notectl-editor> Web Component that drops into React, Vue, Angular, Svelte, or plain HTML with zero adapters, zero wrappers, and zero compromises.

One tag. Any framework.

<notectl-editor> is a native custom element. No React bindings, no Vue wrappers, no Angular modules. Import it, drop it in, done. Framework upgrades never break your editor.

Only ship what you use

Every feature is a plugin. Bold, tables, fonts, checklists — compose exactly the editor you need. Your bundle stays lean, your users stay happy.

State you can trust

Immutable state, atomic transactions, invertible steps. Every change is predictable, every change is undoable. No more “how did the DOM get into this state?” debugging.

Toolbar in one line

Configure your toolbar with a simple array. Group plugins visually, reorder freely, add separators — all declarative, zero DOM manipulation.

import { createEditor } from '@notectl/core';
const editor = await createEditor({
placeholder: 'Start typing...',
});
document.getElementById('editor')!.appendChild(editor);

18 built-in plugins

Text formatting, headings, lists, tables, links, code blocks, images, fonts, font sizes, text colors, alignment, blockquotes, strikethrough, superscript/subscript, highlight, horizontal rules, hard breaks, and a declarative toolbar. Every plugin ships with keyboard shortcuts, input rules, and accessible toolbar items.

Markdown-style shortcuts

Type # for headings, - for bullet lists, 1. for numbered lists, > for blockquotes, --- for horizontal rules, [ ] for checklists. Your power users will feel right at home.

Tables that actually work

Full grid picker for insertion, multi-cell selection, row/column operations, keyboard navigation between cells. Not a bolted-on afterthought.

Custom fonts made easy

Pass a FontDefinition with WOFF2/TTF/OTF sources. notectl injects @font-face rules automatically. Bundle starter fonts (Fira Sans, Fira Code) or bring your own.

notectl follows a strict unidirectional data flow. Every user action creates a Transaction with atomic, invertible Steps. Transactions pass through a priority-ordered middleware chain, produce a new immutable EditorState, and the view layer patches only the changed DOM blocks.

Input → Transaction (Steps) → Middleware → New State → DOM Reconciliation

This gives you predictable updates, built-in undo/redo, plugin interception points, and state transitions that are pure functions — easy to test, easy to reason about.

LayerWhat it does
ModelImmutable Document, BlockNode, TextNode, InlineNode, Mark, Selection
StateEditorState container, Transaction builder, History with step inversion
ViewBlock-level DOM reconciliation, selection sync, input handling
CommandstoggleMark, splitBlock, deleteBackward, insertTable, and more
PluginsSelf-contained feature modules with schema, commands, keymaps, toolbar items