Plugins

Package extensions, toolbar buttons, slash commands and translations with definePlugin().

definePlugin() is the recommended way to share functionality — in your app or as an npm package. The result is a normal Tiptap extension you add to extensions.

plugins/timestamp.ts
import { ActionButton, definePlugin } from 'vue-echo-editor'

export const Timestamp = definePlugin({
  name: 'timestamp',

  // Translations — missing keys fall back to English
  locales: {
    en: { 'timestamp.insert': 'Insert timestamp' },
    fr: { 'timestamp.insert': "Insérer l'horodatage" },
  },

  // Toolbar button (same contract as built-in extensions)
  toolbar: ({ editor, t }) => ({
    component: ActionButton,
    componentProps: {
      icon: 'Hash',
      tooltip: t('timestamp.insert'),
      action: () => editor.chain().focus().insertContent(new Date().toLocaleString()).run(),
    },
  }),

  // Slash menu entries
  slashCommands: [
    {
      name: 'insert', // extend a preset group…
      commands: [
        {
          name: 'timestamp',
          label: 'Timestamp',
          aliases: ['date', 'now'],
          iconName: 'Hash',
          action: ({ editor, range }) =>
            editor.chain().focus().deleteRange(range).insertContent(new Date().toLocaleString()).run(),
        },
      ],
    },
  ],

  // Runs when the editor is created; return a cleanup function
  setup({ editor }) {
    const onBlur = () => console.log('saved at', Date.now())
    editor.on('blur', onBlur)
    return () => editor.off('blur', onBlur)
  },
})
const extensions = [BaseKit, Bold, SlashCommand, Timestamp]

Definition

FieldTypeDescription
namestringRequired. Unique name (also the extension name).
defaultOptionsobjectOptions available as options in the callbacks; override with plugin.configure({ pluginOptions }).
extensionsAnyExtension[] | (options) => AnyExtension[]Tiptap extensions the plugin brings along.
toolbarButtonViewToolbar button(s).
slashCommandsPluginSlashGroup[] | (ctx) => PluginSlashGroup[]Slash menu contributions.
localesRecord<lang, Record<key, string>>Translations, registered when the plugin is defined.
setup({ editor, options }) => void | (() => void)Called after the editor is created; the returned function runs on destroy.

Options

const Greeting = definePlugin({
  name: 'greeting',
  defaultOptions: { text: 'Hello' },
  toolbar: ({ editor, extension }) => ({
    component: ActionButton,
    componentProps: {
      icon: 'Sparkles',
      tooltip: 'Greet',
      action: () => editor.commands.insertContent(extension.options.pluginOptions.text),
    },
  }),
})

Greeting.configure({ pluginOptions: { text: 'Karibu' } })

Slash commands

A PluginSlashGroup with the name of a preset group (format, insert, others) appends commands to it; any other name creates a new group titled title (a string or a locale key).

Publishing a plugin

  • Name the package echo-editor-plugin-* and add the echo-editor-plugin keyword.
  • List vue-echo-editor and any @tiptap/* packages as peer dependencies.
  • Ship translations for at least English through locales.