Last updated Apr 27, 2018

Enabling TinyMCE plugins

Applicable:This tutorial applies to Confluence Server 5.9.1 and higher.
Level of experience:Beginner.
Time estimate:It should take you less than 1 hour to complete this tutorial.

In this tutorial, you will learn how to customize and enable a very simple TinyMCE plugin in Confluence by converting it as an Atlassian plugin.

Before you begin

To complete this tutorial, you should:

  1. Work through the Atlassian Plugin SDK tutorial.
  2. Have a basic knowledge of JavaScript.

Plugin source

If you want to skip ahead or check your work when you finish, you can find the plugin source code on Atlassian Bitbucket. Alternatively, you can download the source as a ZIP archive

To clone the repository, run the following command:

1
2
git clone git@bitbucket.org:atlassian_tutorial/tinymce-example-plugin.git

About these instructions

You can use any supported combination of operating system and IDE to create this plugin. These instructions were written using IntelliJ IDEA 2017.3 on macOS Sierra. If you use another operating system or IDE combination, you should use the equivalent operations for your specific environment.

This tutorial was last tested with Confluence 6.7.1 using the Atlassian SDK 6.3.10.

Step 1. Create the plugin project and prune the skeleton

In this step, you'll generate skeleton code for your plugin. Because you won't need many of the skeleton files, you also delete them in this step. 

  1. Open a Terminal and navigate to directory where you want to keep your plugin code.

  2. To create a plugin skeleton, run the following command:

    1
    2
    atlas-create-confluence-plugin
    

    The atlas- commands are part of the Atlassian Plugin SDK and automate some of the work of plugin development for you.  

  3. To identify your plugin, enter the following information.

    group-id

    com.example.plugins.tutorial.confluence

    artifact-id

    tinymce-example

    version

    1.0-SNAPSHOT

    package

    com.example.plugins.tutorial.confluence

  4. Confirm your entries when prompted.
    The SDK creates your project skeleton and puts it in a tinymce-example directory. 

  5. Navigate to the tinymce-example directory created in the previous step.

  6. Delete the test directories.

    Setting up testing is not part of this tutorial. Run the following commands to delete the generated test skeleton:

    1
    2
    rm -rf ./src/test/java
    rm -rf ./src/test/resources/
    
  7. Delete the unneeded Java class files.

    A basic TinyMCE plugin doesn't require you to write any Java code. To delete the generated Java class skeleton, run the following command:

    1
    2
    rm -rf ./src/main/java/com/example/plugins/tutorial/confluence/*
    
  8. Import the project into your favorite IDE.

Step 2. Edit plugin descriptor

  1. To make your resources available inside editor, replace auto generated context with editor.

    1
    2
     <atlassian-plugin name='TinyMCE Search Replace Plugin' key='tinymce.searchreplace.plugin'>
       ...
    
       <web-resource key="tinymce-example-resources" name="tinymce-example Web Resources">
               <dependency>com.atlassian.auiplugin:ajs</dependency>
    
               <resource type="download" name="tinymce-example.css" location="/css/tinymce-example.css"/>
               <resource type="download" name="tinymce-example.js" location="/js/tinymce-example.js"/>
               <resource type="download" name="images/" location="/images"/>
    
               <context>editor</context>
           </web-resource>
    </atlassian-plugin>
    
  2. To make i18n resources accessible from JavaScript, add transformation tag right inside <web-resource>:

1
2
<transformation extension="js">
    <transformer key="jsI18n"/>
</transformation>

Here is a complete atlassian-plugin.xml file:

1
2
<atlassian-plugin key="${atlassian.plugin.key}" name="${project.name}" plugins-version="2">
    <plugin-info>
        <description>${project.description}</description>
        <version>${project.version}</version>
        <vendor name="${project.organization.name}" url="${project.organization.url}" />
        <param name="plugin-icon">images/pluginIcon.png</param>
        <param name="plugin-logo">images/pluginLogo.png</param>
    </plugin-info>

    <!-- add our i18n resource -->
    <resource type="i18n" name="i18n" location="tinymce-example"/>

    <!-- add our web resources -->
    <web-resource key="tinymce-example-resources" name="tinymce-example Web Resources">
        <dependency>com.atlassian.auiplugin:ajs</dependency>
        <transformation extension="js">
            <transformer key="jsI18n"/>
        </transformation>

        <resource type="download" name="tinymce-example.css" location="/css/tinymce-example.css"/>
        <resource type="download" name="tinymce-example.js" location="/js/tinymce-example.js"/>
        <resource type="download" name="images/" location="/images"/>
        <context>editor</context>
    </web-resource>

</atlassian-plugin>

Step 3. Create a simple TinyMCE plugin for Confluence

Starting from Confluence 5.9, Confluence globals are deprecated in favor of AMD modules.

  1. To define AMD module for plugin and register plugin in TinyMCE editor, add the following code to /src/main/resources/js/tinymce-example.js file:
1
2
define('com/example/plugins', ['ajs', 'jquery'], function (AJS, $){
    "use strict";

    return {
        init : function(ed) {

        },
        getInfo : function() {
            return {
                longname : 'Example',
                author : 'Atlassian',
                authorurl : 'http://www.atlassian.com',
                version : tinymce.majorVersion + "." + tinymce.minorVersion
            };
        }
    }
});


require('confluence/module-exporter')
    .safeRequire('com/example/plugins', function(ExamplePlugin) {
        var tinymce = require('tinymce');

        tinymce.create('tinymce.plugins.ExamplePlugin', ExamplePlugin);

        // Register plugin
        tinymce.PluginManager.add('example', tinymce.plugins.ExamplePlugin);

        require('confluence-editor/loader/tinymce-bootstrap').addTinyMcePluginInit(function(settings) {
            settings.plugins += ",example";
        });
    });

So, we created and registered plugin, but it doesn't provide any functionality yet.

Step 4. Create a custom location and button

You can use any existing location group:

  • rte-toolbar-group-formatting
  • rte-toolbar-group-style
  • rte-toolbar-group-lists
  • rte-toolbar-group-task-lists
  • rte-toolbar-group-indentation
  • rte-toolbar-group-justification
  • rte-toolbar-group-files
  • rte-toolbar-group-link
  • rte-toolbar-group-table
  • rte-toolbar-group-templates
  • rte-toolbar-group-insert

In this step we will create a custom location using jQuery.

  1. Inside init() method, enter the following:

    1
    2
    $("#rte-toolbar .toolbar-primary").append($("<ul class='aui-buttons'></ul>")
                                      .addClass("rte-toolbar-group-example"));
    

    This will create a .rte-toolbar-group-example at the end of the toolbar. To add a button, use the ed.addButton() method, which takes the following parameters:

  2. Add the following lines to init() method:

    1
    2
     // Register button in a new group
    ed.addButton('confluence-example-button', {
        //default value of "toolbar" is "toolbar-primary"
        title: "",
        tooltip: AJS.I18n.getText("com.example.plugins.tutorial.confluence.tinymce-example.example.button.tooltip"),
        cmd: "mceExample",
        className: "example",
        icon: "aui-icon aui-icon-small aui-iconfont-addon",
        locationGroup: "rte-toolbar-group-example",
        weight: 0
    });
    
  3. To make sure that the button works correctly, add a command:

    1
    2
    ed.addCommand('mceExample', function() {
        alert('button pressed');
    });
    

    So, when the button is clicked, the message appears. Here is a complete tinymce-example.js file:

    1
    2
    define('com/example/plugins', ['ajs', 'jquery'], function (AJS, $){
        "use strict";
    
        return {
            init : function(ed) {
                // create new group
                $("#rte-toolbar .toolbar-primary").append($("<ul class='aui-buttons'></ul>")
                    .addClass("rte-toolbar-group-example"));
    
                ed.addCommand('mceExample', function() {
                    alert('button pressed');
                });
                // Register button in a new group
                ed.addButton('confluence-example-button', {
                    //default value of "toolbar" is "toolbar-primary"
                    title: "",
                    tooltip: AJS.I18n.getText("com.example.plugins.tutorial.confluence.tinymce-example.example.button.tooltip"),
                    cmd: "mceExample",
                    className: "example",
                    icon: "aui-icon aui-icon-small aui-iconfont-addon",
                    locationGroup: "rte-toolbar-group-example",
                    weight: 0
                });
            },
            getInfo : function() {
                return {
                    longname : 'Example',
                    author : 'Atlassian',
                    authorurl : 'http://www.atlassian.com',
                    version : tinymce.majorVersion + "." + tinymce.minorVersion
                };
            }
        }
    });
    
    require('confluence/module-exporter')
        .safeRequire('com/example/plugins', function(ExamplePlugin) {
            var tinymce = require('tinymce');
    
            tinymce.create('tinymce.plugins.ExamplePlugin', ExamplePlugin);
    
            // Register plugin
            tinymce.PluginManager.add('example', tinymce.plugins.ExamplePlugin);
    
            require('confluence-editor/loader/tinymce-bootstrap').addTinyMcePluginInit(function(settings) {
                settings.plugins += ",example";
            });
        });
    
  4. Add in i18n property to src/main/resources/tinymce-example.properties.

1
2
com.example.plugins.tutorial.confluence.tinymce-example.example.button.tooltip=Example Button

Step 5. Run your plugin 

At this point, you can run Confluence and test the plugin you have just created.

  1. To start a local Confluence instance, run the following command:

    1
    2
    atlas-run
    

    This command takes a minute or so to run. It builds your plugin code, starts a Confluence instance, and installs your plugin. When the process is finished, you see many status lines on your screen concluding with something like the following:

    1
    2
    [INFO] [talledLocalContainer] INFO: Starting Coyote HTTP/1.1 on http-1990
    [INFO] [talledLocalContainer] Tomcat 8.x started on port [1990]
    [INFO] confluence started successfully in 132s at http://localhost:1990/confluence
    [INFO] Type Ctrl-D to shutdown gracefully
    [INFO] Type Ctrl-C to exit
    

    The output includes a URL for the Confluence instance.

  2. Log in as admin / admin.
    The Confluence Dashboard appears.

  3. To open the editor, click Create button.

  4. Your button appears the last in the toolbar:

Rate this page: