@atlaskit/editor-plugin-toolbar 2.1.4 → 2.1.5
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.
- package/CHANGELOG.md +9 -0
- package/afm-cc/tsconfig.json +3 -0
- package/dist/cjs/ui/SelectionToolbar/index.js +53 -1
- package/dist/cjs/ui/toolbar-components.js +2 -1
- package/dist/cjs/ui/utils/toolbar.js +19 -1
- package/dist/es2019/ui/SelectionToolbar/index.js +55 -3
- package/dist/es2019/ui/toolbar-components.js +2 -1
- package/dist/es2019/ui/utils/toolbar.js +18 -0
- package/dist/esm/ui/SelectionToolbar/index.js +55 -3
- package/dist/esm/ui/toolbar-components.js +2 -1
- package/dist/esm/ui/utils/toolbar.js +18 -0
- package/dist/types/ui/utils/toolbar.d.ts +2 -0
- package/dist/types-ts4.5/ui/utils/toolbar.d.ts +2 -0
- package/package.json +4 -3
package/CHANGELOG.md
CHANGED
|
@@ -1,5 +1,14 @@
|
|
|
1
1
|
# @atlaskit/editor-plugin-toolbar
|
|
2
2
|
|
|
3
|
+
## 2.1.5
|
|
4
|
+
|
|
5
|
+
### Patch Changes
|
|
6
|
+
|
|
7
|
+
- [`bb498825fca37`](https://bitbucket.org/atlassian/atlassian-frontend-monorepo/commits/bb498825fca37) -
|
|
8
|
+
[ux] [ED-29266] add ToolbarKeyboardNavigationProvider to selection toolbar with Alt+F10 shortcut
|
|
9
|
+
to focus
|
|
10
|
+
- Updated dependencies
|
|
11
|
+
|
|
3
12
|
## 2.1.4
|
|
4
13
|
|
|
5
14
|
### Patch Changes
|
package/afm-cc/tsconfig.json
CHANGED
|
@@ -6,8 +6,11 @@ Object.defineProperty(exports, "__esModule", {
|
|
|
6
6
|
});
|
|
7
7
|
exports.SelectionToolbar = void 0;
|
|
8
8
|
var _react = _interopRequireWildcard(require("react"));
|
|
9
|
+
var _reactIntlNext = require("react-intl-next");
|
|
10
|
+
var _browserApis = require("@atlaskit/browser-apis");
|
|
9
11
|
var _coreUtils = require("@atlaskit/editor-common/core-utils");
|
|
10
12
|
var _hooks = require("@atlaskit/editor-common/hooks");
|
|
13
|
+
var _messages = require("@atlaskit/editor-common/messages");
|
|
11
14
|
var _toolbar = require("@atlaskit/editor-common/toolbar");
|
|
12
15
|
var _ui = require("@atlaskit/editor-common/ui");
|
|
13
16
|
var _useSharedPluginStateSelector = require("@atlaskit/editor-common/use-shared-plugin-state-selector");
|
|
@@ -20,6 +23,7 @@ var _platformFeatureFlagsReact = require("@atlaskit/platform-feature-flags-react
|
|
|
20
23
|
var _expValEquals = require("@atlaskit/tmp-editor-statsig/exp-val-equals");
|
|
21
24
|
var _expValEqualsNoExposure = require("@atlaskit/tmp-editor-statsig/exp-val-equals-no-exposure");
|
|
22
25
|
var _consts = require("../consts");
|
|
26
|
+
var _toolbar2 = require("../utils/toolbar");
|
|
23
27
|
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); }
|
|
24
28
|
var isToolbarComponent = function isToolbarComponent(component) {
|
|
25
29
|
return component.type === 'toolbar' && component.key === 'inline-text-toolbar';
|
|
@@ -76,10 +80,14 @@ var SelectionToolbar = exports.SelectionToolbar = function SelectionToolbar(_ref
|
|
|
76
80
|
shouldShowToolbar = _usePluginState.shouldShowToolbar,
|
|
77
81
|
editorViewMode = _usePluginState.editorViewMode,
|
|
78
82
|
selection = _usePluginState.selection;
|
|
83
|
+
var intl = (0, _reactIntlNext.useIntl)();
|
|
79
84
|
var components = api === null || api === void 0 || (_api$toolbar = api.toolbar) === null || _api$toolbar === void 0 ? void 0 : _api$toolbar.actions.getComponents();
|
|
80
85
|
var toolbar = components === null || components === void 0 ? void 0 : components.find(function (component) {
|
|
81
86
|
return isToolbarComponent(component);
|
|
82
87
|
});
|
|
88
|
+
var keyboardNavigation = (0, _react.useMemo)(function () {
|
|
89
|
+
return getKeyboardNavigationConfig(editorView, intl, api);
|
|
90
|
+
}, [editorView, intl, api]);
|
|
83
91
|
var isOffline = connectivityStateMode === 'offline';
|
|
84
92
|
var isTextSelection = !editorView.state.selection.empty && editorView.state.selection instanceof _state.TextSelection;
|
|
85
93
|
var isAllSelection = !editorView.state.selection.empty && editorView.state.selection instanceof _state.AllSelection && (0, _expValEquals.expValEquals)('platform_editor_toolbar_aifc_patch_2', 'isEnabled', true);
|
|
@@ -118,7 +126,8 @@ var SelectionToolbar = exports.SelectionToolbar = function SelectionToolbar(_ref
|
|
|
118
126
|
fireAnalyticsEvent: (0, _expValEquals.expValEquals)('platform_editor_toolbar_aifc_toolbar_analytic', 'isEnabled', true) ? function (payload) {
|
|
119
127
|
var _api$analytics;
|
|
120
128
|
api === null || api === void 0 || (_api$analytics = api.analytics) === null || _api$analytics === void 0 || _api$analytics.actions.fireAnalyticsEvent(payload);
|
|
121
|
-
} : undefined
|
|
129
|
+
} : undefined,
|
|
130
|
+
keyboardNavigation: (0, _expValEquals.expValEquals)('platform_editor_toolbar_aifc_patch_5', 'isEnabled', true) ? keyboardNavigation : undefined
|
|
122
131
|
}, /*#__PURE__*/_react.default.createElement(_editorToolbarModel.ToolbarModelRenderer, {
|
|
123
132
|
toolbar: toolbar,
|
|
124
133
|
components: components,
|
|
@@ -160,4 +169,47 @@ var getDomRefFromSelection = function getDomRefFromSelection(view
|
|
|
160
169
|
// dispatchAnalyticsEvent(payload);
|
|
161
170
|
// }
|
|
162
171
|
}
|
|
172
|
+
};
|
|
173
|
+
var getKeyboardNavigationConfig = function getKeyboardNavigationConfig(editorView, intl, api) {
|
|
174
|
+
if (!(editorView.dom instanceof HTMLElement)) {
|
|
175
|
+
return;
|
|
176
|
+
}
|
|
177
|
+
var toolbarSelector = "[data-testid='editor-floating-toolbar']";
|
|
178
|
+
return {
|
|
179
|
+
childComponentSelector: toolbarSelector,
|
|
180
|
+
dom: editorView.dom,
|
|
181
|
+
isShortcutToFocusToolbar: _toolbar2.isShortcutToFocusToolbar,
|
|
182
|
+
handleFocus: function handleFocus(event) {
|
|
183
|
+
var _getDocument, _filteredFocusableEle, _filteredFocusableEle2, _filteredFocusableEle3;
|
|
184
|
+
var toolbar = (_getDocument = (0, _browserApis.getDocument)()) === null || _getDocument === void 0 ? void 0 : _getDocument.querySelector(toolbarSelector);
|
|
185
|
+
if (!(toolbar instanceof HTMLElement)) {
|
|
186
|
+
return;
|
|
187
|
+
}
|
|
188
|
+
var filteredFocusableElements = (0, _toolbar2.getFocusableElements)(toolbar);
|
|
189
|
+
(_filteredFocusableEle = filteredFocusableElements[0]) === null || _filteredFocusableEle === void 0 || _filteredFocusableEle.focus();
|
|
190
|
+
|
|
191
|
+
// the button element removes the focus ring so this class adds it back
|
|
192
|
+
if (((_filteredFocusableEle2 = filteredFocusableElements[0]) === null || _filteredFocusableEle2 === void 0 ? void 0 : _filteredFocusableEle2.tagName) === 'BUTTON') {
|
|
193
|
+
filteredFocusableElements[0].classList.add('first-floating-toolbar-button');
|
|
194
|
+
}
|
|
195
|
+
(_filteredFocusableEle3 = filteredFocusableElements[0]) === null || _filteredFocusableEle3 === void 0 || _filteredFocusableEle3.scrollIntoView({
|
|
196
|
+
behavior: 'smooth',
|
|
197
|
+
block: 'center',
|
|
198
|
+
inline: 'nearest'
|
|
199
|
+
});
|
|
200
|
+
event.preventDefault();
|
|
201
|
+
event.stopPropagation();
|
|
202
|
+
},
|
|
203
|
+
handleEscape: function handleEscape(event) {
|
|
204
|
+
var isDropdownOpen = !!document.querySelector('[data-toolbar-component="menu-section"]');
|
|
205
|
+
if (isDropdownOpen) {
|
|
206
|
+
return;
|
|
207
|
+
}
|
|
208
|
+
api === null || api === void 0 || api.core.actions.focus();
|
|
209
|
+
event.preventDefault();
|
|
210
|
+
event.stopPropagation();
|
|
211
|
+
},
|
|
212
|
+
ariaControls: _ui.EDIT_AREA_ID,
|
|
213
|
+
ariaLabel: intl.formatMessage(_messages.fullPageMessages.toolbarLabel)
|
|
214
|
+
};
|
|
163
215
|
};
|
|
@@ -25,7 +25,8 @@ var getToolbarComponents = exports.getToolbarComponents = function getToolbarCom
|
|
|
25
25
|
var children = _ref.children;
|
|
26
26
|
return /*#__PURE__*/_react.default.createElement(_editorToolbar.Toolbar, {
|
|
27
27
|
label: _consts.SELECTION_TOOLBAR_LABEL,
|
|
28
|
-
actionSubjectId: _analytics.ACTION_SUBJECT_ID.SELECTION_TOOLBAR
|
|
28
|
+
actionSubjectId: _analytics.ACTION_SUBJECT_ID.SELECTION_TOOLBAR,
|
|
29
|
+
testId: (0, _expValEquals.expValEquals)('platform_editor_toolbar_aifc_patch_5', 'isEnabled', true) ? 'editor-floating-toolbar' : undefined
|
|
29
30
|
}, children);
|
|
30
31
|
}
|
|
31
32
|
}, {
|
|
@@ -3,11 +3,29 @@
|
|
|
3
3
|
Object.defineProperty(exports, "__esModule", {
|
|
4
4
|
value: true
|
|
5
5
|
});
|
|
6
|
-
exports.isEventInContainer = void 0;
|
|
6
|
+
exports.isShortcutToFocusToolbar = exports.isEventInContainer = exports.getFocusableElements = void 0;
|
|
7
7
|
var isEventInContainer = exports.isEventInContainer = function isEventInContainer(event, containerSelector) {
|
|
8
8
|
var target = event.target instanceof Element ? event.target : null;
|
|
9
9
|
if (!target) {
|
|
10
10
|
return false;
|
|
11
11
|
}
|
|
12
12
|
return !!target.closest(containerSelector);
|
|
13
|
+
};
|
|
14
|
+
var isShortcutToFocusToolbar = exports.isShortcutToFocusToolbar = function isShortcutToFocusToolbar(event) {
|
|
15
|
+
return event.altKey && event.key === 'F10';
|
|
16
|
+
};
|
|
17
|
+
var getFocusableElements = exports.getFocusableElements = function getFocusableElements(rootNode) {
|
|
18
|
+
if (!rootNode) {
|
|
19
|
+
return [];
|
|
20
|
+
}
|
|
21
|
+
var focusableElements = rootNode.querySelectorAll('a[href], button:not([disabled]), textarea, input, select, div[tabindex="-1"], div[tabindex="0"]') || [];
|
|
22
|
+
var focusableElementsArray = Array.from(focusableElements);
|
|
23
|
+
|
|
24
|
+
// filter out focusable elements from child components such as dropdown menus / popups
|
|
25
|
+
return focusableElementsArray.filter(function (elm) {
|
|
26
|
+
var style = window.getComputedStyle(elm);
|
|
27
|
+
|
|
28
|
+
// filter out invisible elements
|
|
29
|
+
return style.visibility !== 'hidden' && style.display !== 'none';
|
|
30
|
+
});
|
|
13
31
|
};
|
|
@@ -1,8 +1,11 @@
|
|
|
1
|
-
import React, { useCallback } from 'react';
|
|
1
|
+
import React, { useCallback, useMemo } from 'react';
|
|
2
|
+
import { useIntl } from 'react-intl-next';
|
|
3
|
+
import { getDocument } from '@atlaskit/browser-apis';
|
|
2
4
|
import { isSSR } from '@atlaskit/editor-common/core-utils';
|
|
3
5
|
import { useSharedPluginStateWithSelector } from '@atlaskit/editor-common/hooks';
|
|
6
|
+
import { fullPageMessages } from '@atlaskit/editor-common/messages';
|
|
4
7
|
import { EditorToolbarProvider, EditorToolbarUIProvider } from '@atlaskit/editor-common/toolbar';
|
|
5
|
-
import { Popup } from '@atlaskit/editor-common/ui';
|
|
8
|
+
import { Popup, EDIT_AREA_ID } from '@atlaskit/editor-common/ui';
|
|
6
9
|
import { useSharedPluginStateSelector } from '@atlaskit/editor-common/use-shared-plugin-state-selector';
|
|
7
10
|
import { calculateToolbarPositionTrackHead, calculateToolbarPositionOnCellSelection } from '@atlaskit/editor-common/utils';
|
|
8
11
|
import { AllSelection, TextSelection } from '@atlaskit/editor-prosemirror/state';
|
|
@@ -13,6 +16,7 @@ import { conditionalHooksFactory } from '@atlaskit/platform-feature-flags-react'
|
|
|
13
16
|
import { expValEquals } from '@atlaskit/tmp-editor-statsig/exp-val-equals';
|
|
14
17
|
import { expValEqualsNoExposure } from '@atlaskit/tmp-editor-statsig/exp-val-equals-no-exposure';
|
|
15
18
|
import { SELECTION_TOOLBAR_LABEL } from '../consts';
|
|
19
|
+
import { getFocusableElements, isShortcutToFocusToolbar } from '../utils/toolbar';
|
|
16
20
|
const isToolbarComponent = component => {
|
|
17
21
|
return component.type === 'toolbar' && component.key === 'inline-text-toolbar';
|
|
18
22
|
};
|
|
@@ -70,8 +74,12 @@ export const SelectionToolbar = ({
|
|
|
70
74
|
// @ts-expect-error
|
|
71
75
|
selection
|
|
72
76
|
} = usePluginState(api);
|
|
77
|
+
const intl = useIntl();
|
|
73
78
|
const components = api === null || api === void 0 ? void 0 : (_api$toolbar = api.toolbar) === null || _api$toolbar === void 0 ? void 0 : _api$toolbar.actions.getComponents();
|
|
74
79
|
const toolbar = components === null || components === void 0 ? void 0 : components.find(component => isToolbarComponent(component));
|
|
80
|
+
const keyboardNavigation = useMemo(() => {
|
|
81
|
+
return getKeyboardNavigationConfig(editorView, intl, api);
|
|
82
|
+
}, [editorView, intl, api]);
|
|
75
83
|
const isOffline = connectivityStateMode === 'offline';
|
|
76
84
|
const isTextSelection = !editorView.state.selection.empty && editorView.state.selection instanceof TextSelection;
|
|
77
85
|
const isAllSelection = !editorView.state.selection.empty && editorView.state.selection instanceof AllSelection && expValEquals('platform_editor_toolbar_aifc_patch_2', 'isEnabled', true);
|
|
@@ -110,7 +118,8 @@ export const SelectionToolbar = ({
|
|
|
110
118
|
fireAnalyticsEvent: expValEquals('platform_editor_toolbar_aifc_toolbar_analytic', 'isEnabled', true) ? payload => {
|
|
111
119
|
var _api$analytics;
|
|
112
120
|
api === null || api === void 0 ? void 0 : (_api$analytics = api.analytics) === null || _api$analytics === void 0 ? void 0 : _api$analytics.actions.fireAnalyticsEvent(payload);
|
|
113
|
-
} : undefined
|
|
121
|
+
} : undefined,
|
|
122
|
+
keyboardNavigation: expValEquals('platform_editor_toolbar_aifc_patch_5', 'isEnabled', true) ? keyboardNavigation : undefined
|
|
114
123
|
}, /*#__PURE__*/React.createElement(ToolbarModelRenderer, {
|
|
115
124
|
toolbar: toolbar,
|
|
116
125
|
components: components,
|
|
@@ -152,4 +161,47 @@ const getDomRefFromSelection = (view
|
|
|
152
161
|
// dispatchAnalyticsEvent(payload);
|
|
153
162
|
// }
|
|
154
163
|
}
|
|
164
|
+
};
|
|
165
|
+
const getKeyboardNavigationConfig = (editorView, intl, api) => {
|
|
166
|
+
if (!(editorView.dom instanceof HTMLElement)) {
|
|
167
|
+
return;
|
|
168
|
+
}
|
|
169
|
+
const toolbarSelector = "[data-testid='editor-floating-toolbar']";
|
|
170
|
+
return {
|
|
171
|
+
childComponentSelector: toolbarSelector,
|
|
172
|
+
dom: editorView.dom,
|
|
173
|
+
isShortcutToFocusToolbar: isShortcutToFocusToolbar,
|
|
174
|
+
handleFocus: event => {
|
|
175
|
+
var _getDocument, _filteredFocusableEle, _filteredFocusableEle2, _filteredFocusableEle3;
|
|
176
|
+
const toolbar = (_getDocument = getDocument()) === null || _getDocument === void 0 ? void 0 : _getDocument.querySelector(toolbarSelector);
|
|
177
|
+
if (!(toolbar instanceof HTMLElement)) {
|
|
178
|
+
return;
|
|
179
|
+
}
|
|
180
|
+
const filteredFocusableElements = getFocusableElements(toolbar);
|
|
181
|
+
(_filteredFocusableEle = filteredFocusableElements[0]) === null || _filteredFocusableEle === void 0 ? void 0 : _filteredFocusableEle.focus();
|
|
182
|
+
|
|
183
|
+
// the button element removes the focus ring so this class adds it back
|
|
184
|
+
if (((_filteredFocusableEle2 = filteredFocusableElements[0]) === null || _filteredFocusableEle2 === void 0 ? void 0 : _filteredFocusableEle2.tagName) === 'BUTTON') {
|
|
185
|
+
filteredFocusableElements[0].classList.add('first-floating-toolbar-button');
|
|
186
|
+
}
|
|
187
|
+
(_filteredFocusableEle3 = filteredFocusableElements[0]) === null || _filteredFocusableEle3 === void 0 ? void 0 : _filteredFocusableEle3.scrollIntoView({
|
|
188
|
+
behavior: 'smooth',
|
|
189
|
+
block: 'center',
|
|
190
|
+
inline: 'nearest'
|
|
191
|
+
});
|
|
192
|
+
event.preventDefault();
|
|
193
|
+
event.stopPropagation();
|
|
194
|
+
},
|
|
195
|
+
handleEscape: event => {
|
|
196
|
+
const isDropdownOpen = !!document.querySelector('[data-toolbar-component="menu-section"]');
|
|
197
|
+
if (isDropdownOpen) {
|
|
198
|
+
return;
|
|
199
|
+
}
|
|
200
|
+
api === null || api === void 0 ? void 0 : api.core.actions.focus();
|
|
201
|
+
event.preventDefault();
|
|
202
|
+
event.stopPropagation();
|
|
203
|
+
},
|
|
204
|
+
ariaControls: EDIT_AREA_ID,
|
|
205
|
+
ariaLabel: intl.formatMessage(fullPageMessages.toolbarLabel)
|
|
206
|
+
};
|
|
155
207
|
};
|
|
@@ -18,7 +18,8 @@ export const getToolbarComponents = (api, disableSelectionToolbar) => {
|
|
|
18
18
|
}) => {
|
|
19
19
|
return /*#__PURE__*/React.createElement(Toolbar, {
|
|
20
20
|
label: SELECTION_TOOLBAR_LABEL,
|
|
21
|
-
actionSubjectId: ACTION_SUBJECT_ID.SELECTION_TOOLBAR
|
|
21
|
+
actionSubjectId: ACTION_SUBJECT_ID.SELECTION_TOOLBAR,
|
|
22
|
+
testId: expValEquals('platform_editor_toolbar_aifc_patch_5', 'isEnabled', true) ? 'editor-floating-toolbar' : undefined
|
|
22
23
|
}, children);
|
|
23
24
|
}
|
|
24
25
|
}, {
|
|
@@ -4,4 +4,22 @@ export const isEventInContainer = (event, containerSelector) => {
|
|
|
4
4
|
return false;
|
|
5
5
|
}
|
|
6
6
|
return !!target.closest(containerSelector);
|
|
7
|
+
};
|
|
8
|
+
export const isShortcutToFocusToolbar = event => {
|
|
9
|
+
return event.altKey && event.key === 'F10';
|
|
10
|
+
};
|
|
11
|
+
export const getFocusableElements = rootNode => {
|
|
12
|
+
if (!rootNode) {
|
|
13
|
+
return [];
|
|
14
|
+
}
|
|
15
|
+
const focusableElements = rootNode.querySelectorAll('a[href], button:not([disabled]), textarea, input, select, div[tabindex="-1"], div[tabindex="0"]') || [];
|
|
16
|
+
const focusableElementsArray = Array.from(focusableElements);
|
|
17
|
+
|
|
18
|
+
// filter out focusable elements from child components such as dropdown menus / popups
|
|
19
|
+
return focusableElementsArray.filter(elm => {
|
|
20
|
+
const style = window.getComputedStyle(elm);
|
|
21
|
+
|
|
22
|
+
// filter out invisible elements
|
|
23
|
+
return style.visibility !== 'hidden' && style.display !== 'none';
|
|
24
|
+
});
|
|
7
25
|
};
|
|
@@ -1,8 +1,11 @@
|
|
|
1
|
-
import React, { useCallback } from 'react';
|
|
1
|
+
import React, { useCallback, useMemo } from 'react';
|
|
2
|
+
import { useIntl } from 'react-intl-next';
|
|
3
|
+
import { getDocument } from '@atlaskit/browser-apis';
|
|
2
4
|
import { isSSR } from '@atlaskit/editor-common/core-utils';
|
|
3
5
|
import { useSharedPluginStateWithSelector } from '@atlaskit/editor-common/hooks';
|
|
6
|
+
import { fullPageMessages } from '@atlaskit/editor-common/messages';
|
|
4
7
|
import { EditorToolbarProvider, EditorToolbarUIProvider } from '@atlaskit/editor-common/toolbar';
|
|
5
|
-
import { Popup } from '@atlaskit/editor-common/ui';
|
|
8
|
+
import { Popup, EDIT_AREA_ID } from '@atlaskit/editor-common/ui';
|
|
6
9
|
import { useSharedPluginStateSelector } from '@atlaskit/editor-common/use-shared-plugin-state-selector';
|
|
7
10
|
import { calculateToolbarPositionTrackHead, calculateToolbarPositionOnCellSelection } from '@atlaskit/editor-common/utils';
|
|
8
11
|
import { AllSelection, TextSelection } from '@atlaskit/editor-prosemirror/state';
|
|
@@ -13,6 +16,7 @@ import { conditionalHooksFactory } from '@atlaskit/platform-feature-flags-react'
|
|
|
13
16
|
import { expValEquals } from '@atlaskit/tmp-editor-statsig/exp-val-equals';
|
|
14
17
|
import { expValEqualsNoExposure } from '@atlaskit/tmp-editor-statsig/exp-val-equals-no-exposure';
|
|
15
18
|
import { SELECTION_TOOLBAR_LABEL } from '../consts';
|
|
19
|
+
import { getFocusableElements, isShortcutToFocusToolbar } from '../utils/toolbar';
|
|
16
20
|
var isToolbarComponent = function isToolbarComponent(component) {
|
|
17
21
|
return component.type === 'toolbar' && component.key === 'inline-text-toolbar';
|
|
18
22
|
};
|
|
@@ -68,10 +72,14 @@ export var SelectionToolbar = function SelectionToolbar(_ref) {
|
|
|
68
72
|
shouldShowToolbar = _usePluginState.shouldShowToolbar,
|
|
69
73
|
editorViewMode = _usePluginState.editorViewMode,
|
|
70
74
|
selection = _usePluginState.selection;
|
|
75
|
+
var intl = useIntl();
|
|
71
76
|
var components = api === null || api === void 0 || (_api$toolbar = api.toolbar) === null || _api$toolbar === void 0 ? void 0 : _api$toolbar.actions.getComponents();
|
|
72
77
|
var toolbar = components === null || components === void 0 ? void 0 : components.find(function (component) {
|
|
73
78
|
return isToolbarComponent(component);
|
|
74
79
|
});
|
|
80
|
+
var keyboardNavigation = useMemo(function () {
|
|
81
|
+
return getKeyboardNavigationConfig(editorView, intl, api);
|
|
82
|
+
}, [editorView, intl, api]);
|
|
75
83
|
var isOffline = connectivityStateMode === 'offline';
|
|
76
84
|
var isTextSelection = !editorView.state.selection.empty && editorView.state.selection instanceof TextSelection;
|
|
77
85
|
var isAllSelection = !editorView.state.selection.empty && editorView.state.selection instanceof AllSelection && expValEquals('platform_editor_toolbar_aifc_patch_2', 'isEnabled', true);
|
|
@@ -110,7 +118,8 @@ export var SelectionToolbar = function SelectionToolbar(_ref) {
|
|
|
110
118
|
fireAnalyticsEvent: expValEquals('platform_editor_toolbar_aifc_toolbar_analytic', 'isEnabled', true) ? function (payload) {
|
|
111
119
|
var _api$analytics;
|
|
112
120
|
api === null || api === void 0 || (_api$analytics = api.analytics) === null || _api$analytics === void 0 || _api$analytics.actions.fireAnalyticsEvent(payload);
|
|
113
|
-
} : undefined
|
|
121
|
+
} : undefined,
|
|
122
|
+
keyboardNavigation: expValEquals('platform_editor_toolbar_aifc_patch_5', 'isEnabled', true) ? keyboardNavigation : undefined
|
|
114
123
|
}, /*#__PURE__*/React.createElement(ToolbarModelRenderer, {
|
|
115
124
|
toolbar: toolbar,
|
|
116
125
|
components: components,
|
|
@@ -152,4 +161,47 @@ var getDomRefFromSelection = function getDomRefFromSelection(view
|
|
|
152
161
|
// dispatchAnalyticsEvent(payload);
|
|
153
162
|
// }
|
|
154
163
|
}
|
|
164
|
+
};
|
|
165
|
+
var getKeyboardNavigationConfig = function getKeyboardNavigationConfig(editorView, intl, api) {
|
|
166
|
+
if (!(editorView.dom instanceof HTMLElement)) {
|
|
167
|
+
return;
|
|
168
|
+
}
|
|
169
|
+
var toolbarSelector = "[data-testid='editor-floating-toolbar']";
|
|
170
|
+
return {
|
|
171
|
+
childComponentSelector: toolbarSelector,
|
|
172
|
+
dom: editorView.dom,
|
|
173
|
+
isShortcutToFocusToolbar: isShortcutToFocusToolbar,
|
|
174
|
+
handleFocus: function handleFocus(event) {
|
|
175
|
+
var _getDocument, _filteredFocusableEle, _filteredFocusableEle2, _filteredFocusableEle3;
|
|
176
|
+
var toolbar = (_getDocument = getDocument()) === null || _getDocument === void 0 ? void 0 : _getDocument.querySelector(toolbarSelector);
|
|
177
|
+
if (!(toolbar instanceof HTMLElement)) {
|
|
178
|
+
return;
|
|
179
|
+
}
|
|
180
|
+
var filteredFocusableElements = getFocusableElements(toolbar);
|
|
181
|
+
(_filteredFocusableEle = filteredFocusableElements[0]) === null || _filteredFocusableEle === void 0 || _filteredFocusableEle.focus();
|
|
182
|
+
|
|
183
|
+
// the button element removes the focus ring so this class adds it back
|
|
184
|
+
if (((_filteredFocusableEle2 = filteredFocusableElements[0]) === null || _filteredFocusableEle2 === void 0 ? void 0 : _filteredFocusableEle2.tagName) === 'BUTTON') {
|
|
185
|
+
filteredFocusableElements[0].classList.add('first-floating-toolbar-button');
|
|
186
|
+
}
|
|
187
|
+
(_filteredFocusableEle3 = filteredFocusableElements[0]) === null || _filteredFocusableEle3 === void 0 || _filteredFocusableEle3.scrollIntoView({
|
|
188
|
+
behavior: 'smooth',
|
|
189
|
+
block: 'center',
|
|
190
|
+
inline: 'nearest'
|
|
191
|
+
});
|
|
192
|
+
event.preventDefault();
|
|
193
|
+
event.stopPropagation();
|
|
194
|
+
},
|
|
195
|
+
handleEscape: function handleEscape(event) {
|
|
196
|
+
var isDropdownOpen = !!document.querySelector('[data-toolbar-component="menu-section"]');
|
|
197
|
+
if (isDropdownOpen) {
|
|
198
|
+
return;
|
|
199
|
+
}
|
|
200
|
+
api === null || api === void 0 || api.core.actions.focus();
|
|
201
|
+
event.preventDefault();
|
|
202
|
+
event.stopPropagation();
|
|
203
|
+
},
|
|
204
|
+
ariaControls: EDIT_AREA_ID,
|
|
205
|
+
ariaLabel: intl.formatMessage(fullPageMessages.toolbarLabel)
|
|
206
|
+
};
|
|
155
207
|
};
|
|
@@ -18,7 +18,8 @@ export var getToolbarComponents = function getToolbarComponents(api, disableSele
|
|
|
18
18
|
var children = _ref.children;
|
|
19
19
|
return /*#__PURE__*/React.createElement(Toolbar, {
|
|
20
20
|
label: SELECTION_TOOLBAR_LABEL,
|
|
21
|
-
actionSubjectId: ACTION_SUBJECT_ID.SELECTION_TOOLBAR
|
|
21
|
+
actionSubjectId: ACTION_SUBJECT_ID.SELECTION_TOOLBAR,
|
|
22
|
+
testId: expValEquals('platform_editor_toolbar_aifc_patch_5', 'isEnabled', true) ? 'editor-floating-toolbar' : undefined
|
|
22
23
|
}, children);
|
|
23
24
|
}
|
|
24
25
|
}, {
|
|
@@ -4,4 +4,22 @@ export var isEventInContainer = function isEventInContainer(event, containerSele
|
|
|
4
4
|
return false;
|
|
5
5
|
}
|
|
6
6
|
return !!target.closest(containerSelector);
|
|
7
|
+
};
|
|
8
|
+
export var isShortcutToFocusToolbar = function isShortcutToFocusToolbar(event) {
|
|
9
|
+
return event.altKey && event.key === 'F10';
|
|
10
|
+
};
|
|
11
|
+
export var getFocusableElements = function getFocusableElements(rootNode) {
|
|
12
|
+
if (!rootNode) {
|
|
13
|
+
return [];
|
|
14
|
+
}
|
|
15
|
+
var focusableElements = rootNode.querySelectorAll('a[href], button:not([disabled]), textarea, input, select, div[tabindex="-1"], div[tabindex="0"]') || [];
|
|
16
|
+
var focusableElementsArray = Array.from(focusableElements);
|
|
17
|
+
|
|
18
|
+
// filter out focusable elements from child components such as dropdown menus / popups
|
|
19
|
+
return focusableElementsArray.filter(function (elm) {
|
|
20
|
+
var style = window.getComputedStyle(elm);
|
|
21
|
+
|
|
22
|
+
// filter out invisible elements
|
|
23
|
+
return style.visibility !== 'hidden' && style.display !== 'none';
|
|
24
|
+
});
|
|
7
25
|
};
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@atlaskit/editor-plugin-toolbar",
|
|
3
|
-
"version": "2.1.
|
|
3
|
+
"version": "2.1.5",
|
|
4
4
|
"description": "Toolbar plugin for @atlaskit/editor-core",
|
|
5
5
|
"author": "Atlassian Pty Ltd",
|
|
6
6
|
"license": "Apache-2.0",
|
|
@@ -28,6 +28,7 @@
|
|
|
28
28
|
"sideEffects": false,
|
|
29
29
|
"atlaskit:src": "src/index.ts",
|
|
30
30
|
"dependencies": {
|
|
31
|
+
"@atlaskit/browser-apis": "^0.0.1",
|
|
31
32
|
"@atlaskit/editor-plugin-analytics": "^5.2.0",
|
|
32
33
|
"@atlaskit/editor-plugin-connectivity": "^5.0.0",
|
|
33
34
|
"@atlaskit/editor-plugin-editor-viewmode": "^7.0.0",
|
|
@@ -38,13 +39,13 @@
|
|
|
38
39
|
"@atlaskit/editor-toolbar": "^0.9.0",
|
|
39
40
|
"@atlaskit/editor-toolbar-model": "^0.2.0",
|
|
40
41
|
"@atlaskit/platform-feature-flags-react": "^0.3.0",
|
|
41
|
-
"@atlaskit/tmp-editor-statsig": "^12.
|
|
42
|
+
"@atlaskit/tmp-editor-statsig": "^12.28.0",
|
|
42
43
|
"@babel/runtime": "^7.0.0",
|
|
43
44
|
"bind-event-listener": "^3.0.0",
|
|
44
45
|
"react-intl-next": "npm:react-intl@^5.18.1"
|
|
45
46
|
},
|
|
46
47
|
"peerDependencies": {
|
|
47
|
-
"@atlaskit/editor-common": "^109.
|
|
48
|
+
"@atlaskit/editor-common": "^109.12.0",
|
|
48
49
|
"react": "^18.2.0"
|
|
49
50
|
},
|
|
50
51
|
"techstack": {
|