XF 2.2 Add Froala editor button alias

Rasmus Vind

Well-known member
My site supports a special programming language highlighting with [code=jass]. I very much like to highlight this, so my graphic artist created an icon for it. The only problem is that I can't seem to create a custom button for it. The only real way to do this from my eyes is to create a new BB code tag for [jass] but I'd rather piggy back on the existing foundation of [code].

I was looking into running this code on the clientside, but it did not do anything:

JavaScript:
const name = 'code';
const defTitle = 'JASS code highlight';
const tagUpper = 'code';
const template = {
    template: 'image',
    SRC: '"' + XF.canonicalizeUrl('styles/default/ratory/trigger_tag.png') + '"',
    ALT: '"' + defTitle + '"'
};

var config = {
    title: defTitle,
    icon: name,
    undo: true,
    focus: true,
    callback: function()
    {
        XF.EditorHelpers.wrapSelectionText(
            this,
            '[' + tagUpper + '=jass]',
            '[/' + tagUpper + ']',
            true
        );
    }
};
FroalaEditor.DefineIcon(name, template);
FroalaEditor.RegisterCommand(name, config);
XF.editorStart.custom.push(name);

Any tips?
 
Okay, I found a super hacky way of doing this.

I created a template modification for the template editor:

search:
Code:
, xf/editor.js
replace:
Code:
, xf/editor.js, rasmus-test.js

and rasmus-test.js contains:
JavaScript:
!(function ($, window, document, _undefined) {
    'use strict';

    console.log('rasmus-test.js loaded');

    XF.Element.extend('editor', {
        init: function (...args) {
            console.log('HI INIT', args, this);

            this.$target.on('editor:config', (e, config, xfEditor) => {
                // console.log('editor:config');
                // console.log(config);
                // console.log(xfEditor);
                config.toolbarButtons.moreRich.buttons.push('jass');

                this.extendEditor();
            });

            this.__proto__.__proto__.init.call(this);
        },

        extendEditor: function () {
            const name = 'jass';
            const defTitle = 'JASS code highlight';
            const tagUpper = 'code';

            const template = {
                template: 'image',
                SRC:
                    '"' +
                    XF.canonicalizeUrl('styles/default/ratory/jass_tag.png') +
                    '"',
                ALT: '"' + defTitle + '"',
            };

            var config = {
                title: defTitle,
                icon: name,
                undo: true,
                focus: true,
                callback: function () {
                    XF.EditorHelpers.wrapSelectionText(
                        this,
                        '[' + tagUpper + '=jass]',
                        '[/' + tagUpper + ']',
                        true
                    );
                },
            };

            FroalaEditor.DefineIcon(name, template);
            FroalaEditor.RegisterCommand(name, config);

            XF.editorStart.custom.push(name);
        },
    });
})(jQuery, window, document);

Next step will be to create a dummy bb code in the database, maybe called [placeholder_jass_placeholder] and then in this JS script search through the structures to just replace the callback with the one I want, that is an alias of [code].

Still hacky, but customizable at least.
 
I recommend against creating a new button for that and just extend the existing code BB code to support it.
  1. Add the code language under ACP > Options > Message Options > Allowed code BB code block languages
  2. Create a phrase (code_language.<your_code_language>)
  3. Extend Prism.js (XFs code syntax highlight library) to add syntax highlighting for your own language
  4. Educate your users on how to use it
 
I think you misunderstand. I already added an extra language to the [code] tag, I just want a separate button in the editor to insert [code=jass] because it's very significant to my community. Thus, an editor button alias.
 
Okay, so now I have finished this feature. I added a dummy Bb code (so I can add a button in the button manager) and then in a JS script, I replace its function like so:
JavaScript:
!(function ($, window, document, _undefined) {
    'use strict';

    XF.Element.extend('editor', {
        init: function (...args) {
            this.$target.on('editor:config', (e, config, xfEditor) => {
                if (!FroalaEditor.COMMANDS.xfCustom_jass_alias_msg_ralle) {
                    return;
                }
                FroalaEditor.COMMANDS.xfCustom_jass_alias_msg_ralle.callback = function () {
                    XF.EditorHelpers.wrapSelectionText(
                        this,
                        '[code=jass]',
                        '[/co'+'de]',
                        true
                    );
                };
            });
            this.__proto__.__proto__.init.call(this);
        },
    });
})(jQuery, window, document);

NOTE: I split the ending code tag in two to prevent the BB formatter from thinking the code piece is done.
 
@Ralle rather than this.__proto__.__proto__.init.call there is a built in feature to XF.extend for this;

Code:
XF.Editor = XF.extend(XF.Editor, {
    __backup: {
        'normalizePaste': 'svAdvancedBbCode_normalizePaste'
    },

    normalizePaste: function(content) {
...
        content = this.svAdvancedBbCode_normalizePaste(content);
...
        return content;
    }
});
Make sure the svAdvancedBbCode_normalizePaste part is unique! ie addonName_<originalFunction>
 
I will give it a try. Thanks! It looks... Interesting. But I will figure it out :)

Update: This is AWESOME. Here's the latest version of my code:
JavaScript:
!(function ($, window, document, _undefined) {
    'use strict';
    XF.Editor = XF.extend(XF.Editor, {
        __backup: {
            startInit: 'vinditBbCode_startInit',
        },
        startInit: function () {
            this.vinditBbCode_startInit();
            if (!FroalaEditor.COMMANDS.xfCustom_jass_alias_msg_ralle) {
                return;
            }
            FroalaEditor.COMMANDS.xfCustom_jass_alias_msg_ralle.callback = function () {
                XF.EditorHelpers.wrapSelectionText(
                    this,
                    '[CODE=JASS]',
                    '[/CO' + 'DE]',
                    true
                );
            };
        },
    });
})(jQuery, window, document);
 
Last edited:
Posting an updated version. startInit takes arguments and ignoring them causes problems with profile posts.
JavaScript:
!(function ($, window, document, _undefined) {
    'use strict';
    XF.Editor = XF.extend(XF.Editor, {
        __backup: {
            startInit: 'vinditBbCode_startInit',
        },
        startInit: function (callbacks) {
            this.vinditBbCode_startInit(callbacks);
            if (!FroalaEditor.COMMANDS.xfCustom_jass_alias_msg_ralle) {
                return;
            }
            FroalaEditor.COMMANDS.xfCustom_jass_alias_msg_ralle.callback = function () {
                XF.EditorHelpers.wrapSelectionText(
                    this,
                    '[CODE=JASS]',
                    '[/CO' + 'DE]',
                    true
                );
            };
        },
    });
})(jQuery, window, document);
 
Top Bottom