/** * Copyright (c) Facebook, Inc. and its affiliates. * * This source code is licensed under the MIT license found in the * LICENSE file in the root directory of this source tree. * * @format * * @emails oncall+draft_js */ 'use strict'; var KeyBindingUtil = require("./KeyBindingUtil"); var Keys = require("fbjs/lib/Keys"); var UserAgent = require("fbjs/lib/UserAgent"); var isOSX = UserAgent.isPlatform('Mac OS X'); // Firefox on OSX had a bug resulting in navigation instead of cursor movement. // This bug was fixed in Firefox 29. Feature detection is virtually impossible // so we just check the version number. See #342765. var shouldFixFirefoxMovement = isOSX && UserAgent.isBrowser('Firefox < 29'); var hasCommandModifier = KeyBindingUtil.hasCommandModifier, isCtrlKeyCommand = KeyBindingUtil.isCtrlKeyCommand; function shouldRemoveWord(e) { return isOSX && e.altKey || isCtrlKeyCommand(e); } /** * Get the appropriate undo/redo command for a Z key command. */ function getZCommand(e) { if (!hasCommandModifier(e)) { return null; } return e.shiftKey ? 'redo' : 'undo'; } function getDeleteCommand(e) { // Allow default "cut" behavior for PCs on Shift + Delete. if (!isOSX && e.shiftKey) { return null; } return shouldRemoveWord(e) ? 'delete-word' : 'delete'; } function getBackspaceCommand(e) { if (hasCommandModifier(e) && isOSX) { return 'backspace-to-start-of-line'; } return shouldRemoveWord(e) ? 'backspace-word' : 'backspace'; } /** * Retrieve a bound key command for the given event. */ function getDefaultKeyBinding(e) { switch (e.keyCode) { case 66: // B return hasCommandModifier(e) ? 'bold' : null; case 68: // D return isCtrlKeyCommand(e) ? 'delete' : null; case 72: // H return isCtrlKeyCommand(e) ? 'backspace' : null; case 73: // I return hasCommandModifier(e) ? 'italic' : null; case 74: // J return hasCommandModifier(e) ? 'code' : null; case 75: // K return isOSX && isCtrlKeyCommand(e) ? 'secondary-cut' : null; case 77: // M return isCtrlKeyCommand(e) ? 'split-block' : null; case 79: // O return isCtrlKeyCommand(e) ? 'split-block' : null; case 84: // T return isOSX && isCtrlKeyCommand(e) ? 'transpose-characters' : null; case 85: // U return hasCommandModifier(e) ? 'underline' : null; case 87: // W return isOSX && isCtrlKeyCommand(e) ? 'backspace-word' : null; case 89: // Y if (isCtrlKeyCommand(e)) { return isOSX ? 'secondary-paste' : 'redo'; } return null; case 90: // Z return getZCommand(e) || null; case Keys.RETURN: return 'split-block'; case Keys.DELETE: return getDeleteCommand(e); case Keys.BACKSPACE: return getBackspaceCommand(e); // LEFT/RIGHT handlers serve as a workaround for a Firefox bug. case Keys.LEFT: return shouldFixFirefoxMovement && hasCommandModifier(e) ? 'move-selection-to-start-of-block' : null; case Keys.RIGHT: return shouldFixFirefoxMovement && hasCommandModifier(e) ? 'move-selection-to-end-of-block' : null; default: return null; } } module.exports = getDefaultKeyBinding;