@atlaskit/editor-plugin-table 1.6.1 → 1.6.3

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (35) hide show
  1. package/CHANGELOG.md +12 -0
  2. package/dist/cjs/plugins/table/index.js +2 -1
  3. package/dist/cjs/plugins/table/pm-plugins/sticky-headers/nodeviews/tableRow.js +3 -1
  4. package/dist/cjs/plugins/table/types.js +1 -0
  5. package/dist/cjs/plugins/table/ui/FloatingContextualButton/FixedButton.js +133 -0
  6. package/dist/cjs/plugins/table/ui/FloatingContextualButton/index.js +73 -128
  7. package/dist/cjs/version.json +1 -1
  8. package/dist/es2019/plugins/table/index.js +2 -1
  9. package/dist/es2019/plugins/table/pm-plugins/sticky-headers/nodeviews/tableRow.js +3 -1
  10. package/dist/es2019/plugins/table/types.js +1 -0
  11. package/dist/es2019/plugins/table/ui/FloatingContextualButton/FixedButton.js +120 -0
  12. package/dist/es2019/plugins/table/ui/FloatingContextualButton/index.js +76 -108
  13. package/dist/es2019/version.json +1 -1
  14. package/dist/esm/plugins/table/index.js +2 -1
  15. package/dist/esm/plugins/table/pm-plugins/sticky-headers/nodeviews/tableRow.js +3 -1
  16. package/dist/esm/plugins/table/types.js +1 -0
  17. package/dist/esm/plugins/table/ui/FloatingContextualButton/FixedButton.js +118 -0
  18. package/dist/esm/plugins/table/ui/FloatingContextualButton/index.js +73 -129
  19. package/dist/esm/version.json +1 -1
  20. package/dist/types/plugins/table/types.d.ts +1 -0
  21. package/dist/types/plugins/table/ui/FloatingContextualButton/FixedButton.d.ts +23 -0
  22. package/dist/types/plugins/table/ui/FloatingContextualButton/index.d.ts +1 -9
  23. package/dist/types-ts4.5/plugins/table/types.d.ts +1 -0
  24. package/dist/types-ts4.5/plugins/table/ui/FloatingContextualButton/FixedButton.d.ts +23 -0
  25. package/dist/types-ts4.5/plugins/table/ui/FloatingContextualButton/index.d.ts +1 -9
  26. package/package.json +5 -4
  27. package/src/__tests__/playwright/__fixtures__/base-adfs.ts +1486 -0
  28. package/src/__tests__/playwright/extensions.spec.ts +67 -0
  29. package/src/__tests__/unit/nodeviews/cell.ts +0 -14
  30. package/src/__tests__/unit/ui/FixedButton.tsx +214 -0
  31. package/src/plugins/table/index.tsx +1 -0
  32. package/src/plugins/table/pm-plugins/sticky-headers/nodeviews/tableRow.ts +2 -1
  33. package/src/plugins/table/types.ts +1 -0
  34. package/src/plugins/table/ui/FloatingContextualButton/FixedButton.tsx +175 -0
  35. package/src/plugins/table/ui/FloatingContextualButton/index.tsx +41 -95
@@ -1,128 +1,96 @@
1
- import _defineProperty from "@babel/runtime/helpers/defineProperty";
2
1
  /** @jsx jsx */
3
2
  import React from 'react';
4
3
  import { jsx } from '@emotion/react';
5
4
  import { findDomRefAtPos } from 'prosemirror-utils';
6
5
  import { injectIntl } from 'react-intl-next';
7
6
  import { Popup } from '@atlaskit/editor-common/ui';
8
- import { akEditorFloatingOverlapPanelZIndex, akEditorSmallZIndex } from '@atlaskit/editor-shared-styles';
7
+ import { akEditorSmallZIndex } from '@atlaskit/editor-shared-styles';
9
8
  import ExpandIcon from '@atlaskit/icon/glyph/chevron-down';
10
9
  import { ToolbarButton } from '@atlaskit/editor-common/ui-menu';
11
- import { closestElement } from '@atlaskit/editor-common/utils';
12
10
  import { toggleContextualMenu } from '../../commands';
13
11
  import { TableCssClassName as ClassName } from '../../types';
14
12
  import messages from '../../ui/messages';
15
- import { CONTENT_COMPONENT } from '@atlaskit/editor-common/analytics';
16
- import { ACTION, ACTION_SUBJECT, EVENT_TYPE } from '@atlaskit/editor-common/analytics';
13
+ import FixedButton from './FixedButton';
14
+ import { ACTION_SUBJECT } from '@atlaskit/editor-common/analytics';
17
15
  import { tableFloatingCellButtonStyles, tableFloatingCellButtonSelectedStyles } from './styles';
18
16
  import { ErrorBoundary } from '@atlaskit/editor-common/error-boundary';
19
- export class FloatingContextualButtonInner extends React.Component {
20
- constructor(...args) {
21
- super(...args);
22
- _defineProperty(this, "handleClick", () => {
23
- const {
24
- state,
25
- dispatch
26
- } = this.props.editorView;
27
- // Clicking outside the dropdown handles toggling the menu closed
28
- // (otherwise these two toggles combat each other).
29
- // In the event a user clicks the chevron button again
30
- // That will count as clicking outside the dropdown and
31
- // will be toggled appropriately
32
- if (!this.props.isContextualMenuOpen) {
33
- toggleContextualMenu()(state, dispatch);
34
- }
35
- });
36
- }
37
- render() {
38
- const {
39
- mountPoint,
40
- scrollableElement,
41
- editorView,
42
- targetCellPosition,
43
- isContextualMenuOpen,
44
- intl: {
45
- formatMessage
46
- },
47
- dispatchAnalyticsEvent
48
- } = this.props; // : Props & WrappedComponentProps
49
- const domAtPos = editorView.domAtPos.bind(editorView);
50
- let targetCellRef;
51
- try {
52
- targetCellRef = findDomRefAtPos(targetCellPosition, domAtPos);
53
- } catch (error) {
54
- // eslint-disable-next-line no-console
55
- console.warn(error);
56
- if (dispatchAnalyticsEvent) {
57
- const payload = {
58
- action: ACTION.ERRORED,
59
- actionSubject: ACTION_SUBJECT.CONTENT_COMPONENT,
60
- eventType: EVENT_TYPE.OPERATIONAL,
61
- attributes: {
62
- component: CONTENT_COMPONENT.FLOATING_CONTEXTUAL_BUTTON,
63
- selection: editorView.state.selection.toJSON(),
64
- position: targetCellPosition,
65
- docSize: editorView.state.doc.nodeSize,
66
- error: error instanceof Error ? error.message : String(error)
67
- },
68
- nonPrivacySafeAttributes: {
69
- errorStack: error instanceof Error ? error.stack : undefined
70
- }
71
- };
72
- dispatchAnalyticsEvent(payload);
73
- }
74
- }
75
- if (!targetCellRef || !(targetCellRef instanceof HTMLElement)) {
76
- return null;
17
+ const BUTTON_OFFSET = 3;
18
+ const FloatingContextualButtonInner = /*#__PURE__*/React.memo(props => {
19
+ const {
20
+ editorView,
21
+ isContextualMenuOpen,
22
+ mountPoint,
23
+ scrollableElement,
24
+ stickyHeader,
25
+ tableWrapper,
26
+ targetCellPosition,
27
+ intl: {
28
+ formatMessage
77
29
  }
78
- const tableWrapper = closestElement(targetCellRef, `.${ClassName.TABLE_NODE_WRAPPER}`);
79
- const labelCellOptions = formatMessage(messages.cellOptions);
80
- const button = jsx("div", {
81
- css: theme => [tableFloatingCellButtonStyles({
82
- theme
83
- }), isContextualMenuOpen && tableFloatingCellButtonSelectedStyles({
84
- theme
85
- })]
86
- }, jsx(ToolbarButton, {
87
- className: ClassName.CONTEXTUAL_MENU_BUTTON,
88
- selected: isContextualMenuOpen,
89
- title: labelCellOptions,
90
- onClick: this.handleClick,
91
- iconBefore: jsx(ExpandIcon, {
92
- label: ""
93
- }),
94
- "aria-label": labelCellOptions
95
- }));
96
- const parentSticky = targetCellRef.parentElement && targetCellRef.parentElement.className.indexOf('sticky') > -1;
97
- if (this.props.stickyHeader && parentSticky) {
98
- const pos = targetCellRef.getBoundingClientRect();
99
- return jsx("div", {
100
- style: {
101
- position: 'fixed',
102
- top: this.props.stickyHeader.top + this.props.stickyHeader.padding + 3 + 3,
103
- zIndex: akEditorFloatingOverlapPanelZIndex,
104
- left: pos.left + targetCellRef.clientWidth - 20 - 3
105
- }
106
- }, button);
30
+ } = props; // : Props & WrappedComponentProps
31
+
32
+ const handleClick = () => {
33
+ const {
34
+ state,
35
+ dispatch
36
+ } = editorView;
37
+ // Clicking outside the dropdown handles toggling the menu closed
38
+ // (otherwise these two toggles combat each other).
39
+ // In the event a user clicks the chevron button again
40
+ // That will count as clicking outside the dropdown and
41
+ // will be toggled appropriately
42
+ if (!isContextualMenuOpen) {
43
+ toggleContextualMenu()(state, dispatch);
107
44
  }
108
- return jsx(Popup, {
109
- alignX: "right",
110
- alignY: "start",
111
- target: targetCellRef,
112
- mountTo: tableWrapper || mountPoint,
113
- boundariesElement: targetCellRef,
114
- scrollableElement: scrollableElement,
115
- offset: [3, -3],
116
- forcePlacement: true,
117
- allowOutOfBounds: true,
118
- zIndex: akEditorSmallZIndex
119
- }, button);
45
+ };
46
+ const domAtPos = editorView.domAtPos.bind(editorView);
47
+ let targetCellRef;
48
+ targetCellRef = findDomRefAtPos(targetCellPosition, domAtPos);
49
+ if (!targetCellRef || !(targetCellRef instanceof HTMLElement)) {
50
+ return null;
120
51
  }
121
- shouldComponentUpdate(nextProps) {
122
- return this.props.tableNode !== nextProps.tableNode || this.props.targetCellPosition !== nextProps.targetCellPosition || this.props.layout !== nextProps.layout || this.props.isContextualMenuOpen !== nextProps.isContextualMenuOpen || this.props.isNumberColumnEnabled !== nextProps.isNumberColumnEnabled || this.props.stickyHeader !== nextProps.stickyHeader;
52
+ const labelCellOptions = formatMessage(messages.cellOptions);
53
+ const button = jsx("div", {
54
+ css: theme => [tableFloatingCellButtonStyles({
55
+ theme
56
+ }), isContextualMenuOpen && tableFloatingCellButtonSelectedStyles({
57
+ theme
58
+ })]
59
+ }, jsx(ToolbarButton, {
60
+ className: ClassName.CONTEXTUAL_MENU_BUTTON,
61
+ selected: isContextualMenuOpen,
62
+ title: labelCellOptions,
63
+ onClick: handleClick,
64
+ iconBefore: jsx(ExpandIcon, {
65
+ label: ""
66
+ }),
67
+ "aria-label": labelCellOptions
68
+ }));
69
+ const parentSticky = targetCellRef.parentElement && targetCellRef.parentElement.className.indexOf('sticky') > -1;
70
+ if (stickyHeader && parentSticky && tableWrapper) {
71
+ return jsx(FixedButton, {
72
+ offset: BUTTON_OFFSET,
73
+ stickyHeader: stickyHeader,
74
+ tableWrapper: tableWrapper,
75
+ targetCellPosition: targetCellPosition,
76
+ targetCellRef: targetCellRef,
77
+ mountTo: tableWrapper,
78
+ isContextualMenuOpen: isContextualMenuOpen
79
+ }, button);
123
80
  }
124
- }
125
- _defineProperty(FloatingContextualButtonInner, "displayName", 'FloatingContextualButton');
81
+ return jsx(Popup, {
82
+ alignX: "right",
83
+ alignY: "start",
84
+ target: targetCellRef,
85
+ mountTo: tableWrapper || mountPoint,
86
+ boundariesElement: targetCellRef,
87
+ scrollableElement: scrollableElement,
88
+ offset: [BUTTON_OFFSET, -BUTTON_OFFSET],
89
+ forcePlacement: true,
90
+ allowOutOfBounds: true,
91
+ zIndex: akEditorSmallZIndex
92
+ }, button);
93
+ });
126
94
  const FloatingContextualButton = injectIntl(FloatingContextualButtonInner);
127
95
  export default function (props) {
128
96
  return jsx(ErrorBoundary, {
@@ -1,5 +1,5 @@
1
1
  {
2
2
  "name": "@atlaskit/editor-plugin-table",
3
- "version": "1.6.1",
3
+ "version": "1.6.3",
4
4
  "sideEffects": false
5
5
  }
@@ -254,7 +254,8 @@ var tablesPlugin = function tablesPlugin(options, api) {
254
254
  dispatchAnalyticsEvent: dispatchAnalyticsEvent,
255
255
  isContextualMenuOpen: isContextualMenuOpen,
256
256
  layout: layout,
257
- stickyHeader: stickyHeader
257
+ stickyHeader: stickyHeader,
258
+ tableWrapper: tableWrapperTarget
258
259
  }), allowControls && /*#__PURE__*/React.createElement(FloatingInsertButton, {
259
260
  tableNode: tableNode,
260
261
  tableRef: tableRef,
@@ -225,7 +225,8 @@ export var TableRowNodeView = /*#__PURE__*/function () {
225
225
  if (_this.stickyRowHeight && _this.stickyRowHeight > window.innerHeight / 2) {
226
226
  return;
227
227
  }
228
- var table = tree.table;
228
+ var table = tree.table,
229
+ wrapper = tree.wrapper;
229
230
 
230
231
  // ED-16035 Make sure sticky header is only applied to first row
231
232
  var tbody = _this.dom.parentElement;
@@ -246,6 +247,7 @@ export var TableRowNodeView = /*#__PURE__*/function () {
246
247
  }
247
248
  _this.dom.style.top = "".concat(domTop, "px");
248
249
  updateTableMargin(table);
250
+ _this.dom.scrollLeft = wrapper.scrollLeft;
249
251
  _this.emitOn(domTop, _this.colControlsOffset);
250
252
  });
251
253
  _defineProperty(this, "makeRowHeaderNotSticky", function (table) {
@@ -90,6 +90,7 @@ export var TableCssClassName = _objectSpread(_objectSpread({}, TableSharedCssCla
90
90
  CONTEXTUAL_SUBMENU: "".concat(tablePrefixSelector, "-contextual-submenu"),
91
91
  CONTEXTUAL_MENU_BUTTON_WRAP: "".concat(tablePrefixSelector, "-contextual-menu-button-wrap"),
92
92
  CONTEXTUAL_MENU_BUTTON: "".concat(tablePrefixSelector, "-contextual-menu-button"),
93
+ CONTEXTUAL_MENU_BUTTON_FIXED: "".concat(tablePrefixSelector, "-contextual-menu-button-fixed"),
93
94
  CONTEXTUAL_MENU_ICON: "".concat(tablePrefixSelector, "-contextual-submenu-icon"),
94
95
  // come from prosemirror-table
95
96
  SELECTED_CELL: 'selectedCell',
@@ -0,0 +1,118 @@
1
+ import React, { useEffect, useRef } from 'react';
2
+ import { createPortal } from 'react-dom';
3
+ import rafSchedule from 'raf-schd';
4
+ import { akEditorFloatingPanelZIndex } from '@atlaskit/editor-shared-styles';
5
+ import { insertColumnButtonOffset } from '../common-styles';
6
+ import { TableCssClassName as ClassName } from '../../types';
7
+ export var BUTTON_WIDTH = 20;
8
+ export var calcLeftPos = function calcLeftPos(_ref) {
9
+ var buttonWidth = _ref.buttonWidth,
10
+ cellRectLeft = _ref.cellRectLeft,
11
+ cellRefWidth = _ref.cellRefWidth,
12
+ offset = _ref.offset;
13
+ return cellRectLeft + cellRefWidth - buttonWidth - offset;
14
+ };
15
+ export var calcObserverTargetMargin = function calcObserverTargetMargin(tableWrapper, fixedButtonRefCurrent) {
16
+ var tableWrapperRect = tableWrapper.getBoundingClientRect();
17
+ var fixedButtonRect = fixedButtonRefCurrent.getBoundingClientRect();
18
+ var scrollLeft = tableWrapper.scrollLeft;
19
+ return fixedButtonRect.left - tableWrapperRect.left + scrollLeft;
20
+ };
21
+ export var FixedButton = function FixedButton(_ref2) {
22
+ var children = _ref2.children,
23
+ isContextualMenuOpen = _ref2.isContextualMenuOpen,
24
+ mountTo = _ref2.mountTo,
25
+ offset = _ref2.offset,
26
+ stickyHeader = _ref2.stickyHeader,
27
+ tableWrapper = _ref2.tableWrapper,
28
+ targetCellPosition = _ref2.targetCellPosition,
29
+ targetCellRef = _ref2.targetCellRef;
30
+ var fixedButtonRef = useRef(null);
31
+ var observerTargetRef = useRef(null);
32
+
33
+ // Using refs here rather than state to prevent heaps of renders on scroll
34
+ var scrollDataRef = useRef(0);
35
+ var leftPosDataRef = useRef(0);
36
+ useEffect(function () {
37
+ var observerTargetRefCurrent = observerTargetRef.current;
38
+ var fixedButtonRefCurrent = fixedButtonRef.current;
39
+ if (fixedButtonRefCurrent && observerTargetRefCurrent) {
40
+ scrollDataRef.current = tableWrapper.scrollLeft;
41
+ leftPosDataRef.current = 0;
42
+ // Hide the button initially in case there's a flash of the button being
43
+ // outside the table before the Intersection Observer fires
44
+ fixedButtonRefCurrent.style.visibility = 'hidden';
45
+ var margin = calcObserverTargetMargin(tableWrapper, fixedButtonRefCurrent);
46
+
47
+ // Much more simple and predictable to add this margin to the observer target
48
+ // rather than using it to calculate the rootMargin values
49
+ observerTargetRefCurrent.style.marginLeft = "".concat(margin, "px");
50
+ var observer = new IntersectionObserver(function (entries) {
51
+ entries.forEach(function (entry) {
52
+ if (entry.isIntersecting) {
53
+ fixedButtonRefCurrent.style.visibility = 'visible';
54
+ } else {
55
+ fixedButtonRefCurrent.style.visibility = 'hidden';
56
+ }
57
+ });
58
+ }, {
59
+ root: tableWrapper,
60
+ rootMargin: "0px ".concat(insertColumnButtonOffset, "px 0px 0px"),
61
+ threshold: 1
62
+ });
63
+ var handleScroll = rafSchedule(function (event) {
64
+ if (fixedButtonRef.current) {
65
+ var delta = event.target.scrollLeft - scrollDataRef.current;
66
+ var style = "translateX(".concat(leftPosDataRef.current - delta, "px)");
67
+ fixedButtonRef.current.style.transform = style;
68
+ scrollDataRef.current = event.target.scrollLeft;
69
+ leftPosDataRef.current = leftPosDataRef.current - delta;
70
+ }
71
+ });
72
+ observer.observe(observerTargetRefCurrent);
73
+ tableWrapper.addEventListener('scroll', handleScroll);
74
+ return function () {
75
+ tableWrapper.removeEventListener('scroll', handleScroll);
76
+ fixedButtonRefCurrent.style.transform = '';
77
+ observer.unobserve(observerTargetRefCurrent);
78
+ };
79
+ }
80
+ }, [fixedButtonRef, observerTargetRef, tableWrapper, targetCellPosition, targetCellRef, isContextualMenuOpen]);
81
+ var targetCellRect = targetCellRef.getBoundingClientRect();
82
+
83
+ // Using a portal here to ensure wrapperRef has the tableWrapper as an
84
+ // ancestor. This is required to make the Intersection Observer work.
85
+ return /*#__PURE__*/createPortal(
86
+ /*#__PURE__*/
87
+ // Using observerTargetRef here for our Intersection Observer. There is issues
88
+ // getting the observer to work just using the fixedButtonRef, possible due
89
+ // to using position fixed on this Element, or possibly due to its position
90
+ // being changed on scroll.
91
+ React.createElement("div", {
92
+ ref: observerTargetRef,
93
+ style: {
94
+ position: 'absolute',
95
+ top: '0px',
96
+ left: '0px',
97
+ width: "".concat(BUTTON_WIDTH, "px"),
98
+ height: "".concat(BUTTON_WIDTH, "px")
99
+ }
100
+ }, /*#__PURE__*/React.createElement("div", {
101
+ ref: fixedButtonRef,
102
+ style: {
103
+ position: 'fixed',
104
+ top: stickyHeader.top + stickyHeader.padding + offset * 2,
105
+ zIndex: akEditorFloatingPanelZIndex,
106
+ left: calcLeftPos({
107
+ buttonWidth: BUTTON_WIDTH,
108
+ cellRectLeft: targetCellRect.left,
109
+ cellRefWidth: targetCellRef.clientWidth,
110
+ offset: offset
111
+ }),
112
+ width: "".concat(BUTTON_WIDTH, "px"),
113
+ height: "".concat(BUTTON_WIDTH, "px")
114
+ },
115
+ className: ClassName.CONTEXTUAL_MENU_BUTTON_FIXED
116
+ }, children)), mountTo);
117
+ };
118
+ export default FixedButton;
@@ -1,148 +1,92 @@
1
- import _classCallCheck from "@babel/runtime/helpers/classCallCheck";
2
- import _createClass from "@babel/runtime/helpers/createClass";
3
- import _assertThisInitialized from "@babel/runtime/helpers/assertThisInitialized";
4
- import _inherits from "@babel/runtime/helpers/inherits";
5
- import _possibleConstructorReturn from "@babel/runtime/helpers/possibleConstructorReturn";
6
- import _getPrototypeOf from "@babel/runtime/helpers/getPrototypeOf";
7
- import _defineProperty from "@babel/runtime/helpers/defineProperty";
8
- function _createSuper(Derived) { var hasNativeReflectConstruct = _isNativeReflectConstruct(); return function _createSuperInternal() { var Super = _getPrototypeOf(Derived), result; if (hasNativeReflectConstruct) { var NewTarget = _getPrototypeOf(this).constructor; result = Reflect.construct(Super, arguments, NewTarget); } else { result = Super.apply(this, arguments); } return _possibleConstructorReturn(this, result); }; }
9
- function _isNativeReflectConstruct() { if (typeof Reflect === "undefined" || !Reflect.construct) return false; if (Reflect.construct.sham) return false; if (typeof Proxy === "function") return true; try { Boolean.prototype.valueOf.call(Reflect.construct(Boolean, [], function () {})); return true; } catch (e) { return false; } }
10
1
  /** @jsx jsx */
11
2
  import React from 'react';
12
3
  import { jsx } from '@emotion/react';
13
4
  import { findDomRefAtPos } from 'prosemirror-utils';
14
5
  import { injectIntl } from 'react-intl-next';
15
6
  import { Popup } from '@atlaskit/editor-common/ui';
16
- import { akEditorFloatingOverlapPanelZIndex, akEditorSmallZIndex } from '@atlaskit/editor-shared-styles';
7
+ import { akEditorSmallZIndex } from '@atlaskit/editor-shared-styles';
17
8
  import ExpandIcon from '@atlaskit/icon/glyph/chevron-down';
18
9
  import { ToolbarButton } from '@atlaskit/editor-common/ui-menu';
19
- import { closestElement } from '@atlaskit/editor-common/utils';
20
10
  import { toggleContextualMenu } from '../../commands';
21
11
  import { TableCssClassName as ClassName } from '../../types';
22
12
  import messages from '../../ui/messages';
23
- import { CONTENT_COMPONENT } from '@atlaskit/editor-common/analytics';
24
- import { ACTION, ACTION_SUBJECT, EVENT_TYPE } from '@atlaskit/editor-common/analytics';
13
+ import FixedButton from './FixedButton';
14
+ import { ACTION_SUBJECT } from '@atlaskit/editor-common/analytics';
25
15
  import { tableFloatingCellButtonStyles, tableFloatingCellButtonSelectedStyles } from './styles';
26
16
  import { ErrorBoundary } from '@atlaskit/editor-common/error-boundary';
27
- export var FloatingContextualButtonInner = /*#__PURE__*/function (_React$Component) {
28
- _inherits(FloatingContextualButtonInner, _React$Component);
29
- var _super = _createSuper(FloatingContextualButtonInner);
30
- function FloatingContextualButtonInner() {
31
- var _this;
32
- _classCallCheck(this, FloatingContextualButtonInner);
33
- for (var _len = arguments.length, args = new Array(_len), _key = 0; _key < _len; _key++) {
34
- args[_key] = arguments[_key];
17
+ var BUTTON_OFFSET = 3;
18
+ var FloatingContextualButtonInner = /*#__PURE__*/React.memo(function (props) {
19
+ var editorView = props.editorView,
20
+ isContextualMenuOpen = props.isContextualMenuOpen,
21
+ mountPoint = props.mountPoint,
22
+ scrollableElement = props.scrollableElement,
23
+ stickyHeader = props.stickyHeader,
24
+ tableWrapper = props.tableWrapper,
25
+ targetCellPosition = props.targetCellPosition,
26
+ formatMessage = props.intl.formatMessage; // : Props & WrappedComponentProps
27
+
28
+ var handleClick = function handleClick() {
29
+ var state = editorView.state,
30
+ dispatch = editorView.dispatch;
31
+ // Clicking outside the dropdown handles toggling the menu closed
32
+ // (otherwise these two toggles combat each other).
33
+ // In the event a user clicks the chevron button again
34
+ // That will count as clicking outside the dropdown and
35
+ // will be toggled appropriately
36
+ if (!isContextualMenuOpen) {
37
+ toggleContextualMenu()(state, dispatch);
35
38
  }
36
- _this = _super.call.apply(_super, [this].concat(args));
37
- _defineProperty(_assertThisInitialized(_this), "handleClick", function () {
38
- var _this$props$editorVie = _this.props.editorView,
39
- state = _this$props$editorVie.state,
40
- dispatch = _this$props$editorVie.dispatch;
41
- // Clicking outside the dropdown handles toggling the menu closed
42
- // (otherwise these two toggles combat each other).
43
- // In the event a user clicks the chevron button again
44
- // That will count as clicking outside the dropdown and
45
- // will be toggled appropriately
46
- if (!_this.props.isContextualMenuOpen) {
47
- toggleContextualMenu()(state, dispatch);
48
- }
49
- });
50
- return _this;
39
+ };
40
+ var domAtPos = editorView.domAtPos.bind(editorView);
41
+ var targetCellRef;
42
+ targetCellRef = findDomRefAtPos(targetCellPosition, domAtPos);
43
+ if (!targetCellRef || !(targetCellRef instanceof HTMLElement)) {
44
+ return null;
51
45
  }
52
- _createClass(FloatingContextualButtonInner, [{
53
- key: "render",
54
- value: function render() {
55
- var _this$props = this.props,
56
- mountPoint = _this$props.mountPoint,
57
- scrollableElement = _this$props.scrollableElement,
58
- editorView = _this$props.editorView,
59
- targetCellPosition = _this$props.targetCellPosition,
60
- isContextualMenuOpen = _this$props.isContextualMenuOpen,
61
- formatMessage = _this$props.intl.formatMessage,
62
- dispatchAnalyticsEvent = _this$props.dispatchAnalyticsEvent; // : Props & WrappedComponentProps
63
- var domAtPos = editorView.domAtPos.bind(editorView);
64
- var targetCellRef;
65
- try {
66
- targetCellRef = findDomRefAtPos(targetCellPosition, domAtPos);
67
- } catch (error) {
68
- // eslint-disable-next-line no-console
69
- console.warn(error);
70
- if (dispatchAnalyticsEvent) {
71
- var payload = {
72
- action: ACTION.ERRORED,
73
- actionSubject: ACTION_SUBJECT.CONTENT_COMPONENT,
74
- eventType: EVENT_TYPE.OPERATIONAL,
75
- attributes: {
76
- component: CONTENT_COMPONENT.FLOATING_CONTEXTUAL_BUTTON,
77
- selection: editorView.state.selection.toJSON(),
78
- position: targetCellPosition,
79
- docSize: editorView.state.doc.nodeSize,
80
- error: error instanceof Error ? error.message : String(error)
81
- },
82
- nonPrivacySafeAttributes: {
83
- errorStack: error instanceof Error ? error.stack : undefined
84
- }
85
- };
86
- dispatchAnalyticsEvent(payload);
87
- }
88
- }
89
- if (!targetCellRef || !(targetCellRef instanceof HTMLElement)) {
90
- return null;
91
- }
92
- var tableWrapper = closestElement(targetCellRef, ".".concat(ClassName.TABLE_NODE_WRAPPER));
93
- var labelCellOptions = formatMessage(messages.cellOptions);
94
- var button = jsx("div", {
95
- css: function css(theme) {
96
- return [tableFloatingCellButtonStyles({
97
- theme: theme
98
- }), isContextualMenuOpen && tableFloatingCellButtonSelectedStyles({
99
- theme: theme
100
- })];
101
- }
102
- }, jsx(ToolbarButton, {
103
- className: ClassName.CONTEXTUAL_MENU_BUTTON,
104
- selected: isContextualMenuOpen,
105
- title: labelCellOptions,
106
- onClick: this.handleClick,
107
- iconBefore: jsx(ExpandIcon, {
108
- label: ""
109
- }),
110
- "aria-label": labelCellOptions
111
- }));
112
- var parentSticky = targetCellRef.parentElement && targetCellRef.parentElement.className.indexOf('sticky') > -1;
113
- if (this.props.stickyHeader && parentSticky) {
114
- var pos = targetCellRef.getBoundingClientRect();
115
- return jsx("div", {
116
- style: {
117
- position: 'fixed',
118
- top: this.props.stickyHeader.top + this.props.stickyHeader.padding + 3 + 3,
119
- zIndex: akEditorFloatingOverlapPanelZIndex,
120
- left: pos.left + targetCellRef.clientWidth - 20 - 3
121
- }
122
- }, button);
123
- }
124
- return jsx(Popup, {
125
- alignX: "right",
126
- alignY: "start",
127
- target: targetCellRef,
128
- mountTo: tableWrapper || mountPoint,
129
- boundariesElement: targetCellRef,
130
- scrollableElement: scrollableElement,
131
- offset: [3, -3],
132
- forcePlacement: true,
133
- allowOutOfBounds: true,
134
- zIndex: akEditorSmallZIndex
135
- }, button);
46
+ var labelCellOptions = formatMessage(messages.cellOptions);
47
+ var button = jsx("div", {
48
+ css: function css(theme) {
49
+ return [tableFloatingCellButtonStyles({
50
+ theme: theme
51
+ }), isContextualMenuOpen && tableFloatingCellButtonSelectedStyles({
52
+ theme: theme
53
+ })];
136
54
  }
137
- }, {
138
- key: "shouldComponentUpdate",
139
- value: function shouldComponentUpdate(nextProps) {
140
- return this.props.tableNode !== nextProps.tableNode || this.props.targetCellPosition !== nextProps.targetCellPosition || this.props.layout !== nextProps.layout || this.props.isContextualMenuOpen !== nextProps.isContextualMenuOpen || this.props.isNumberColumnEnabled !== nextProps.isNumberColumnEnabled || this.props.stickyHeader !== nextProps.stickyHeader;
141
- }
142
- }]);
143
- return FloatingContextualButtonInner;
144
- }(React.Component);
145
- _defineProperty(FloatingContextualButtonInner, "displayName", 'FloatingContextualButton');
55
+ }, jsx(ToolbarButton, {
56
+ className: ClassName.CONTEXTUAL_MENU_BUTTON,
57
+ selected: isContextualMenuOpen,
58
+ title: labelCellOptions,
59
+ onClick: handleClick,
60
+ iconBefore: jsx(ExpandIcon, {
61
+ label: ""
62
+ }),
63
+ "aria-label": labelCellOptions
64
+ }));
65
+ var parentSticky = targetCellRef.parentElement && targetCellRef.parentElement.className.indexOf('sticky') > -1;
66
+ if (stickyHeader && parentSticky && tableWrapper) {
67
+ return jsx(FixedButton, {
68
+ offset: BUTTON_OFFSET,
69
+ stickyHeader: stickyHeader,
70
+ tableWrapper: tableWrapper,
71
+ targetCellPosition: targetCellPosition,
72
+ targetCellRef: targetCellRef,
73
+ mountTo: tableWrapper,
74
+ isContextualMenuOpen: isContextualMenuOpen
75
+ }, button);
76
+ }
77
+ return jsx(Popup, {
78
+ alignX: "right",
79
+ alignY: "start",
80
+ target: targetCellRef,
81
+ mountTo: tableWrapper || mountPoint,
82
+ boundariesElement: targetCellRef,
83
+ scrollableElement: scrollableElement,
84
+ offset: [BUTTON_OFFSET, -BUTTON_OFFSET],
85
+ forcePlacement: true,
86
+ allowOutOfBounds: true,
87
+ zIndex: akEditorSmallZIndex
88
+ }, button);
89
+ });
146
90
  var FloatingContextualButton = injectIntl(FloatingContextualButtonInner);
147
91
  export default function (props) {
148
92
  return jsx(ErrorBoundary, {
@@ -1,5 +1,5 @@
1
1
  {
2
2
  "name": "@atlaskit/editor-plugin-table",
3
- "version": "1.6.1",
3
+ "version": "1.6.3",
4
4
  "sideEffects": false
5
5
  }
@@ -272,6 +272,7 @@ export declare const TableCssClassName: {
272
272
  CONTEXTUAL_SUBMENU: string;
273
273
  CONTEXTUAL_MENU_BUTTON_WRAP: string;
274
274
  CONTEXTUAL_MENU_BUTTON: string;
275
+ CONTEXTUAL_MENU_BUTTON_FIXED: string;
275
276
  CONTEXTUAL_MENU_ICON: string;
276
277
  SELECTED_CELL: string;
277
278
  NODEVIEW_WRAPPER: string;
@@ -0,0 +1,23 @@
1
+ import React from 'react';
2
+ import { RowStickyState } from '../../pm-plugins/sticky-headers';
3
+ export declare const BUTTON_WIDTH = 20;
4
+ export interface Props {
5
+ children: React.ReactNode;
6
+ mountTo: HTMLElement;
7
+ offset: number;
8
+ stickyHeader: RowStickyState;
9
+ targetCellPosition: number;
10
+ targetCellRef: HTMLElement;
11
+ tableWrapper: HTMLElement;
12
+ isContextualMenuOpen: boolean | undefined;
13
+ }
14
+ interface CalcLeftPosData {
15
+ buttonWidth: number;
16
+ cellRectLeft: number;
17
+ cellRefWidth: number;
18
+ offset: number;
19
+ }
20
+ export declare const calcLeftPos: ({ buttonWidth, cellRectLeft, cellRefWidth, offset, }: CalcLeftPosData) => number;
21
+ export declare const calcObserverTargetMargin: (tableWrapper: HTMLElement, fixedButtonRefCurrent: HTMLElement) => number;
22
+ export declare const FixedButton: ({ children, isContextualMenuOpen, mountTo, offset, stickyHeader, tableWrapper, targetCellPosition, targetCellRef, }: Props) => React.ReactPortal;
23
+ export default FixedButton;
@@ -1,14 +1,12 @@
1
- /** @jsx jsx */
2
- import React from 'react';
3
1
  import { jsx } from '@emotion/react';
4
2
  import { EditorView } from 'prosemirror-view';
5
- import { WrappedComponentProps } from 'react-intl-next';
6
3
  import { TableLayout } from '@atlaskit/adf-schema';
7
4
  import { RowStickyState } from '../../pm-plugins/sticky-headers';
8
5
  import { DispatchAnalyticsEvent } from '@atlaskit/editor-common/analytics';
9
6
  import { Node as PMNode } from 'prosemirror-model';
10
7
  export interface Props {
11
8
  editorView: EditorView;
9
+ tableWrapper?: HTMLElement;
12
10
  tableNode?: PMNode;
13
11
  targetCellPosition: number;
14
12
  isContextualMenuOpen?: boolean;
@@ -20,10 +18,4 @@ export interface Props {
20
18
  stickyHeader?: RowStickyState;
21
19
  dispatchAnalyticsEvent?: DispatchAnalyticsEvent;
22
20
  }
23
- export declare class FloatingContextualButtonInner extends React.Component<Props & WrappedComponentProps, any> {
24
- static displayName: string;
25
- render(): jsx.JSX.Element | null;
26
- shouldComponentUpdate(nextProps: Props): boolean;
27
- private handleClick;
28
- }
29
21
  export default function (props: Props): jsx.JSX.Element;