UNPKG

@atlaskit/editor-plugin-table

Version:

Table plugin for the @atlaskit/editor

190 lines (186 loc) 8.84 kB
"use strict"; var _interopRequireDefault = require("@babel/runtime/helpers/interopRequireDefault"); var _typeof = require("@babel/runtime/helpers/typeof"); Object.defineProperty(exports, "__esModule", { value: true }); exports.DropdownMenu = void 0; var _slicedToArray2 = _interopRequireDefault(require("@babel/runtime/helpers/slicedToArray")); var _extends2 = _interopRequireDefault(require("@babel/runtime/helpers/extends")); var _react = _interopRequireWildcard(require("react")); var _ui = require("@atlaskit/editor-common/ui"); var _uiMenu = require("@atlaskit/editor-common/ui-menu"); var _uiReact = require("@atlaskit/editor-common/ui-react"); var _editorSharedStyles = require("@atlaskit/editor-shared-styles"); var _menu = require("@atlaskit/menu"); var _consts = require("../consts"); function _interopRequireWildcard(e, t) { if ("function" == typeof WeakMap) var r = new WeakMap(), n = new WeakMap(); return (_interopRequireWildcard = function _interopRequireWildcard(e, t) { if (!t && e && e.__esModule) return e; var o, i, f = { __proto__: null, default: e }; if (null === e || "object" != _typeof(e) && "function" != typeof e) return f; if (o = t ? n : r) { if (o.has(e)) return o.get(e); o.set(e, f); } for (var _t in e) "default" !== _t && {}.hasOwnProperty.call(e, _t) && ((i = (o = Object.defineProperty) && Object.getOwnPropertyDescriptor(e, _t)) && (i.get || i.set) ? o(f, _t, i) : f[_t] = e[_t]); return f; })(e, t); } /* eslint-disable @atlaskit/design-system/prefer-primitives */ var DropListWithOutsideClickTargetRef = function DropListWithOutsideClickTargetRef(props) { var setOutsideClickTargetRef = _react.default.useContext(_uiReact.OutsideClickTargetRefContext); // Ignored via go/ees005 // eslint-disable-next-line react/jsx-props-no-spreading return /*#__PURE__*/_react.default.createElement(_ui.DropList, (0, _extends2.default)({ onDroplistRef: setOutsideClickTargetRef }, props)); }; var DropListWithOutsideListeners = (0, _uiReact.withReactEditorViewOuterListeners)(DropListWithOutsideClickTargetRef); var DropdownMenu = exports.DropdownMenu = function DropdownMenu(_ref) { var items = _ref.items, section = _ref.section, disableKeyboardHandling = _ref.disableKeyboardHandling, onItemActivated = _ref.onItemActivated, handleClose = _ref.handleClose, onMouseEnter = _ref.onMouseEnter, onMouseLeave = _ref.onMouseLeave, fitWidth = _ref.fitWidth, fitHeight = _ref.fitHeight, direction = _ref.direction, mountPoint = _ref.mountPoint, boundariesElement = _ref.boundariesElement, scrollableElement = _ref.scrollableElement; var _useState = (0, _react.useState)(['bottom', 'left']), _useState2 = (0, _slicedToArray2.default)(_useState, 2), popupPlacement = _useState2[0], setPopupPlacement = _useState2[1]; var _useState3 = (0, _react.useState)(null), _useState4 = (0, _slicedToArray2.default)(_useState3, 2), targetRefDiv = _useState4[0], setTargetRefDiv = _useState4[1]; var handleRef = function handleRef(ref) { setTargetRefDiv(ref); }; // more offsets calculation as offsets depend on the direction and updated placement here var offsetY = direction === 'row' ? popupPlacement[0] === 'bottom' ? -8 : -34 : 0; var offsetX = direction === 'column' ? popupPlacement[1] === 'left' ? 0 : -7 : 0; var innerMenu = function innerMenu() { return /*#__PURE__*/_react.default.createElement(DropListWithOutsideListeners, { isOpen: true, shouldFitContainer: true, position: popupPlacement.join(' '), handleClickOutside: function handleClickOutside() { return handleClose('editor'); }, handleEscapeKeydown: function handleEscapeKeydown() { if (!disableKeyboardHandling) { handleClose('handle'); } }, handleEnterKeydown: function handleEnterKeydown(e) { if (!disableKeyboardHandling) { e.preventDefault(); e.stopPropagation(); } }, targetRef: targetRefDiv }, /*#__PURE__*/_react.default.createElement("div", { style: { height: 0, minWidth: _consts.dragMenuDropdownWidth } }), /*#__PURE__*/_react.default.createElement(_menu.MenuGroup, { role: "menu" }, items.map(function (group, index) { return /*#__PURE__*/_react.default.createElement(_menu.Section, { hasSeparator: (section === null || section === void 0 ? void 0 : section.hasSeparator) && index > 0, title: section === null || section === void 0 ? void 0 : section.title // Ignored via go/ees005 // eslint-disable-next-line react/no-array-index-key , key: index }, group.items.map(function (item) { var _item$key; return /*#__PURE__*/_react.default.createElement(_uiMenu.DropdownMenuItem, { shouldUseDefaultRole: false, key: (_item$key = item.key) !== null && _item$key !== void 0 ? _item$key : String(item.content), item: item, onItemActivated: onItemActivated, onMouseEnter: onMouseEnter, onMouseLeave: onMouseLeave }); })); }))); }; var onClose = (0, _react.useCallback)(function () { return handleClose('handle'); }, [handleClose]); var onSelection = (0, _react.useCallback)(function (index) { var results = items.flatMap(function (item) { return 'items' in item ? item.items : item; }); // onSelection is called when any focusable element is 'activated' // this is an issue as some menu items have toggles, which cause the index value // in the callback to be outside of array length. // The logic below normalises the index value based on the number // of menu items with 2 focusable elements, and adjusts the index to ensure // the correct menu item is sent in onItemActivated callback var keys = ['row_numbers', 'header_row', 'header_column']; var doubleItemCount = 0; var firstIndex = results.findIndex(function (value) { var key = value.key; return key !== undefined && keys.includes(key); }); if (firstIndex === -1 || index <= firstIndex) { onItemActivated && onItemActivated({ item: results[index] }); return; } for (var i = firstIndex; i < results.length; i += 1) { var key = results[i].key; if (key !== undefined && keys.includes(key)) { doubleItemCount += 1; } if (firstIndex % 2 === 0 && index - doubleItemCount === i) { onItemActivated && onItemActivated({ item: results[i] }); return; } if (firstIndex % 2 === 1 && index - doubleItemCount === i) { onItemActivated && onItemActivated({ item: results[i] }); return; } } }, [items, onItemActivated]); return ( /*#__PURE__*/ // eslint-disable-next-line @atlaskit/ui-styling-standard/no-classname-prop -- Ignored via go/DSP-18766 _react.default.createElement("div", { className: "drag-dropdown-menu-wrapper" }, /*#__PURE__*/_react.default.createElement("div", { className: "drag-dropdown-menu-popup-ref", ref: handleRef }), /*#__PURE__*/_react.default.createElement(_ui.Popup // Ignored via go/ees005 // eslint-disable-next-line @atlaskit/editor/no-as-casting , { target: targetRefDiv, mountTo: mountPoint, boundariesElement: boundariesElement, scrollableElement: scrollableElement, onPlacementChanged: function onPlacementChanged(placement) { setPopupPlacement(placement); }, fitHeight: fitHeight, fitWidth: fitWidth, zIndex: _editorSharedStyles.akEditorFloatingPanelZIndex, offset: [offsetX, offsetY], allowOutOfBounds: true // required as this popup is child of a parent popup, should be allowed to be out of bound of the parent popup, otherwise horizontal offset is not right }, /*#__PURE__*/_react.default.createElement(_uiMenu.ArrowKeyNavigationProvider, { closeOnTab: !disableKeyboardHandling, type: _uiMenu.ArrowKeyNavigationType.MENU, handleClose: onClose, onSelection: onSelection // disableKeyboardHandling is linked with isSubmenuOpen in DragMenu // When isSubmenuOpen is true, the background color picker palette is open, and the picker is a ColorPaletteArrowKeyNavigationProvider // At the same time the MenuArrowKeyNavigationProvider are renderer too, as it is the wrapper for all other DragMenu items // In this case we want the ColorPaletteArrowKeyNavigationProvider to handle the keyboard event, not the MenuArrowKeyNavigationProvider // Hence set disableArrowKeyNavigation to true when disableKeyboardHandling is true , disableArrowKeyNavigation: disableKeyboardHandling }, innerMenu()))) ); };