From a978284b3c7051cb250bd8feffc87336f02ec93c Mon Sep 17 00:00:00 2001 From: John Rayes Date: Tue, 4 May 2021 23:53:58 -0700 Subject: [PATCH] feat: Linebreak in toolbar Use a double pipe `||` to add a new row Closes #731 --- src/lib/SCEditor.js | 147 ++++++++++++++++++++----------------- tests/unit/lib/SCEditor.js | 29 ++++++++ 2 files changed, 109 insertions(+), 67 deletions(-) diff --git a/src/lib/SCEditor.js b/src/lib/SCEditor.js index b0916fb18..69e15fea9 100644 --- a/src/lib/SCEditor.js +++ b/src/lib/SCEditor.js @@ -1,4 +1,4 @@ -import * as dom from './dom.js'; +import * as dom from './dom.js'; import * as utils from './utils.js'; import defaultOptions from './defaultOptions.js'; import defaultCommands from './defaultCommands.js'; @@ -709,10 +709,11 @@ export default function SCEditor(original, userOptions) { * @private */ initToolBar = function () { - var group, + var + group, commands = base.commands, exclude = (options.toolbarExclude || '').split(','), - groups = options.toolbar.split('|'); + rows = options.toolbar.split('||'); toolbar = dom.createElement('div', { className: 'sceditor-toolbar', @@ -723,84 +724,96 @@ export default function SCEditor(original, userOptions) { icons = new SCEditor.icons[options.icons](); } - utils.each(groups, function (_, menuItems) { - group = dom.createElement('div', { - className: 'sceditor-group' + utils.each(rows, function (_, rowItems) { + var row = dom.createElement('div', { + className: 'sceditor-row' }); - utils.each(menuItems.split(','), function (_, commandName) { - var button, shortcut, - command = commands[commandName]; + utils.each(rowItems.split('|'), function (_, menuItems) { + group = dom.createElement('div', { + className: 'sceditor-group' + }); - // The commandName must be a valid command and not excluded - if (!command || exclude.indexOf(commandName) > -1) { - return; - } + utils.each(menuItems.split(','), function (_, commandName) { + var + button, shortcut, + command = commands[commandName]; - shortcut = command.shortcut; - button = _tmpl('toolbarButton', { - name: commandName, - dispName: base._(command.name || - command.tooltip || commandName) - }, true).firstChild; - - if (icons && icons.create) { - var icon = icons.create(commandName); - if (icon) { - dom.insertBefore(icons.create(commandName), - button.firstChild); - dom.addClass(button, 'has-icon'); + // The commandName must be a valid command and not excluded + if (!command || exclude.indexOf(commandName) > -1) { + return; } - } - button._sceTxtMode = !!command.txtExec; - button._sceWysiwygMode = !!command.exec; - dom.toggleClass(button, 'disabled', !command.exec); - dom.on(button, 'click', function (e) { - if (!dom.hasClass(button, 'disabled')) { - handleCommand(button, command); + shortcut = command.shortcut; + button = _tmpl('toolbarButton', { + name: commandName, + dispName: base._(command.name || + command.tooltip || commandName) + }, true).firstChild; + + if (icons && icons.create) { + var icon = icons.create(commandName); + if (icon) { + dom.insertBefore(icons.create(commandName), + button.firstChild); + dom.addClass(button, 'has-icon'); + } } - updateActiveButtons(); - e.preventDefault(); - }); - // Prevent editor losing focus when button clicked - dom.on(button, 'mousedown', function (e) { - base.closeDropDown(); - e.preventDefault(); - }); - - if (command.tooltip) { - dom.attr(button, 'title', - base._(command.tooltip) + - (shortcut ? ' (' + shortcut + ')' : '') - ); - } - - if (shortcut) { - base.addShortcut(shortcut, commandName); - } + button._sceTxtMode = !!command.txtExec; + button._sceWysiwygMode = !!command.exec; + dom.toggleClass(button, 'disabled', !command.exec); + dom.on(button, 'click', function (e) { + if (!dom.hasClass(button, 'disabled')) { + handleCommand(button, command); + } - if (command.state) { - btnStateHandlers.push({ - name: commandName, - state: command.state + updateActiveButtons(); + e.preventDefault(); }); - // exec string commands can be passed to queryCommandState - } else if (utils.isString(command.exec)) { - btnStateHandlers.push({ - name: commandName, - state: command.exec + // Prevent editor losing focus when button clicked + dom.on(button, 'mousedown', function (e) { + base.closeDropDown(); + e.preventDefault(); }); - } - dom.appendChild(group, button); - toolbarButtons[commandName] = button; + if (command.tooltip) { + dom.attr(button, 'title', + base._(command.tooltip) + + (shortcut ? ' (' + shortcut + ')' : '') + ); + } + + if (shortcut) { + base.addShortcut(shortcut, commandName); + } + + if (command.state) { + btnStateHandlers.push({ + name: commandName, + state: command.state + }); + // exec string commands can be passed to queryCommandState + } else if (utils.isString(command.exec)) { + btnStateHandlers.push({ + name: commandName, + state: command.exec + }); + } + + dom.appendChild(group, button); + toolbarButtons[commandName] = button; + }); + + // Exclude empty groups + if (group.firstChild) { + dom.appendChild(row, group); + } }); - // Exclude empty groups - if (group.firstChild) { - dom.appendChild(toolbar, group); + // Exclude empty rows + if (row.firstChild) { + dom.appendChild(toolbar, row); } }); diff --git a/tests/unit/lib/SCEditor.js b/tests/unit/lib/SCEditor.js index add3567a9..f866c39dd 100644 --- a/tests/unit/lib/SCEditor.js +++ b/tests/unit/lib/SCEditor.js @@ -503,6 +503,35 @@ QUnit.test('emoticons() - Longest first', function (assert) { assert.equal($body.find('img[data-sceditor-emoticon=":("]').length, 1); }); +QUnit.test('toolbar', function (assert) { + reloadEditor({ + toolbar: 'bold,,italic,underline|scribble,strike||subscript,superscript' + }); + var $container = $fixture.children('.sceditor-container'); + assert.equal($container.find('.sceditor-row').length, 2); + assert.equal($container.find('.sceditor-group').length, 3); + assert.equal($container.find('.sceditor-toolbar a').length, 6); +}); + +QUnit.test('toolbarExclude', function (assert) { + reloadEditor({ + toolbar: 'bold,italic', + toolbarExclude: 'italic' + }); + var $container = $fixture.children('.sceditor-container'); + assert.equal($container.find('.sceditor-toolbar a').length, 1); +}); + +QUnit.test('toolbarContainer', function (assert) { + reloadEditor({ + toolbar: 'bold,italic', + toolbarContainer: $fixture.get(0) + }); + var $container = $fixture.children('.sceditor-container'); + assert.equal($container.find('.sceditor-toolbar').length, 0); + assert.equal($fixture.find('.sceditor-toolbar').length, 1); +}); + QUnit.test('Insert image XSS', function (assert) { var done = assert.async();