@ckeditor/ckeditor5-ui 42.0.2 → 43.0.0-alpha.0
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 +1 -539
- package/dist/button/button.d.ts +0 -6
- package/dist/button/buttonview.d.ts +16 -4
- package/dist/button/filedialogbuttonview.d.ts +42 -15
- package/dist/button/listitembuttonview.d.ts +82 -0
- package/dist/editorui/accessibilityhelp/accessibilityhelp.d.ts +1 -1
- package/dist/editorui/editorui.d.ts +57 -0
- package/dist/editorui/editoruiview.d.ts +5 -0
- package/dist/focuscycler.d.ts +53 -7
- package/dist/formheader/formheaderview.d.ts +1 -2
- package/dist/highlightedtext/buttonlabelwithhighlightview.d.ts +34 -0
- package/dist/highlightedtext/labelwithhighlightview.d.ts +30 -0
- package/dist/index-editor.css +32 -0
- package/dist/index.css +42 -0
- package/dist/index.css.map +1 -1
- package/dist/index.d.ts +6 -2
- package/dist/index.js +4934 -4291
- package/dist/index.js.map +1 -1
- package/dist/menubar/menubarmenubuttonview.d.ts +2 -2
- package/dist/menubar/menubarmenulistitembuttonview.d.ts +2 -2
- package/dist/menubar/menubarmenulistitemfiledialogbuttonview.d.ts +2 -2
- package/dist/menubar/menubarmenulistview.d.ts +5 -0
- package/dist/menubar/menubarview.d.ts +10 -1
- package/dist/menubar/utils.d.ts +16 -10
- package/dist/panel/balloon/balloonpanelview.d.ts +13 -1
- package/dist/search/filtergroupanditemnames.d.ts +19 -0
- package/dist/toolbar/block/blocktoolbar.d.ts +14 -0
- package/dist/tooltipmanager.d.ts +0 -7
- package/dist/translations/sr-latn.js +1 -1
- package/dist/translations/sr-latn.umd.js +1 -1
- package/lang/translations/sr-latn.po +17 -17
- package/package.json +3 -3
- package/src/arialiveannouncer.js +0 -1
- package/src/bindings/draggableviewmixin.js +1 -1
- package/src/button/button.d.ts +0 -6
- package/src/button/buttonview.d.ts +16 -4
- package/src/button/buttonview.js +32 -2
- package/src/button/filedialogbuttonview.d.ts +42 -15
- package/src/button/filedialogbuttonview.js +69 -27
- package/src/button/listitembuttonview.d.ts +78 -0
- package/src/button/listitembuttonview.js +129 -0
- package/src/colorpicker/colorpickerview.js +5 -0
- package/src/colorselector/colorgridsfragmentview.js +9 -5
- package/src/dialog/dialog.js +4 -1
- package/src/dialog/dialogview.js +1 -14
- package/src/dropdown/utils.js +23 -3
- package/src/editorui/accessibilityhelp/accessibilityhelp.d.ts +1 -1
- package/src/editorui/accessibilityhelp/accessibilityhelp.js +20 -12
- package/src/editorui/bodycollection.js +2 -1
- package/src/editorui/editorui.d.ts +57 -0
- package/src/editorui/editorui.js +104 -12
- package/src/editorui/editoruiview.d.ts +5 -0
- package/src/focuscycler.d.ts +53 -7
- package/src/focuscycler.js +79 -1
- package/src/formheader/formheaderview.d.ts +1 -2
- package/src/formheader/formheaderview.js +1 -2
- package/src/highlightedtext/buttonlabelwithhighlightview.d.ts +30 -0
- package/src/highlightedtext/buttonlabelwithhighlightview.js +31 -0
- package/src/highlightedtext/labelwithhighlightview.d.ts +26 -0
- package/src/highlightedtext/labelwithhighlightview.js +33 -0
- package/src/index.d.ts +6 -2
- package/src/index.js +6 -2
- package/src/menubar/menubarmenubuttonview.d.ts +2 -2
- package/src/menubar/menubarmenubuttonview.js +2 -2
- package/src/menubar/menubarmenulistitembuttonview.d.ts +2 -2
- package/src/menubar/menubarmenulistitembuttonview.js +2 -2
- package/src/menubar/menubarmenulistitemfiledialogbuttonview.d.ts +2 -2
- package/src/menubar/menubarmenulistitemfiledialogbuttonview.js +2 -2
- package/src/menubar/menubarmenulistview.d.ts +5 -0
- package/src/menubar/menubarmenulistview.js +49 -0
- package/src/menubar/menubarview.d.ts +10 -1
- package/src/menubar/menubarview.js +11 -4
- package/src/menubar/utils.d.ts +16 -10
- package/src/menubar/utils.js +84 -53
- package/src/panel/balloon/balloonpanelview.d.ts +13 -1
- package/src/panel/balloon/balloonpanelview.js +41 -3
- package/src/search/filtergroupanditemnames.d.ts +15 -0
- package/src/search/filtergroupanditemnames.js +38 -0
- package/src/search/text/searchtextview.js +1 -0
- package/src/toolbar/balloon/balloontoolbar.js +1 -1
- package/src/toolbar/block/blocktoolbar.d.ts +14 -0
- package/src/toolbar/block/blocktoolbar.js +83 -3
- package/src/tooltipmanager.d.ts +0 -7
- package/src/tooltipmanager.js +1 -18
- package/theme/components/button/listitembutton.css +38 -0
|
@@ -0,0 +1,38 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* @license Copyright (c) 2003-2024, CKSource Holding sp. z o.o. All rights reserved.
|
|
3
|
+
* For licensing, see LICENSE.md or https://ckeditor.com/legal/ckeditor-oss-license
|
|
4
|
+
*/
|
|
5
|
+
/**
|
|
6
|
+
* A filter function that returns matching item and group names in the list view.
|
|
7
|
+
*/
|
|
8
|
+
export default function filterGroupAndItemNames(regExp, items) {
|
|
9
|
+
let totalItemsCount = 0;
|
|
10
|
+
let resultsCount = 0;
|
|
11
|
+
for (const groupView of items) {
|
|
12
|
+
const group = groupView;
|
|
13
|
+
const groupItems = group.items;
|
|
14
|
+
const isGroupLabelMatching = regExp && !!group.label.match(regExp);
|
|
15
|
+
group.labelView.highlightText(isGroupLabelMatching ? regExp : null);
|
|
16
|
+
for (const listItemView of groupItems) {
|
|
17
|
+
const buttonView = listItemView.children.first;
|
|
18
|
+
const labelView = buttonView.labelView;
|
|
19
|
+
if (!regExp) {
|
|
20
|
+
listItemView.isVisible = true;
|
|
21
|
+
labelView.highlightText(null);
|
|
22
|
+
}
|
|
23
|
+
else {
|
|
24
|
+
const isItemLabelMatching = !!buttonView.label.match(regExp);
|
|
25
|
+
labelView.highlightText(isItemLabelMatching ? regExp : null);
|
|
26
|
+
listItemView.isVisible = isGroupLabelMatching || isItemLabelMatching;
|
|
27
|
+
}
|
|
28
|
+
}
|
|
29
|
+
const visibleInGroupCount = groupItems.filter(listItemView => listItemView.isVisible).length;
|
|
30
|
+
totalItemsCount += group.items.length;
|
|
31
|
+
resultsCount += isGroupLabelMatching ? group.items.length : visibleInGroupCount;
|
|
32
|
+
group.isVisible = isGroupLabelMatching || !!visibleInGroupCount;
|
|
33
|
+
}
|
|
34
|
+
return {
|
|
35
|
+
resultsCount,
|
|
36
|
+
totalItemsCount
|
|
37
|
+
};
|
|
38
|
+
}
|
|
@@ -162,7 +162,7 @@ export default class BalloonToolbar extends Plugin {
|
|
|
162
162
|
if (selectionContainsOnlyMultipleSelectables(selection, schema)) {
|
|
163
163
|
return;
|
|
164
164
|
}
|
|
165
|
-
//
|
|
165
|
+
// Do not show the toolbar when all components inside are disabled
|
|
166
166
|
// see https://github.com/ckeditor/ckeditor5-ui/issues/269.
|
|
167
167
|
if (Array.from(this.toolbarView.items).every((item) => item.isEnabled !== undefined && !item.isEnabled)) {
|
|
168
168
|
return;
|
|
@@ -133,12 +133,26 @@ export default class BlockToolbar extends Plugin {
|
|
|
133
133
|
* @param focusEditable When `true`, the editable will be focused after hiding the panel.
|
|
134
134
|
*/
|
|
135
135
|
private _hidePanel;
|
|
136
|
+
/**
|
|
137
|
+
* Repositions the button on scroll.
|
|
138
|
+
*/
|
|
139
|
+
private _repositionButtonOnScroll;
|
|
136
140
|
/**
|
|
137
141
|
* Attaches the {@link #buttonView} to the target block of content.
|
|
138
142
|
*
|
|
139
143
|
* @param targetElement Target element.
|
|
140
144
|
*/
|
|
141
145
|
private _attachButtonToElement;
|
|
146
|
+
/**
|
|
147
|
+
* Clips the button element to the viewport of the editable element.
|
|
148
|
+
*
|
|
149
|
+
* * If the button overflows the editable viewport, it is clipped to make it look like it's cut off by the editable scrollable region.
|
|
150
|
+
* * If the button is fully hidden by the top of the editable, it is not clickable but still visible in the DOM.
|
|
151
|
+
*
|
|
152
|
+
* @param buttonView The button view to clip.
|
|
153
|
+
* @param editableElement The editable element whose viewport is used for clipping.
|
|
154
|
+
*/
|
|
155
|
+
private _clipButtonToViewport;
|
|
142
156
|
/**
|
|
143
157
|
* Creates a resize observer that observes selected editable and resizes the toolbar panel accordingly.
|
|
144
158
|
*/
|
|
@@ -7,7 +7,7 @@
|
|
|
7
7
|
*/
|
|
8
8
|
/* global window */
|
|
9
9
|
import { Plugin } from '@ckeditor/ckeditor5-core';
|
|
10
|
-
import { Rect, ResizeObserver, toUnit } from '@ckeditor/ckeditor5-utils';
|
|
10
|
+
import { global, Rect, ResizeObserver, toUnit } from '@ckeditor/ckeditor5-utils';
|
|
11
11
|
import BlockButtonView from './blockbuttonview.js';
|
|
12
12
|
import BalloonPanelView from '../../panel/balloon/balloonpanelview.js';
|
|
13
13
|
import ToolbarView, { NESTED_TOOLBAR_ICONS } from '../toolbarview.js';
|
|
@@ -131,6 +131,8 @@ export default class BlockToolbar extends Plugin {
|
|
|
131
131
|
this._hidePanel();
|
|
132
132
|
}
|
|
133
133
|
});
|
|
134
|
+
// Reposition button on scroll.
|
|
135
|
+
this._repositionButtonOnScroll();
|
|
134
136
|
// Register the toolbar so it becomes available for Alt+F10 and Esc navigation.
|
|
135
137
|
editor.ui.addToolbar(this.toolbarView, {
|
|
136
138
|
beforeFocus: () => this._showPanel(),
|
|
@@ -328,19 +330,52 @@ export default class BlockToolbar extends Plugin {
|
|
|
328
330
|
this.editor.editing.view.focus();
|
|
329
331
|
}
|
|
330
332
|
}
|
|
333
|
+
/**
|
|
334
|
+
* Repositions the button on scroll.
|
|
335
|
+
*/
|
|
336
|
+
_repositionButtonOnScroll() {
|
|
337
|
+
const { buttonView } = this;
|
|
338
|
+
let pendingAnimationFrame = false;
|
|
339
|
+
// Reposition the button on scroll, but do it only once per animation frame to avoid performance issues.
|
|
340
|
+
const repositionOnScroll = () => {
|
|
341
|
+
if (pendingAnimationFrame) {
|
|
342
|
+
return;
|
|
343
|
+
}
|
|
344
|
+
pendingAnimationFrame = true;
|
|
345
|
+
global.window.requestAnimationFrame(() => {
|
|
346
|
+
this._updateButton();
|
|
347
|
+
pendingAnimationFrame = false;
|
|
348
|
+
});
|
|
349
|
+
};
|
|
350
|
+
// Watch scroll event only when the button is visible, it prevents attaching the scroll event listener
|
|
351
|
+
// to the document when the button is not visible.
|
|
352
|
+
buttonView.on('change:isVisible', (evt, name, isVisible) => {
|
|
353
|
+
if (isVisible) {
|
|
354
|
+
buttonView.listenTo(global.document, 'scroll', repositionOnScroll, {
|
|
355
|
+
useCapture: true,
|
|
356
|
+
usePassive: true
|
|
357
|
+
});
|
|
358
|
+
}
|
|
359
|
+
else {
|
|
360
|
+
buttonView.stopListening(global.document, 'scroll', repositionOnScroll);
|
|
361
|
+
}
|
|
362
|
+
});
|
|
363
|
+
}
|
|
331
364
|
/**
|
|
332
365
|
* Attaches the {@link #buttonView} to the target block of content.
|
|
333
366
|
*
|
|
334
367
|
* @param targetElement Target element.
|
|
335
368
|
*/
|
|
336
369
|
_attachButtonToElement(targetElement) {
|
|
370
|
+
const buttonElement = this.buttonView.element;
|
|
371
|
+
const editableElement = this._getSelectedEditableElement();
|
|
337
372
|
const contentStyles = window.getComputedStyle(targetElement);
|
|
338
|
-
const editableRect = new Rect(
|
|
373
|
+
const editableRect = new Rect(editableElement);
|
|
339
374
|
const contentPaddingTop = parseInt(contentStyles.paddingTop, 10);
|
|
340
375
|
// When line height is not an integer then treat it as "normal".
|
|
341
376
|
// MDN says that 'normal' == ~1.2 on desktop browsers.
|
|
342
377
|
const contentLineHeight = parseInt(contentStyles.lineHeight, 10) || parseInt(contentStyles.fontSize, 10) * 1.2;
|
|
343
|
-
const buttonRect = new Rect(
|
|
378
|
+
const buttonRect = new Rect(buttonElement);
|
|
344
379
|
const contentRect = new Rect(targetElement);
|
|
345
380
|
let positionLeft;
|
|
346
381
|
if (this.editor.locale.uiLanguageDirection === 'ltr') {
|
|
@@ -354,6 +389,51 @@ export default class BlockToolbar extends Plugin {
|
|
|
354
389
|
const absoluteButtonRect = buttonRect.toAbsoluteRect();
|
|
355
390
|
this.buttonView.top = absoluteButtonRect.top;
|
|
356
391
|
this.buttonView.left = absoluteButtonRect.left;
|
|
392
|
+
this._clipButtonToViewport(this.buttonView, editableElement);
|
|
393
|
+
}
|
|
394
|
+
/**
|
|
395
|
+
* Clips the button element to the viewport of the editable element.
|
|
396
|
+
*
|
|
397
|
+
* * If the button overflows the editable viewport, it is clipped to make it look like it's cut off by the editable scrollable region.
|
|
398
|
+
* * If the button is fully hidden by the top of the editable, it is not clickable but still visible in the DOM.
|
|
399
|
+
*
|
|
400
|
+
* @param buttonView The button view to clip.
|
|
401
|
+
* @param editableElement The editable element whose viewport is used for clipping.
|
|
402
|
+
*/
|
|
403
|
+
_clipButtonToViewport(buttonView, editableElement) {
|
|
404
|
+
const absoluteButtonRect = new Rect(buttonView.element);
|
|
405
|
+
const scrollViewportRect = new Rect(editableElement).getVisible();
|
|
406
|
+
// Sets polygon clip path for the button element, if there is no argument provided, the clip path is removed.
|
|
407
|
+
const setButtonClipping = (...paths) => {
|
|
408
|
+
buttonView.element.style.clipPath = paths.length ? `polygon(${paths.join(',')})` : '';
|
|
409
|
+
};
|
|
410
|
+
// Hide the button if it's fully hidden by the top of the editable.
|
|
411
|
+
// Note that the button is still visible in the DOM, but it's not clickable. It's because we don't
|
|
412
|
+
// want to hide the button completely, as there are plenty of `isVisible` watchers which toggles
|
|
413
|
+
// the button scroll listeners.
|
|
414
|
+
const markAsHidden = (isHidden) => {
|
|
415
|
+
buttonView.isEnabled = !isHidden;
|
|
416
|
+
buttonView.element.style.pointerEvents = isHidden ? 'none' : '';
|
|
417
|
+
};
|
|
418
|
+
if (scrollViewportRect && scrollViewportRect.bottom < absoluteButtonRect.bottom) {
|
|
419
|
+
// Calculate the delta between the button bottom and the editable bottom, and clip the button
|
|
420
|
+
// to make it look like it's cut off by the editable scrollable region.
|
|
421
|
+
const delta = Math.min(absoluteButtonRect.height, absoluteButtonRect.bottom - scrollViewportRect.bottom);
|
|
422
|
+
markAsHidden(delta >= absoluteButtonRect.height);
|
|
423
|
+
setButtonClipping('0 0', '100% 0', `100% calc(100% - ${toPx(delta)})`, `0 calc(100% - ${toPx(delta)}`);
|
|
424
|
+
}
|
|
425
|
+
else if (scrollViewportRect && scrollViewportRect.top > absoluteButtonRect.top) {
|
|
426
|
+
// Calculate the delta between the button top and the editable top, and clip the button
|
|
427
|
+
// to make it look like it's cut off by the editable scrollable region.
|
|
428
|
+
const delta = Math.min(absoluteButtonRect.height, scrollViewportRect.top - absoluteButtonRect.top);
|
|
429
|
+
markAsHidden(delta >= absoluteButtonRect.height);
|
|
430
|
+
setButtonClipping(`0 ${toPx(delta)}`, `100% ${toPx(delta)}`, '100% 100%', '0 100%');
|
|
431
|
+
}
|
|
432
|
+
else {
|
|
433
|
+
// Reset the clip path if button is fully visible.
|
|
434
|
+
markAsHidden(false);
|
|
435
|
+
setButtonClipping();
|
|
436
|
+
}
|
|
357
437
|
}
|
|
358
438
|
/**
|
|
359
439
|
* Creates a resize observer that observes selected editable and resizes the toolbar panel accordingly.
|
package/src/tooltipmanager.d.ts
CHANGED
|
@@ -93,13 +93,6 @@ export default class TooltipManager extends /* #__PURE__ */ TooltipManager_base
|
|
|
93
93
|
* Stores the current tooltip position. `null` when there's no tooltip in the UI.
|
|
94
94
|
*/
|
|
95
95
|
private _currentTooltipPosition;
|
|
96
|
-
/**
|
|
97
|
-
* An instance of the resize observer that keeps track on target element visibility,
|
|
98
|
-
* when it hides the tooltip should also disappear.
|
|
99
|
-
*
|
|
100
|
-
* {@link module:core/editor/editorconfig~EditorConfig#balloonToolbar configuration}.
|
|
101
|
-
*/
|
|
102
|
-
private _resizeObserver;
|
|
103
96
|
/**
|
|
104
97
|
* An instance of the mutation observer that keeps track on target element attributes changes.
|
|
105
98
|
*/
|
package/src/tooltipmanager.js
CHANGED
|
@@ -7,7 +7,7 @@
|
|
|
7
7
|
*/
|
|
8
8
|
import View from './view.js';
|
|
9
9
|
import BalloonPanelView from './panel/balloon/balloonpanelview.js';
|
|
10
|
-
import { DomEmitterMixin,
|
|
10
|
+
import { DomEmitterMixin, first, global, isVisible } from '@ckeditor/ckeditor5-utils';
|
|
11
11
|
import { isElement, debounce } from 'lodash-es';
|
|
12
12
|
import '../theme/components/tooltip/tooltip.css';
|
|
13
13
|
const BALLOON_CLASS = 'ck-tooltip';
|
|
@@ -80,13 +80,6 @@ class TooltipManager extends /* #__PURE__ */ DomEmitterMixin() {
|
|
|
80
80
|
* Stores the current tooltip position. `null` when there's no tooltip in the UI.
|
|
81
81
|
*/
|
|
82
82
|
this._currentTooltipPosition = null;
|
|
83
|
-
/**
|
|
84
|
-
* An instance of the resize observer that keeps track on target element visibility,
|
|
85
|
-
* when it hides the tooltip should also disappear.
|
|
86
|
-
*
|
|
87
|
-
* {@link module:core/editor/editorconfig~EditorConfig#balloonToolbar configuration}.
|
|
88
|
-
*/
|
|
89
|
-
this._resizeObserver = null;
|
|
90
83
|
/**
|
|
91
84
|
* An instance of the mutation observer that keeps track on target element attributes changes.
|
|
92
85
|
*/
|
|
@@ -319,13 +312,6 @@ class TooltipManager extends /* #__PURE__ */ DomEmitterMixin() {
|
|
|
319
312
|
target: targetDomElement,
|
|
320
313
|
positions: TooltipManager.getPositioningFunctions(position)
|
|
321
314
|
});
|
|
322
|
-
this._resizeObserver = new ResizeObserver(targetDomElement, () => {
|
|
323
|
-
// The ResizeObserver will call its callback when the target element hides and the tooltip
|
|
324
|
-
// should also disappear (https://github.com/ckeditor/ckeditor5/issues/12492).
|
|
325
|
-
if (!isVisible(targetDomElement)) {
|
|
326
|
-
this._unpinTooltip();
|
|
327
|
-
}
|
|
328
|
-
});
|
|
329
315
|
this._mutationObserver.attach(targetDomElement);
|
|
330
316
|
// Start responding to changes in editor UI or content layout. For instance, when collaborators change content
|
|
331
317
|
// and a contextual toolbar attached to a content starts to move (and so should move the tooltip).
|
|
@@ -349,9 +335,6 @@ class TooltipManager extends /* #__PURE__ */ DomEmitterMixin() {
|
|
|
349
335
|
this._currentElementWithTooltip = null;
|
|
350
336
|
this._currentTooltipPosition = null;
|
|
351
337
|
this.tooltipTextView.text = '';
|
|
352
|
-
if (this._resizeObserver) {
|
|
353
|
-
this._resizeObserver.destroy();
|
|
354
|
-
}
|
|
355
338
|
this._mutationObserver.detach();
|
|
356
339
|
}
|
|
357
340
|
/**
|
|
@@ -0,0 +1,38 @@
|
|
|
1
|
+
/*
|
|
2
|
+
* Copyright (c) 2003-2024, CKSource Holding sp. z o.o. All rights reserved.
|
|
3
|
+
* For licensing, see LICENSE.md or https://ckeditor.com/legal/ckeditor-oss-license
|
|
4
|
+
*/
|
|
5
|
+
|
|
6
|
+
@import "../../mixins/_dir.css";
|
|
7
|
+
|
|
8
|
+
.ck.ck-list-item-button {
|
|
9
|
+
min-height: unset;
|
|
10
|
+
width: 100%;
|
|
11
|
+
border-radius: 0;
|
|
12
|
+
|
|
13
|
+
@mixin ck-dir ltr {
|
|
14
|
+
text-align: left;
|
|
15
|
+
}
|
|
16
|
+
|
|
17
|
+
@mixin ck-dir rtl {
|
|
18
|
+
text-align: right;
|
|
19
|
+
}
|
|
20
|
+
|
|
21
|
+
& .ck-list-item-button__check-holder {
|
|
22
|
+
display: inline-flex;
|
|
23
|
+
width: 1em;
|
|
24
|
+
height: 1em;
|
|
25
|
+
|
|
26
|
+
@mixin ck-dir ltr {
|
|
27
|
+
margin-right: var(--ck-spacing-standard);
|
|
28
|
+
}
|
|
29
|
+
|
|
30
|
+
@mixin ck-dir rtl {
|
|
31
|
+
margin-left: var(--ck-spacing-standard);
|
|
32
|
+
}
|
|
33
|
+
}
|
|
34
|
+
|
|
35
|
+
& .ck-list-item-button__check-icon {
|
|
36
|
+
height: 100%;
|
|
37
|
+
}
|
|
38
|
+
}
|