---
title: "Events in Tiptap"
description: "Use and handle various events in Tiptap, including creation, updates, focus, blur, and destruction. More in the docs!"
canonical_url: "https://tiptap.dev/docs/editor/api/events"
---

# Events in Tiptap

Use and handle various events in Tiptap, including creation, updates, focus, blur, and destruction. More in the docs!

The editor fires a few different events that you can hook into. Let’s have a look at all the available events first.

## List of available events

| Event Name        | Description                                                                                                                             |
| ----------------- | --------------------------------------------------------------------------------------------------------------------------------------- |
| `beforeCreate`    | Before the editor view is created.                                                                                                      |
| `create`          | When the editor is fully initialized and ready.                                                                                         |
| `update`          | When there is a change in the content.                                                                                                  |
| `selectionUpdate` | When the selection changes within the editor.                                                                                           |
| `transaction`     | When the editor state changes due to any operation.                                                                                     |
| `focus`           | When the editor gains focus.                                                                                                            |
| `blur`            | When the editor loses focus.                                                                                                            |
| `destroy`         | When the editor instance is being destroyed.                                                                                            |
| `paste`           | When content is pasted into the editor.                                                                                                 |
| `drop`            | When content is dropped into the editor.                                                                                                |
| `delete`          | When content is deleted from the editor.                                                                                                |
| `contentError`    | The content does not match the schema. [Read more here](https://tiptap.dev/docs/editor/core-concepts/schema.md#invalid-schema-handling) |

## Register event listeners

There are three ways to register event listeners.

### Option 1: Configuration

You can define your event listeners on a new editor instance right-away:

```js
const editor = new Editor({
  onBeforeCreate({ editor }) {
    // Before the view is created.
  },
  onCreate({ editor }) {
    // The editor is ready.
  },
  onUpdate({ editor }) {
    // The content has changed.
  },
  onSelectionUpdate({ editor }) {
    // The selection has changed.
  },
  onTransaction({ editor, transaction }) {
    // The editor state has changed.
  },
  onFocus({ editor, event }) {
    // The editor is focused.
  },
  onBlur({ editor, event }) {
    // The editor isn’t focused anymore.
  },
  onDestroy() {
    // The editor is being destroyed.
  },
  onPaste(event: ClipboardEvent, slice: Slice) {
    // The editor is being pasted into.
  },
  onDrop(event: DragEvent, slice: Slice, moved: boolean) {
    // The editor is being pasted into.
  },
  onDelete({ type, deletedRange, newRange, partial, node, mark, from, to, newFrom, newTo }) {
    // Content was deleted from the editor (either a node or mark).
  },
  onContentError({ editor, error, disableCollaboration }) {
    // The editor content does not match the schema.
  },
})
```

### Option 2: Binding

Or you can register your event listeners on a running editor instance:

#### Bind event listeners

```js
editor.on('beforeCreate', ({ editor }) => {
  // Before the view is created.
})

editor.on('create', ({ editor }) => {
  // The editor is ready.
})

editor.on('update', ({ editor }) => {
  // The content has changed.
})

editor.on('selectionUpdate', ({ editor }) => {
  // The selection has changed.
})

editor.on('transaction', ({ editor, transaction }) => {
  // The editor state has changed.
})

editor.on('focus', ({ editor, event }) => {
  // The editor is focused.
})

editor.on('blur', ({ editor, event }) => {
  // The editor isn’t focused anymore.
})

editor.on('destroy', () => {
  // The editor is being destroyed.
})

editor.on('paste', ({ event, slice, editor }) => {
  // The editor is being pasted into.
})

editor.on('drop', ({ editor, event, slice, moved }) => {
  // The editor is being destroyed.
})

editor.on('delete', ({ type, deletedRange, newRange, partial, node, mark }) => {
  // Content was deleted from the editor (either a node or mark).
})

editor.on('contentError', ({ editor, error, disableCollaboration }) => {
  // The editor content does not match the schema.
})
```

#### Unbind event listeners

If you need to unbind those event listeners at some point, you should register your event listeners with `.on()` and unbind them with `.off()` then.

```js
const onUpdate = () => {
  // The content has changed.
}

// Bind …
editor.on('update', onUpdate)

// … and unbind.
editor.off('update', onUpdate)
```

### Option 3: Extensions

Moving your event listeners to custom extensions (or nodes, or marks) is also possible. Here’s how that would look like:

```js
import { Extension } from '@tiptap/core'

const CustomExtension = Extension.create({
  onBeforeCreate({ editor }) {
    // Before the view is created.
  },
  onCreate({ editor }) {
    // The editor is ready.
  },
  onUpdate({ editor }) {
    // The content has changed.
  },
  onSelectionUpdate({ editor }) {
    // The selection has changed.
  },
  onTransaction({ editor, transaction }) {
    // The editor state has changed.
  },
  onFocus({ editor, event }) {
    // The editor is focused.
  },
  onBlur({ editor, event }) {
    // The editor isn’t focused anymore.
  },
  onDestroy() {
    // The editor is being destroyed.
  },
  onPaste(event: ClipboardEvent, slice: Slice) {
    // The editor is being pasted into.
  },
  onDrop(event: DragEvent, slice: Slice, moved: boolean) {
    // The editor is being pasted into.
  },
  onDelete({ type, deletedRange, newRange, partial, node, mark }) {
    // Content was deleted from the editor (either a node or mark).
  },
  onContentError({ editor, error, disableCollaboration }) {
    // The editor content does not match the schema.
  },
})
```
