Contribute to this guide

guideHeadings

The Heading feature enables support for headings. These are used by the creators to structure their documents. They also aid both the readers, making the content more organized and easier to read, and the search indexers scanning for crucial information.

Headings can easily be added with toolbar dropdown, buttons or with Markdown code as you type. They can also be cleared with the remove format feature.

This feature is enabled by default in all builds.

# Heading levels

By default this feature is configured to support <h2>, <h3> and <h4> elements which are named: “Heading 1”, “Heading 2” and “Heading 3”, respectively. The rationale behind starting from <h2> is that <h1> should be reserved for the page’s main title and the page content will usually start from <h2>.

Support for adding a document title is provided through the Title plugin. This plugin is optional and needs to be added to your editor build. When it is enabled, a <h1> element pasted into the editor will be rendered as the document title.

By default, when your editor build does not include the title plugin, a <h1> element pasted into the rich-text editor is converted to <h2> (“Heading 1”).

You can read more about why the editor should not create <h1> elements for content headings in the Headings section of Editor Recommendations.

# Demo

Use the toolbar dropdown to style a heading, or type one or more # characters (depending on the heading level), followed by a space, to start a new heading with the autoformatting feature.

On the importance of headings

What is a heading?

A heading should be viewed as a title or a subtitle displayed in the document or a webpage. These are created with the <h1> to <h6> HTML tags where 1 is the largest (and most important) while 6 is the lowest level heading.

The reason to use headings

Headings serve dual purpose in the documents: they help the creators and readers interact with the content and they also affect the way search engines index the webpage.

Human interaction

Having a clearly defined structure with sections and subsections is beneficial for both the creator, who can convey their message better as well as for the readers, who can access the content with ease. Having a few good headings aids scanning and searching for specific information in the document as well as structuring the data contained.

Search engine indexing algorithms

Search engines use the headings to index the structure of the document and point to important keywords.

# Heading buttons

The heading feature lets you also use a set of heading buttons instead of the dropdown list. The toolbar buttons are configurable and it is possible to include a paragraph button, too. Compare the heading toolbar dropdown from the demo above with the heading buttons below to check the functionality and usability of this variation.

Choosing the best user experience

Usability

There are certain situations, both user-oriented or context-dependent, in which different solutions work better. Splitting the heading dropdown into separate buttons does certainly speed up the access, while at the same time taking up more space. It is up to the user to decide whether easier accessability prevails over a tidy toolbar.

Personal preference

Usability and editing needs might be one of the factors but still there is the personal preference — the user's previous experience and habits might come forth and be a decisive factor.

Flexibility

Whatever the reason may be to use both the standard heading dropdown list or the separate heading toolbar buttons, CKEditor 5 WYSIWYG editor offers both of these options for greater comfort of rich-text creation and user satisfaction.

There are more CKEditor 5 features that can help you format your content:

  • Basic font styles – The essentials, like bold, italic and others.
  • Document title – Clearly divide your content into a title and body.
  • Block indentation – Set indentation for text blocks such as paragraphs or lists.
  • Lists – Organize your content better with ordered and unordered lists you can style.
  • Remove format – Easily clean basic text formatting.
  • Autoformatting – Add formatting elements (such as headings) as you type with Markdown code.

# Configuration

# Configuring heading levels

You can configure which heading levels the editor will support and how they should be named in the Headings dropdown. Use the heading.options configuration option to do so.

For example, the following editor will support only two levels of headings — <h1> and <h2>:

<div id="editor">
    <h1>Heading 1</h1>
    <h2>Heading 2</h2>
    <p>This is <a href="https://ckeditor.com">CKEditor 5</a>.</p>
</div>
ClassicEditor
    .create( document.querySelector( '#editor' ), {
        heading: {
            options: [
                { model: 'paragraph', title: 'Paragraph', class: 'ck-heading_paragraph' },
                { model: 'heading1', view: 'h1', title: 'Heading 1', class: 'ck-heading_heading1' },
                { model: 'heading2', view: 'h2', title: 'Heading 2', class: 'ck-heading_heading2' }
            ]
        }
    } )
    .then( ... )
    .catch( ... );

Heading 1

Heading 2

This is CKEditor 5.

# Configuring custom heading elements

It is also possible to define fully custom elements for headings by using the advanced format of the heading.options configuration option.

For example, the following editor will support the following two heading options at the same time: <h2 class="fancy"> and <h2>:

<style>
    /* Styles for the heading in the content and for the dropdown item. */
    h2.fancy, .ck.ck-button.ck-heading_heading2_fancy {
        color: #ff0050;
        font-size: 17px;
    }
</style>

<div id="snippet-custom-heading-levels">
    <h1>Heading 1</h1>
    <h2>Heading 2</h2>
    <h2 class="fancy">Fancy Heading 2</h2>
    <p>This is <a href="https://ckeditor.com">CKEditor 5</a>.</p>
</div>
ClassicEditor
    .create( document.querySelector( '#editor' ), {
        heading: {
            options: [
                { model: 'paragraph', title: 'Paragraph', class: 'ck-heading_paragraph' },
                { model: 'heading1', view: 'h1', title: 'Heading 1', class: 'ck-heading_heading1' },
                { model: 'heading2', view: 'h2', title: 'Heading 2', class: 'ck-heading_heading2' },
                {
                    model: 'headingFancy',
                    view: {
                        name: 'h2',
                        classes: 'fancy'
                    },
                    title: 'Heading 2 (fancy)',
                    class: 'ck-heading_heading2_fancy',

                    // It needs to be converted before the standard 'heading2'.
                    converterPriority: 'high'
                }
            ]
        }
    } )
    .then( ... )
    .catch( ... );

Heading 1

Heading 2

Fancy Heading 2

This is CKEditor 5.

# Configuring toolbar buttons

In order to use individual toolbar buttons instead of the heading dropdown, you need to properly configure the feature. You also need to import proper UI elements; see the installation section for instructions on how to do it.

ClassicEditor
    .create( document.querySelector( '#editor' ), {
        toolbar: [ 'paragraph', 'heading1', 'heading2', 'heading3', 'heading4', 'heading5', 'heading6', '|', 'undo', 'redo' ],
        heading: {
            options: [
                { model: 'paragraph', title: 'Paragraph', class: 'ck-heading_paragraph' },
                { model: 'heading1', view: 'h1', title: 'Heading 1', class: 'ck-heading_heading1' },
                { model: 'heading2', view: 'h2', title: 'Heading 2', class: 'ck-heading_heading2' },
                { model: 'heading3', view: 'h3', title: 'Heading 3', class: 'ck-heading_heading3' },
                { model: 'heading4', view: 'h4', title: 'Heading 4', class: 'ck-heading_heading4' },
                { model: 'heading5', view: 'h5', title: 'Heading 5', class: 'ck-heading_heading5' },
                { model: 'heading6', view: 'h6', title: 'Heading 6', class: 'ck-heading_heading6' }
            ]
        }
    } )
    .then( ... )
    .catch( ... );

Heading 1

Heading 2

This is CKEditor 5.

# Installation

This feature is enabled by default in all builds. The installation instructions are for developers interested in building their own, custom editor.

To add this feature to your editor install the @ckeditor/ckeditor5-heading package:

npm install --save @ckeditor/ckeditor5-heading

And add it to your plugin list and toolbar configuration:

import Heading from '@ckeditor/ckeditor5-heading/src/heading';

ClassicEditor
    .create( document.querySelector( '#editor' ), {
        plugins: [ Heading, ... ],
        toolbar: [ 'heading', ... ]
    } )
    .then( ... )
    .catch( ... );

# Installation with toolbar heading buttons

In order to be able to configure the toolbar buttons for headings and paragraph, you need to import the following into your plugin list and configuration:

import HeadingButtonsUI from '@ckeditor/ckeditor5-heading/src/headingbuttonsui';
import ParagraphButtonUI from '@ckeditor/ckeditor5-paragraph/src/paragraphbuttonui';

Read more about installing plugins.

# Common API

The Heading plugin registers:

  • The 'heading' dropdown.

  • The 'heading' command that accepts a value based on the heading.options configuration option.

    You can turn the currently selected block(s) to headings by executing one of these commands:

    editor.execute( 'heading', { value: 'heading2' } );
    

The HeadingButtonsUI plugin registers six UI button components that will execute the 'heading' command with the proper value of the value attribute:

  • 'heading1'
  • 'heading2'
  • 'heading3'
  • 'heading4'
  • 'heading5'
  • 'heading6'

The ParagraphButtonUI plugin registers the UI button component: 'paragraph'.

We recommend using the official CKEditor 5 inspector for development and debugging. It will give you tons of useful information about the state of the editor such as internal data structures, selection, commands, and many more.

# Contribute

The source code of the feature is available on GitHub in https://github.com/ckeditor/ckeditor5/tree/master/packages/ckeditor5-heading.