@atlaskit/editor-common
Version:
A package that contains common classes and components for editor and renderer
360 lines (355 loc) • 17 kB
JavaScript
import _typeof from "@babel/runtime/helpers/typeof";
/**
* @jsxRuntime classic
* @jsx jsx
*/
import React, { Fragment } from 'react';
// eslint-disable-next-line @atlaskit/ui-styling-standard/use-compiled -- Ignored via go/DSP-18766
import { css, jsx } from '@emotion/react';
import { base, keyName } from 'w3c-keyname';
import { editorCommandToPMCommand } from '../preset/editor-commands';
import { browser } from '../utils';
export var addAltText = makeKeyMapWithCommon('Add Alt Text', 'Mod-Alt-y');
export var navToEditorToolbar = makeKeyMapWithCommon('Navigate to editor toolbar', 'Alt-F9');
export var navToFloatingToolbar = makeKeyMapWithCommon('Navigate to floating toolbar', 'Alt-F10');
export var toggleBold = makeKeyMapWithCommon('Bold', 'Mod-b');
export var toggleItalic = makeKeyMapWithCommon('Italic', 'Mod-i');
export var toggleUnderline = makeKeyMapWithCommon('Underline', 'Mod-u');
export var toggleStrikethrough = makeKeyMapWithCommon('Strikethrough', 'Mod-Shift-s');
export var toggleSubscript = makeKeyMapWithCommon('Subscript', 'Mod-Shift-,');
export var toggleSuperscript = makeKeyMapWithCommon('Superscript', 'Mod-Shift-.');
export var toggleCode = makeKeyMapWithCommon('Code', 'Mod-Shift-m');
export var pastePlainText = makeKeyMapWithCommon('Paste Plain Text', 'Mod-Shift-v');
export var clearFormatting = makeKeyMapWithCommon('Clear formatting', 'Mod-\\');
export var setNormalText = makeKeyMapWithCommon('Normal text', 'Mod-Alt-0');
export var toggleHeading1 = makeKeyMapWithCommon('Heading 1', 'Mod-Alt-1');
export var toggleHeading2 = makeKeyMapWithCommon('Heading 2', 'Mod-Alt-2');
export var toggleHeading3 = makeKeyMapWithCommon('Heading 3', 'Mod-Alt-3');
export var toggleHeading4 = makeKeyMapWithCommon('Heading 4', 'Mod-Alt-4');
export var toggleHeading5 = makeKeyMapWithCommon('Heading 5', 'Mod-Alt-5');
export var toggleHeading6 = makeKeyMapWithCommon('Heading 6', 'Mod-Alt-6');
export var toggleOrderedList = makeKeyMapWithCommon('Numbered list', 'Mod-Shift-7');
export var ctrlBackSpace = makeKeyMapWithCommon('Cmd + Backspace', 'Mod-Backspace');
export var toggleBulletList = makeKeyMapWithCommon('Bullet list', 'Mod-Shift-8');
export var toggleBlockQuote = makeKeyMapWithCommon('Quote', 'Mod-Shift-9');
export var insertNewLine = makeKeyMapWithCommon('Insert new line', 'Shift-Enter');
export var shiftBackspace = makeKeyMapWithCommon('Shift Backspace', 'Shift-Backspace');
export var splitCodeBlock = makeKeyMapWithCommon('Split code block', 'Enter');
export var splitListItem = makeKeyMapWithCommon('Split list item', 'Enter');
export var insertRule = makeKeyMapWithCommon('Insert horizontal rule', 'Mod-Shift--');
export var undo = makeKeyMapWithCommon('Undo', 'Mod-z');
export var moveUp = makeKeyMapWithCommon('Move up', 'ArrowUp');
export var moveDown = makeKeyMapWithCommon('Move down', 'ArrowDown');
export var moveLeft = makeKeyMapWithCommon('Move left', 'ArrowLeft');
export var moveRight = makeKeyMapWithCommon('Move right', 'ArrowRight');
export var indentList = makeKeyMapWithCommon('Indent List', 'Tab');
export var outdentList = makeKeyMapWithCommon('Outdent List', 'Shift-Tab');
export var redo = makeKeymap('Redo', 'Ctrl-y', 'Mod-Shift-z');
export var openHelp = makeKeyMapWithCommon('Open Help', 'Mod-/');
export var addLink = makeKeyMapWithCommon('Link', 'Mod-k');
export var addInlineComment = makeKeyMapWithCommon('Annotate', 'Mod-Alt-c');
export var submit = makeKeyMapWithCommon('Submit Content', 'Mod-Enter');
export var enter = makeKeyMapWithCommon('Enter', 'Enter');
export var shiftEnter = makeKeyMapWithCommon('Shift Enter', 'Shift-Enter');
export var tab = makeKeyMapWithCommon('Tab', 'Tab');
export var indent = makeKeyMapWithCommon('Indent', 'Tab');
export var outdent = makeKeyMapWithCommon('Outdent', 'Shift-Tab');
export var backspace = makeKeyMapWithCommon('Backspace', 'Backspace');
export var deleteKey = makeKeyMapWithCommon('Delete', 'Delete');
export var forwardDelete = makeKeymap('Forward Delete', '', 'Ctrl-d');
export var space = makeKeyMapWithCommon('Space', 'Space');
export var escape = makeKeyMapWithCommon('Escape', 'Escape');
export var nextCell = makeKeyMapWithCommon('Next cell', 'Tab');
export var previousCell = makeKeyMapWithCommon('Previous cell', 'Shift-Tab');
export var shiftArrowUp = makeKeyMapWithCommon('Shift ArrowUp', 'Shift-ArrowUp');
export var shiftTab = makeKeyMapWithCommon('Shift Tab', 'Shift-Tab');
export var toggleTable = makeKeyMapWithCommon('Table', 'Shift-Alt-t');
export var focusTableResizer = makeKeyMapWithCommon('Focus Table Resizer', 'Mod-Alt-Shift-r');
export var addRowBefore = makeKeyMapWithCommon('Add Row Above', 'Ctrl-Alt-ArrowUp');
export var addRowAfter = makeKeyMapWithCommon('Add Row Below', 'Ctrl-Alt-ArrowDown');
export var addColumnAfter = makeKeyMapWithCommon('Add Column After', 'Ctrl-Alt-ArrowRight');
export var addColumnBefore = makeKeyMapWithCommon('Add Column Before', 'Ctrl-Alt-ArrowLeft');
// The following few shortcuts that end in VO are added specifically for Voice Over users, as shortcuts that perform the same role when using Voice Over don't work because they conflict with default shortcuts in Voice Over
export var addRowBeforeVO = makeKeyMapWithCommon('Add Row Above', 'Mod-Alt-[');
export var addRowAfterVO = makeKeyMapWithCommon('Add Row Below', 'Mod-Alt-]');
export var addColumnAfterVO = makeKeyMapWithCommon('Add Column After', 'Mod-Alt-=');
export var addColumnBeforeVO = makeKeyMapWithCommon('Add Column Before', 'Mod-Alt--');
export var moveColumnLeft = makeKeyMapWithCommon('Move Column Left', 'Ctrl-Alt-Shift-ArrowLeft');
export var moveColumnRight = makeKeyMapWithCommon('Move Column Right', 'Ctrl-Alt-Shift-ArrowRight');
export var moveRowDown = makeKeyMapWithCommon('Move Row Down', 'Ctrl-Alt-Shift-ArrowDown');
export var moveRowUp = makeKeyMapWithCommon('Move Row Up', 'Ctrl-Alt-Shift-ArrowUp');
export var deleteColumn = makeKeyMapWithCommon('Delete Column', 'Ctrl-Backspace');
export var deleteRow = makeKeyMapWithCommon('Delete Row', 'Ctrl-Backspace');
export var startColumnResizing = makeKeyMapWithCommon('Activate Column Resize', 'Mod-Alt-Shift-c');
export var cut = makeKeyMapWithCommon('Cut', 'Mod-x');
export var copy = makeKeyMapWithCommon('Copy', 'Mod-c');
export var paste = makeKeyMapWithCommon('Paste', 'Mod-v');
export var altPaste = makeKeyMapWithCommon('Paste', 'Mod-Shift-v');
export var find = makeKeyMapWithCommon('Find', 'Mod-f');
export var alignLeft = makeKeyMapWithCommon('Align Left', 'Mod-Shift-l');
export var alignCenter = makeKeyMapWithCommon('Align Center', 'Mod-Alt-e');
export var alignRight = makeKeyMapWithCommon('Align Right', 'Mod-Alt-t');
export var toggleTaskItemCheckbox = makeKeyMapWithCommon('Toggles task item', 'Mod-Alt-Enter');
export var selectRow = makeKeyMapArrayWithCommon('Select row', ['Mod-Alt-Shift-ArrowLeft', 'Mod-Alt-Shift-ArrowRight']);
export var selectColumn = makeKeyMapArrayWithCommon('Select column', ['Mod-Alt-Shift-ArrowDown', 'Mod-Alt-Shift-ArrowUp']);
export var selectTable = makeKeyMapWithCommon('Select table', 'Mod-a');
export var increaseMediaSize = makeKeyMapWithCommon('increase image size', 'Mod-Alt-]');
export var decreaseMediaSize = makeKeyMapWithCommon('increase image size', 'Mod-Alt-[');
export var activateVideoControls = makeKeyMapWithCommon('Activate controls panel on video', 'Shift-F10');
export var toggleHighlightPalette = makeKeyMapWithCommon('Toggle Highlight Palette', 'Mod-Alt-b');
export var focusToContextMenuTrigger = makeKeyMapWithCommon('Focus table context menu trigger', 'Shift-F10');
export var dragToMoveUp = makeKeyMapWithCommon('Move node up in the document', 'Ctrl-Shift-ArrowUp');
export var dragToMoveDown = makeKeyMapWithCommon('Move node down in the document', 'Ctrl-Shift-ArrowDown');
export var dragToMoveLeft = makeKeyMapWithCommon('Move node to the left column in the document', 'Ctrl-Shift-Alt-ArrowLeft');
export var dragToMoveRight = makeKeyMapWithCommon('Move node to the right column in the document', 'Ctrl-Shift-Alt-ArrowRight');
export var showElementDragHandle = makeKeyMapWithCommon('Show drag handle for editor element', 'Ctrl-Shift-h');
export var continueInRovoChat = makeKeyMapWithCommon('Continue in Rovo chat', 'Alt-Enter');
var arrowKeysMap = {
// for reference: https://wincent.com/wiki/Unicode_representations_of_modifier_keys
ARROWLEFT: "\u2190",
ARROWRIGHT: "\u2192",
ARROWUP: "\u2191",
ARROWDOWN: "\u2193"
};
var tooltipShortcutStyle = css({
borderRadius: '2px',
backgroundColor: "var(--ds-background-inverse-subtle, #00000029)",
padding: "0 ".concat("var(--ds-space-025, 2px)"),
// NOTE: This might not actually do anything: https://atlassian.slack.com/archives/CFG3PSQ9E/p1647395052443259?thread_ts=1647394572.556029&cid=CFG3PSQ9E
label: 'tooltip-shortcut'
});
export function formatShortcut(keymap) {
var shortcut;
if (browser.mac) {
// for reference: https://wincent.com/wiki/Unicode_representations_of_modifier_keys
shortcut = keymap.mac
// Ignored via go/ees005
// eslint-disable-next-line require-unicode-regexp
.replace(/Cmd/i, "\u2318")
// Ignored via go/ees005
// eslint-disable-next-line require-unicode-regexp
.replace(/Shift/i, "\u21E7")
// Ignored via go/ees005
// eslint-disable-next-line require-unicode-regexp
.replace(/Ctrl/i, "\u2303")
// Ignored via go/ees005
// eslint-disable-next-line require-unicode-regexp
.replace(/Alt/i, "\u2325")
// Ignored via go/ees005
// eslint-disable-next-line require-unicode-regexp
.replace(/Backspace/i, "\u232B")
// Ignored via go/ees005
// eslint-disable-next-line require-unicode-regexp
.replace(/Enter/i, "\u23CE");
} else {
// Ignored via go/ees005
// eslint-disable-next-line require-unicode-regexp
shortcut = keymap.windows.replace(/Backspace/i, "\u232B");
}
var keys = shortcut.split('-');
var lastKey = keys[keys.length - 1];
if (lastKey.length === 1) {
// capitalise single letters
lastKey = lastKey.toUpperCase();
}
keys[keys.length - 1] = arrowKeysMap[lastKey.toUpperCase()] || lastKey;
return keys.join(browser.mac ? '' : '+');
}
export function tooltip(keymap, description) {
if (keymap) {
var shortcut = formatShortcut(keymap);
return description ? "".concat(description, " ").concat(shortcut) : shortcut;
}
return;
}
export var ToolTipContent = /*#__PURE__*/React.memo(function (_ref) {
var description = _ref.description,
shortcutOverride = _ref.shortcutOverride,
keymap = _ref.keymap;
var shortcut = shortcutOverride || keymap && formatShortcut(keymap);
return shortcut || description ? jsx(Fragment, null, description, shortcut && description && "\xA0", shortcut && jsx("span", {
css: tooltipShortcutStyle
}, shortcut)) : null;
});
export var TooltipContentWithMultipleShortcuts = /*#__PURE__*/React.memo(function (_ref2) {
var helpDescriptors = _ref2.helpDescriptors;
var keymapCount = helpDescriptors.length;
return jsx(Fragment, null, helpDescriptors.map(function (descriptor, index) {
return (
// Ignored via go/ees005
// eslint-disable-next-line react/no-array-index-key
jsx(Fragment, {
key: index
}, jsx(ToolTipContent
// Ignored via go/ees005
// eslint-disable-next-line react/jsx-props-no-spreading
, descriptor), ' ', index < keymapCount - 1 && jsx("br", null))
);
}));
});
export function findKeymapByDescription(description) {
var matches = ALL.filter(function (keymap) {
return keymap.description.toUpperCase() === description.toUpperCase();
});
return matches[0];
}
export function findShortcutByDescription(description) {
var keymap = findKeymapByDescription(description);
if (keymap) {
return findShortcutByKeymap(keymap);
}
return;
}
export function findShortcutByKeymap(keymap) {
if (browser.mac) {
return keymap.mac;
}
return keymap.windows;
}
export function getAriaKeyshortcuts(keymap) {
var keyShortcuts;
if (typeof keymap === 'string') {
keyShortcuts = keymap;
} else if (_typeof(keymap) === 'object') {
keyShortcuts = keymap[browser.mac ? 'mac' : 'windows'];
}
if (keyShortcuts) {
return keyShortcuts.toLowerCase().split('-').map(function (modifier) {
switch (modifier) {
case 'cmd':
return 'Meta';
case 'ctrl':
return 'Control';
case 'alt':
return 'Alt';
case 'shift':
return 'Shift';
case 'enter':
return 'Enter';
case 'esc':
return 'Esc';
case 'tab':
return 'Tab';
case 'space':
return 'Space';
case 'backspace':
return 'Backspace';
case 'arrowup':
return 'Arrow Up';
case 'arrowdown':
return 'Arrow Down';
default:
return modifier.split('').join(' ');
}
}).join('+');
} else {
return undefined;
}
}
var ALL = [toggleOrderedList, toggleBulletList, toggleBold, toggleItalic, toggleUnderline, toggleStrikethrough, toggleSubscript, toggleSuperscript, toggleCode, setNormalText, toggleHeading1, toggleHeading2, toggleHeading3, toggleHeading4, toggleHeading5, toggleHeading6, toggleBlockQuote, insertNewLine, insertRule, splitCodeBlock, splitListItem, redo, undo, find, escape, enter, shiftEnter];
// Ignored via go/ees005
// eslint-disable-next-line @typescript-eslint/max-params
export function makeKeymap(description, windows, mac, common) {
return {
description: description,
// Ignored via go/ees005
// eslint-disable-next-line require-unicode-regexp
windows: windows.replace(/Mod/i, 'Ctrl'),
// Ignored via go/ees005
// eslint-disable-next-line require-unicode-regexp
mac: mac.replace(/Mod/i, 'Cmd'),
common: common
};
}
export function makeKeyMapWithCommon(description, common) {
// Ignored via go/ees005
// eslint-disable-next-line require-unicode-regexp
var windows = common.replace(/Mod/i, 'Ctrl');
// Ignored via go/ees005
// eslint-disable-next-line require-unicode-regexp
var mac = common.replace(/Mod/i, 'Cmd');
return makeKeymap(description, windows, mac, common);
}
export function makeKeyMapArrayWithCommon(description, shortcuts) {
var keymapArray = [];
shortcuts.forEach(function (shortcut) {
keymapArray.push(makeKeyMapWithCommon(description, shortcut));
});
return keymapArray;
}
function combineWithOldCommand(cmd, oldCmd) {
return function (state, dispatch, editorView) {
return oldCmd(state, dispatch) || cmd(state, dispatch, editorView);
};
}
export function bindKeymapWithCommand(shortcut, cmd, keymap) {
var oldCmd = keymap[shortcut];
keymap[shortcut] = oldCmd ? combineWithOldCommand(cmd, oldCmd) : cmd;
}
// If there is a need to use the same command with several shortcuts
export function bindKeymapArrayWithCommand(shortcutsArray, cmd, keymap) {
shortcutsArray.forEach(function (shortcut) {
// Ignored via go/ees005
// eslint-disable-next-line @typescript-eslint/no-non-null-assertion
return bindKeymapWithCommand(shortcut.common, cmd, keymap);
});
}
export function bindKeymapWithEditorCommand(shortcut, cmd, keymap) {
bindKeymapWithCommand(shortcut, editorCommandToPMCommand(cmd), keymap);
}
export function findKeyMapForBrowser(keyMap) {
if (keyMap) {
if (browser.mac) {
return keyMap.mac;
}
return keyMap.windows;
}
return;
}
/**
* ED-20175: on windows OS if the capsLock is ON then it registers the key with capital case
* which creates a command (Ctrl-B) and all the keymap bindings are in lower case (Ctrl-b).
*
*/
export function isCapsLockOnAndModifyKeyboardEvent(event) {
var keyboardEvent = event;
var name = keyName(event);
if (event.ctrlKey && event.getModifierState('CapsLock') && !event.getModifierState('Shift') && name.length === 1 &&
// Ignored via go/ees005
// eslint-disable-next-line require-unicode-regexp
/^[A-Z]/.test(name)) {
keyboardEvent = new KeyboardEvent('keydown', {
key: base[event.keyCode].toLowerCase(),
code: event.code,
ctrlKey: true
});
}
return keyboardEvent;
}
export {
// eslint-disable-next-line @atlaskit/editor/no-re-export
DOWN,
// eslint-disable-next-line @atlaskit/editor/no-re-export
HEADING_KEYS,
// eslint-disable-next-line @atlaskit/editor/no-re-export
KEY_0,
// eslint-disable-next-line @atlaskit/editor/no-re-export
KEY_1,
// eslint-disable-next-line @atlaskit/editor/no-re-export
KEY_2,
// eslint-disable-next-line @atlaskit/editor/no-re-export
KEY_3,
// eslint-disable-next-line @atlaskit/editor/no-re-export
KEY_4,
// eslint-disable-next-line @atlaskit/editor/no-re-export
KEY_5,
// eslint-disable-next-line @atlaskit/editor/no-re-export
KEY_6,
// eslint-disable-next-line @atlaskit/editor/no-re-export
LEFT,
// eslint-disable-next-line @atlaskit/editor/no-re-export
RIGHT,
// eslint-disable-next-line @atlaskit/editor/no-re-export
UP } from './consts';
// eslint-disable-next-line @atlaskit/editor/no-re-export
export { keymap } from './keymap';