@ckeditor/ckeditor5-typing 44.3.0 → 45.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/LICENSE.md +1 -1
- package/dist/index.js +85 -50
- package/dist/index.js.map +1 -1
- package/package.json +5 -5
- package/src/delete.js +4 -0
- package/src/deletecommand.js +15 -4
- package/src/input.js +72 -46
- package/src/inserttextcommand.js +4 -0
- package/src/inserttextobserver.js +11 -3
- package/src/texttransformation.js +1 -1
- package/src/textwatcher.js +18 -0
- package/src/twostepcaretmovement.d.ts +7 -4
- package/src/twostepcaretmovement.js +36 -15
- package/src/utils/changebuffer.js +29 -4
package/LICENSE.md
CHANGED
|
@@ -18,7 +18,7 @@ Where not otherwise indicated, all CKEditor content is authored by CKSource engi
|
|
|
18
18
|
|
|
19
19
|
The following libraries are included in CKEditor under the [MIT license](https://opensource.org/licenses/MIT):
|
|
20
20
|
|
|
21
|
-
*
|
|
21
|
+
* es-toolkit - Copyright (c) 2024 Viva Republica, Inc.
|
|
22
22
|
|
|
23
23
|
Trademarks
|
|
24
24
|
----------
|
package/dist/index.js
CHANGED
|
@@ -5,7 +5,7 @@
|
|
|
5
5
|
import { Command, Plugin } from '@ckeditor/ckeditor5-core/dist/index.js';
|
|
6
6
|
import { env, EventInfo, count, isInsideSurrogatePair, isInsideCombinedSymbol, isInsideEmojiSequence, keyCodes, ObservableMixin } from '@ckeditor/ckeditor5-utils/dist/index.js';
|
|
7
7
|
import { Observer, FocusObserver, DomEventData, LiveRange, BubblingEventInfo, MouseObserver, TouchObserver } from '@ckeditor/ckeditor5-engine/dist/index.js';
|
|
8
|
-
import { debounce, escapeRegExp } from '
|
|
8
|
+
import { debounce, escapeRegExp } from 'es-toolkit/compat';
|
|
9
9
|
|
|
10
10
|
/**
|
|
11
11
|
* @license Copyright (c) 2003-2025, CKSource Holding sp. z o.o. All rights reserved.
|
|
@@ -213,6 +213,7 @@ import { debounce, escapeRegExp } from 'lodash-es';
|
|
|
213
213
|
}
|
|
214
214
|
}
|
|
215
215
|
|
|
216
|
+
// @if CK_DEBUG_TYPING // const { _buildLogMessage } = require( '@ckeditor/ckeditor5-engine/src/dev-utils/utils.js' );
|
|
216
217
|
const TYPING_INPUT_TYPES = [
|
|
217
218
|
// For collapsed range:
|
|
218
219
|
// - This one is a regular typing (all browsers, all systems).
|
|
@@ -284,9 +285,11 @@ const TYPING_INPUT_TYPES_ANDROID = [
|
|
|
284
285
|
return;
|
|
285
286
|
}
|
|
286
287
|
// @if CK_DEBUG_TYPING // if ( ( window as any ).logCKETyping ) {
|
|
287
|
-
// @if CK_DEBUG_TYPING // console.log(
|
|
288
|
-
// @if CK_DEBUG_TYPING //
|
|
289
|
-
// @if CK_DEBUG_TYPING //
|
|
288
|
+
// @if CK_DEBUG_TYPING // console.log( ..._buildLogMessage( this, 'InsertTextObserver',
|
|
289
|
+
// @if CK_DEBUG_TYPING // `%cFire insertText event, %c${ JSON.stringify( data ) }`,
|
|
290
|
+
// @if CK_DEBUG_TYPING // 'font-weight: bold',
|
|
291
|
+
// @if CK_DEBUG_TYPING // 'color: blue'
|
|
292
|
+
// @if CK_DEBUG_TYPING // ) );
|
|
290
293
|
// @if CK_DEBUG_TYPING // }
|
|
291
294
|
// How do we know where to insert the composed text?
|
|
292
295
|
// 1. The SelectionObserver is blocked and the view is not updated with the composition changes.
|
|
@@ -309,6 +312,7 @@ const TYPING_INPUT_TYPES_ANDROID = [
|
|
|
309
312
|
*/ stopObserving() {}
|
|
310
313
|
}
|
|
311
314
|
|
|
315
|
+
// @if CK_DEBUG_TYPING // const { _debouncedLine, _buildLogMessage } = require( '@ckeditor/ckeditor5-engine/src/dev-utils/utils.js' );
|
|
312
316
|
/**
|
|
313
317
|
* Handles text input coming from the keyboard or other input methods.
|
|
314
318
|
*/ class Input extends Plugin {
|
|
@@ -382,9 +386,10 @@ const TYPING_INPUT_TYPES_ANDROID = [
|
|
|
382
386
|
}
|
|
383
387
|
if (insertText.length == 0 && modelRanges[0].isCollapsed) {
|
|
384
388
|
// @if CK_DEBUG_TYPING // if ( ( window as any ).logCKETyping ) {
|
|
385
|
-
// @if CK_DEBUG_TYPING // console.log(
|
|
386
|
-
// @if CK_DEBUG_TYPING // '
|
|
387
|
-
// @if CK_DEBUG_TYPING //
|
|
389
|
+
// @if CK_DEBUG_TYPING // console.log( ..._buildLogMessage( this, 'Input',
|
|
390
|
+
// @if CK_DEBUG_TYPING // '%cIgnore insertion of an empty data to the collapsed range.',
|
|
391
|
+
// @if CK_DEBUG_TYPING // 'font-style: italic'
|
|
392
|
+
// @if CK_DEBUG_TYPING // ) );
|
|
388
393
|
// @if CK_DEBUG_TYPING // }
|
|
389
394
|
return;
|
|
390
395
|
}
|
|
@@ -399,21 +404,27 @@ const TYPING_INPUT_TYPES_ANDROID = [
|
|
|
399
404
|
// We just wait for mutation observer to notice changes or as a fallback a timeout.
|
|
400
405
|
if (env.isAndroid && view.document.isComposing) {
|
|
401
406
|
// @if CK_DEBUG_TYPING // if ( ( window as any ).logCKETyping ) {
|
|
402
|
-
// @if CK_DEBUG_TYPING // console.log(
|
|
407
|
+
// @if CK_DEBUG_TYPING // console.log( ..._buildLogMessage( this, 'Input',
|
|
408
|
+
// @if CK_DEBUG_TYPING // `%cQueue insertText:%c "${ commandData.text }"%c ` +
|
|
403
409
|
// @if CK_DEBUG_TYPING // `[${ commandData.selection.getFirstPosition().path }]-` +
|
|
404
410
|
// @if CK_DEBUG_TYPING // `[${ commandData.selection.getLastPosition().path }]` +
|
|
405
411
|
// @if CK_DEBUG_TYPING // ` queue size: ${ this._compositionQueue.length + 1 }`,
|
|
406
|
-
// @if CK_DEBUG_TYPING // 'font-weight: bold
|
|
407
|
-
// @if CK_DEBUG_TYPING //
|
|
412
|
+
// @if CK_DEBUG_TYPING // 'font-weight: bold',
|
|
413
|
+
// @if CK_DEBUG_TYPING // 'color: blue',
|
|
414
|
+
// @if CK_DEBUG_TYPING // ''
|
|
415
|
+
// @if CK_DEBUG_TYPING // ) );
|
|
408
416
|
// @if CK_DEBUG_TYPING // }
|
|
409
417
|
this._compositionQueue.push(commandData);
|
|
410
418
|
} else {
|
|
411
419
|
// @if CK_DEBUG_TYPING // if ( ( window as any ).logCKETyping ) {
|
|
412
|
-
// @if CK_DEBUG_TYPING // console.log(
|
|
420
|
+
// @if CK_DEBUG_TYPING // console.log( ..._buildLogMessage( this, 'Input',
|
|
421
|
+
// @if CK_DEBUG_TYPING // `%cExecute insertText:%c "${ commandData.text }"%c ` +
|
|
413
422
|
// @if CK_DEBUG_TYPING // `[${ commandData.selection.getFirstPosition().path }]-` +
|
|
414
423
|
// @if CK_DEBUG_TYPING // `[${ commandData.selection.getLastPosition().path }]`,
|
|
415
|
-
// @if CK_DEBUG_TYPING // 'font-weight: bold
|
|
416
|
-
// @if CK_DEBUG_TYPING //
|
|
424
|
+
// @if CK_DEBUG_TYPING // 'font-weight: bold',
|
|
425
|
+
// @if CK_DEBUG_TYPING // 'color: blue',
|
|
426
|
+
// @if CK_DEBUG_TYPING // ''
|
|
427
|
+
// @if CK_DEBUG_TYPING // ) );
|
|
417
428
|
// @if CK_DEBUG_TYPING // }
|
|
418
429
|
editor.execute('insertText', commandData);
|
|
419
430
|
view.scrollToTheSelection();
|
|
@@ -431,10 +442,12 @@ const TYPING_INPUT_TYPES_ANDROID = [
|
|
|
431
442
|
// @if CK_DEBUG_TYPING // if ( ( window as any ).logCKETyping ) {
|
|
432
443
|
// @if CK_DEBUG_TYPING // const firstPositionPath = modelSelection.getFirstPosition()!.path;
|
|
433
444
|
// @if CK_DEBUG_TYPING // const lastPositionPath = modelSelection.getLastPosition()!.path;
|
|
434
|
-
// @if CK_DEBUG_TYPING // console.log(
|
|
445
|
+
// @if CK_DEBUG_TYPING // console.log( ..._buildLogMessage( this, 'Input',
|
|
446
|
+
// @if CK_DEBUG_TYPING // '%cKeyDown 229%c -> model.deleteContent() ' +
|
|
435
447
|
// @if CK_DEBUG_TYPING // `[${ firstPositionPath }]-[${ lastPositionPath }]`,
|
|
436
|
-
// @if CK_DEBUG_TYPING // 'font-weight: bold
|
|
437
|
-
// @if CK_DEBUG_TYPING //
|
|
448
|
+
// @if CK_DEBUG_TYPING // 'font-weight: bold',
|
|
449
|
+
// @if CK_DEBUG_TYPING // ''
|
|
450
|
+
// @if CK_DEBUG_TYPING // ) );
|
|
438
451
|
// @if CK_DEBUG_TYPING // }
|
|
439
452
|
deleteSelectionContent(model, insertTextCommand);
|
|
440
453
|
});
|
|
@@ -448,10 +461,12 @@ const TYPING_INPUT_TYPES_ANDROID = [
|
|
|
448
461
|
// @if CK_DEBUG_TYPING // if ( ( window as any ).logCKETyping ) {
|
|
449
462
|
// @if CK_DEBUG_TYPING // const firstPositionPath = modelSelection.getFirstPosition()!.path;
|
|
450
463
|
// @if CK_DEBUG_TYPING // const lastPositionPath = modelSelection.getLastPosition()!.path;
|
|
451
|
-
// @if CK_DEBUG_TYPING // console.log(
|
|
464
|
+
// @if CK_DEBUG_TYPING // console.log( ..._buildLogMessage( this, 'Input',
|
|
465
|
+
// @if CK_DEBUG_TYPING // '%cComposition start%c -> model.deleteContent() ' +
|
|
452
466
|
// @if CK_DEBUG_TYPING // `[${ firstPositionPath }]-[${ lastPositionPath }]`,
|
|
453
|
-
// @if CK_DEBUG_TYPING // 'font-weight: bold
|
|
454
|
-
// @if CK_DEBUG_TYPING //
|
|
467
|
+
// @if CK_DEBUG_TYPING // 'font-weight: bold',
|
|
468
|
+
// @if CK_DEBUG_TYPING // '',
|
|
469
|
+
// @if CK_DEBUG_TYPING // ) );
|
|
455
470
|
// @if CK_DEBUG_TYPING // }
|
|
456
471
|
deleteSelectionContent(model, insertTextCommand);
|
|
457
472
|
});
|
|
@@ -474,9 +489,10 @@ const TYPING_INPUT_TYPES_ANDROID = [
|
|
|
474
489
|
}
|
|
475
490
|
}
|
|
476
491
|
// @if CK_DEBUG_TYPING // if ( ( window as any ).logCKETyping ) {
|
|
477
|
-
// @if CK_DEBUG_TYPING // console.log(
|
|
478
|
-
// @if CK_DEBUG_TYPING // '
|
|
479
|
-
// @if CK_DEBUG_TYPING //
|
|
492
|
+
// @if CK_DEBUG_TYPING // console.log( ..._buildLogMessage( this, 'Input',
|
|
493
|
+
// @if CK_DEBUG_TYPING // '%cMutations not related to the composition.',
|
|
494
|
+
// @if CK_DEBUG_TYPING // 'font-style: italic'
|
|
495
|
+
// @if CK_DEBUG_TYPING // ) );
|
|
480
496
|
// @if CK_DEBUG_TYPING // }
|
|
481
497
|
});
|
|
482
498
|
// Make sure that all changes are applied to the model before the end of composition.
|
|
@@ -502,9 +518,10 @@ const TYPING_INPUT_TYPES_ANDROID = [
|
|
|
502
518
|
}
|
|
503
519
|
if (mutations.length) {
|
|
504
520
|
// @if CK_DEBUG_TYPING // if ( ( window as any ).logCKETyping ) {
|
|
505
|
-
// @if CK_DEBUG_TYPING // console.group(
|
|
506
|
-
// @if CK_DEBUG_TYPING // '
|
|
507
|
-
// @if CK_DEBUG_TYPING //
|
|
521
|
+
// @if CK_DEBUG_TYPING // console.group( ..._buildLogMessage( this, 'Input',
|
|
522
|
+
// @if CK_DEBUG_TYPING // '%cFire post-composition mutation fixes.',
|
|
523
|
+
// @if CK_DEBUG_TYPING // 'font-weight: bold'
|
|
524
|
+
// @if CK_DEBUG_TYPING // ) );
|
|
508
525
|
// @if CK_DEBUG_TYPING // }
|
|
509
526
|
view.document.fire('mutations', {
|
|
510
527
|
mutations
|
|
@@ -530,9 +547,10 @@ const TYPING_INPUT_TYPES_ANDROID = [
|
|
|
530
547
|
// This is especially needed when user cancels composition, so we can clear nodes marked to sync.
|
|
531
548
|
this.listenTo(view.document, 'compositionend', ()=>{
|
|
532
549
|
// @if CK_DEBUG_TYPING // if ( ( window as any ).logCKETyping ) {
|
|
533
|
-
// @if CK_DEBUG_TYPING // console.group(
|
|
534
|
-
// @if CK_DEBUG_TYPING // '
|
|
535
|
-
// @if CK_DEBUG_TYPING //
|
|
550
|
+
// @if CK_DEBUG_TYPING // console.group( ..._buildLogMessage( this, 'Input',
|
|
551
|
+
// @if CK_DEBUG_TYPING // '%cForce render after composition end.',
|
|
552
|
+
// @if CK_DEBUG_TYPING // 'font-weight: bold'
|
|
553
|
+
// @if CK_DEBUG_TYPING // ) );
|
|
536
554
|
// @if CK_DEBUG_TYPING // }
|
|
537
555
|
view.document.fire('mutations', {
|
|
538
556
|
mutations: []
|
|
@@ -631,9 +649,10 @@ const TYPING_INPUT_TYPES_ANDROID = [
|
|
|
631
649
|
return;
|
|
632
650
|
}
|
|
633
651
|
// @if CK_DEBUG_TYPING // if ( ( window as any ).logCKETyping ) {
|
|
634
|
-
// @if CK_DEBUG_TYPING // console.group(
|
|
635
|
-
// @if CK_DEBUG_TYPING //
|
|
636
|
-
// @if CK_DEBUG_TYPING //
|
|
652
|
+
// @if CK_DEBUG_TYPING // console.group( ..._buildLogMessage( this, 'Input',
|
|
653
|
+
// @if CK_DEBUG_TYPING // `%cFlush insertText queue on ${ reason }.`,
|
|
654
|
+
// @if CK_DEBUG_TYPING // 'font-weight: bold'
|
|
655
|
+
// @if CK_DEBUG_TYPING // ) );
|
|
637
656
|
// @if CK_DEBUG_TYPING // }
|
|
638
657
|
const insertTextCommand = editor.commands.get('insertText');
|
|
639
658
|
const buffer = insertTextCommand.buffer;
|
|
@@ -642,12 +661,14 @@ const TYPING_INPUT_TYPES_ANDROID = [
|
|
|
642
661
|
while(this._queue.length){
|
|
643
662
|
const commandData = this.shift();
|
|
644
663
|
// @if CK_DEBUG_TYPING // if ( ( window as any ).logCKETyping ) {
|
|
645
|
-
// @if CK_DEBUG_TYPING // console.log(
|
|
646
|
-
// @if CK_DEBUG_TYPING //
|
|
647
|
-
// @if CK_DEBUG_TYPING //
|
|
648
|
-
// @if CK_DEBUG_TYPING //
|
|
649
|
-
// @if CK_DEBUG_TYPING // 'font-weight: bold
|
|
650
|
-
// @if CK_DEBUG_TYPING //
|
|
664
|
+
// @if CK_DEBUG_TYPING // console.log( ..._buildLogMessage( this, 'Input',
|
|
665
|
+
// @if CK_DEBUG_TYPING // `%cExecute queued insertText:%c "${ commandData.text }"%c ` +
|
|
666
|
+
// @if CK_DEBUG_TYPING // `[${ commandData.selection.getFirstPosition().path }]-` +
|
|
667
|
+
// @if CK_DEBUG_TYPING // `[${ commandData.selection.getLastPosition().path }]`,
|
|
668
|
+
// @if CK_DEBUG_TYPING // 'font-weight: bold',
|
|
669
|
+
// @if CK_DEBUG_TYPING // 'color: blue',
|
|
670
|
+
// @if CK_DEBUG_TYPING // ''
|
|
671
|
+
// @if CK_DEBUG_TYPING // ) );
|
|
651
672
|
// @if CK_DEBUG_TYPING // }
|
|
652
673
|
editor.execute('insertText', commandData);
|
|
653
674
|
}
|
|
@@ -709,6 +730,7 @@ const TYPING_INPUT_TYPES_ANDROID = [
|
|
|
709
730
|
return node;
|
|
710
731
|
}
|
|
711
732
|
|
|
733
|
+
// @if CK_DEBUG_TYPING // const { _buildLogMessage } = require( '@ckeditor/ckeditor5-engine/src/dev-utils/utils.js' );
|
|
712
734
|
/**
|
|
713
735
|
* The delete command. Used by the {@link module:typing/delete~Delete delete feature} to handle the <kbd>Delete</kbd> and
|
|
714
736
|
* <kbd>Backspace</kbd> keys.
|
|
@@ -798,10 +820,11 @@ const TYPING_INPUT_TYPES_ANDROID = [
|
|
|
798
820
|
}));
|
|
799
821
|
});
|
|
800
822
|
// @if CK_DEBUG_TYPING // if ( ( window as any ).logCKETyping ) {
|
|
801
|
-
// @if CK_DEBUG_TYPING // console.log(
|
|
802
|
-
// @if CK_DEBUG_TYPING // '
|
|
803
|
-
// @if CK_DEBUG_TYPING // `[${ selection.getFirstPosition()!.path }]-[${ selection.getLastPosition()!.path }]`,
|
|
804
|
-
// @if CK_DEBUG_TYPING //
|
|
823
|
+
// @if CK_DEBUG_TYPING // console.log( ..._buildLogMessage( this, 'DeleteCommand',
|
|
824
|
+
// @if CK_DEBUG_TYPING // 'Delete content',
|
|
825
|
+
// @if CK_DEBUG_TYPING // `[${ selection.getFirstPosition()!.path }]-[${ selection.getLastPosition()!.path }]`,
|
|
826
|
+
// @if CK_DEBUG_TYPING // options
|
|
827
|
+
// @if CK_DEBUG_TYPING // ) );
|
|
805
828
|
// @if CK_DEBUG_TYPING // }
|
|
806
829
|
model.deleteContent(selection, {
|
|
807
830
|
doNotResetEntireContent,
|
|
@@ -1656,9 +1679,10 @@ const DELETE_EVENT_TYPES = {
|
|
|
1656
1679
|
* Updates the document selection and the view according to the two–step caret movement state
|
|
1657
1680
|
* when moving **forwards**. Executed upon `keypress` in the {@link module:engine/view/view~View}.
|
|
1658
1681
|
*
|
|
1659
|
-
* @
|
|
1682
|
+
* @internal
|
|
1683
|
+
* @param eventData Data of the key press.
|
|
1660
1684
|
* @returns `true` when the handler prevented caret movement.
|
|
1661
|
-
*/ _handleForwardMovement(
|
|
1685
|
+
*/ _handleForwardMovement(eventData) {
|
|
1662
1686
|
const attributes = this.attributes;
|
|
1663
1687
|
const model = this.editor.model;
|
|
1664
1688
|
const selection = model.document.selection;
|
|
@@ -1693,7 +1717,9 @@ const DELETE_EVENT_TYPES = {
|
|
|
1693
1717
|
// <paragraph>foo{}<$text attribute>bar</$text>baz</paragraph>
|
|
1694
1718
|
//
|
|
1695
1719
|
if (isBetweenDifferentAttributes(position, attributes)) {
|
|
1696
|
-
|
|
1720
|
+
if (eventData) {
|
|
1721
|
+
preventCaretMovement(eventData);
|
|
1722
|
+
}
|
|
1697
1723
|
// CLEAR 2-SCM attributes if we are at the end of one 2-SCM and before
|
|
1698
1724
|
// the next one with a different value of the same attribute.
|
|
1699
1725
|
//
|
|
@@ -1712,9 +1738,10 @@ const DELETE_EVENT_TYPES = {
|
|
|
1712
1738
|
* Updates the document selection and the view according to the two–step caret movement state
|
|
1713
1739
|
* when moving **backwards**. Executed upon `keypress` in the {@link module:engine/view/view~View}.
|
|
1714
1740
|
*
|
|
1715
|
-
* @
|
|
1741
|
+
* @internal
|
|
1742
|
+
* @param eventData Data of the key press.
|
|
1716
1743
|
* @returns `true` when the handler prevented caret movement
|
|
1717
|
-
*/ _handleBackwardMovement(
|
|
1744
|
+
*/ _handleBackwardMovement(eventData) {
|
|
1718
1745
|
const attributes = this.attributes;
|
|
1719
1746
|
const model = this.editor.model;
|
|
1720
1747
|
const selection = model.document.selection;
|
|
@@ -1728,7 +1755,9 @@ const DELETE_EVENT_TYPES = {
|
|
|
1728
1755
|
// <paragraph>foo<$text attribute>bar</$text>{}baz</paragraph>
|
|
1729
1756
|
//
|
|
1730
1757
|
if (this._isGravityOverridden) {
|
|
1731
|
-
|
|
1758
|
+
if (eventData) {
|
|
1759
|
+
preventCaretMovement(eventData);
|
|
1760
|
+
}
|
|
1732
1761
|
this._restoreGravity();
|
|
1733
1762
|
// CLEAR 2-SCM attributes if we are at the end of one 2-SCM and before
|
|
1734
1763
|
// the next one with a different value of the same attribute.
|
|
@@ -1749,7 +1778,9 @@ const DELETE_EVENT_TYPES = {
|
|
|
1749
1778
|
//
|
|
1750
1779
|
if (position.isAtStart) {
|
|
1751
1780
|
if (hasAnyAttribute(selection, attributes)) {
|
|
1752
|
-
|
|
1781
|
+
if (eventData) {
|
|
1782
|
+
preventCaretMovement(eventData);
|
|
1783
|
+
}
|
|
1753
1784
|
setSelectionAttributesFromTheNodeBefore(model, attributes, position);
|
|
1754
1785
|
return true;
|
|
1755
1786
|
}
|
|
@@ -1760,7 +1791,9 @@ const DELETE_EVENT_TYPES = {
|
|
|
1760
1791
|
// <paragraph>foo<$text attribute=1>bar</$text>[]<$text attribute=2>bar</$text>baz</paragraph>
|
|
1761
1792
|
//
|
|
1762
1793
|
if (!hasAnyAttribute(selection, attributes) && isBetweenDifferentAttributes(position, attributes, true)) {
|
|
1763
|
-
|
|
1794
|
+
if (eventData) {
|
|
1795
|
+
preventCaretMovement(eventData);
|
|
1796
|
+
}
|
|
1764
1797
|
setSelectionAttributesFromTheNodeBefore(model, attributes, position);
|
|
1765
1798
|
return true;
|
|
1766
1799
|
}
|
|
@@ -1780,7 +1813,9 @@ const DELETE_EVENT_TYPES = {
|
|
|
1780
1813
|
// <paragraph><$text attribute>bar</$text>{}</paragraph>
|
|
1781
1814
|
//
|
|
1782
1815
|
if (position.isAtEnd && !hasAnyAttribute(selection, attributes) && isBetweenDifferentAttributes(position, attributes)) {
|
|
1783
|
-
|
|
1816
|
+
if (eventData) {
|
|
1817
|
+
preventCaretMovement(eventData);
|
|
1818
|
+
}
|
|
1784
1819
|
setSelectionAttributesFromTheNodeBefore(model, attributes, position);
|
|
1785
1820
|
return true;
|
|
1786
1821
|
}
|