@ckeditor/ckeditor5-engine 29.2.0 → 32.0.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.
Files changed (118) hide show
  1. package/LICENSE.md +2 -2
  2. package/package.json +25 -23
  3. package/src/controller/datacontroller.js +60 -12
  4. package/src/controller/editingcontroller.js +1 -1
  5. package/src/conversion/conversion.js +1 -1
  6. package/src/conversion/conversionhelpers.js +1 -1
  7. package/src/conversion/downcastdispatcher.js +1 -1
  8. package/src/conversion/downcasthelpers.js +1 -1
  9. package/src/conversion/mapper.js +1 -1
  10. package/src/conversion/modelconsumable.js +1 -1
  11. package/src/conversion/upcastdispatcher.js +1 -1
  12. package/src/conversion/upcasthelpers.js +1 -1
  13. package/src/conversion/viewconsumable.js +1 -1
  14. package/src/dataprocessor/basichtmlwriter.js +1 -1
  15. package/src/dataprocessor/dataprocessor.jsdoc +1 -1
  16. package/src/dataprocessor/htmldataprocessor.js +18 -43
  17. package/src/dataprocessor/htmlwriter.js +1 -1
  18. package/src/dataprocessor/xmldataprocessor.js +13 -17
  19. package/src/dev-utils/model.js +3 -3
  20. package/src/dev-utils/operationreplayer.js +1 -1
  21. package/src/dev-utils/utils.js +1 -1
  22. package/src/dev-utils/view.js +22 -4
  23. package/src/index.js +1 -1
  24. package/src/model/batch.js +77 -10
  25. package/src/model/differ.js +1 -1
  26. package/src/model/document.js +1 -1
  27. package/src/model/documentfragment.js +1 -1
  28. package/src/model/documentselection.js +1 -1
  29. package/src/model/element.js +1 -1
  30. package/src/model/history.js +1 -1
  31. package/src/model/item.jsdoc +1 -1
  32. package/src/model/liveposition.js +1 -1
  33. package/src/model/liverange.js +1 -1
  34. package/src/model/markercollection.js +6 -5
  35. package/src/model/model.js +17 -9
  36. package/src/model/node.js +1 -1
  37. package/src/model/nodelist.js +1 -1
  38. package/src/model/operation/attributeoperation.js +1 -1
  39. package/src/model/operation/detachoperation.js +1 -1
  40. package/src/model/operation/insertoperation.js +1 -1
  41. package/src/model/operation/markeroperation.js +1 -1
  42. package/src/model/operation/mergeoperation.js +1 -1
  43. package/src/model/operation/moveoperation.js +1 -1
  44. package/src/model/operation/nooperation.js +1 -1
  45. package/src/model/operation/operation.js +1 -1
  46. package/src/model/operation/operationfactory.js +1 -1
  47. package/src/model/operation/renameoperation.js +1 -1
  48. package/src/model/operation/rootattributeoperation.js +1 -1
  49. package/src/model/operation/splitoperation.js +1 -1
  50. package/src/model/operation/transform.js +1 -1
  51. package/src/model/operation/utils.js +1 -1
  52. package/src/model/position.js +1 -1
  53. package/src/model/range.js +2 -2
  54. package/src/model/rootelement.js +1 -1
  55. package/src/model/schema.js +1 -1
  56. package/src/model/selection.js +1 -1
  57. package/src/model/text.js +1 -1
  58. package/src/model/textproxy.js +1 -1
  59. package/src/model/treewalker.js +1 -1
  60. package/src/model/utils/autoparagraphing.js +1 -1
  61. package/src/model/utils/deletecontent.js +1 -1
  62. package/src/model/utils/getselectedcontent.js +1 -1
  63. package/src/model/utils/insertcontent.js +1 -1
  64. package/src/model/utils/modifyselection.js +1 -1
  65. package/src/model/utils/selection-post-fixer.js +44 -29
  66. package/src/model/writer.js +1 -1
  67. package/src/view/attributeelement.js +1 -1
  68. package/src/view/containerelement.js +1 -1
  69. package/src/view/document.js +13 -1
  70. package/src/view/documentfragment.js +1 -1
  71. package/src/view/documentselection.js +1 -1
  72. package/src/view/domconverter.js +268 -24
  73. package/src/view/downcastwriter.js +33 -2
  74. package/src/view/editableelement.js +1 -1
  75. package/src/view/element.js +29 -1
  76. package/src/view/elementdefinition.jsdoc +1 -1
  77. package/src/view/emptyelement.js +1 -1
  78. package/src/view/filler.js +1 -1
  79. package/src/view/item.jsdoc +1 -1
  80. package/src/view/matcher.js +22 -17
  81. package/src/view/node.js +1 -1
  82. package/src/view/observer/arrowkeysobserver.js +1 -1
  83. package/src/view/observer/bubblingemittermixin.js +1 -1
  84. package/src/view/observer/bubblingeventinfo.js +1 -1
  85. package/src/view/observer/clickobserver.js +1 -1
  86. package/src/view/observer/compositionobserver.js +1 -1
  87. package/src/view/observer/domeventdata.js +1 -1
  88. package/src/view/observer/domeventobserver.js +1 -1
  89. package/src/view/observer/fakeselectionobserver.js +1 -1
  90. package/src/view/observer/focusobserver.js +1 -1
  91. package/src/view/observer/inputobserver.js +1 -1
  92. package/src/view/observer/keyobserver.js +1 -1
  93. package/src/view/observer/mouseobserver.js +1 -1
  94. package/src/view/observer/mutationobserver.js +1 -1
  95. package/src/view/observer/observer.js +1 -1
  96. package/src/view/observer/selectionobserver.js +49 -2
  97. package/src/view/placeholder.js +1 -1
  98. package/src/view/position.js +1 -1
  99. package/src/view/range.js +1 -1
  100. package/src/view/rawelement.js +4 -3
  101. package/src/view/renderer.js +94 -40
  102. package/src/view/rooteditableelement.js +1 -1
  103. package/src/view/selection.js +1 -1
  104. package/src/view/styles/background.js +1 -1
  105. package/src/view/styles/border.js +1 -1
  106. package/src/view/styles/margin.js +1 -1
  107. package/src/view/styles/padding.js +1 -1
  108. package/src/view/styles/utils.js +6 -1
  109. package/src/view/stylesmap.js +1 -1
  110. package/src/view/text.js +1 -1
  111. package/src/view/textproxy.js +1 -1
  112. package/src/view/treewalker.js +1 -1
  113. package/src/view/uielement.js +6 -3
  114. package/src/view/upcastwriter.js +1 -1
  115. package/src/view/view.js +2 -2
  116. package/theme/placeholder.css +1 -1
  117. package/theme/renderer.css +9 -0
  118. package/CHANGELOG.md +0 -823
package/LICENSE.md CHANGED
@@ -2,7 +2,7 @@ Software License Agreement
2
2
  ==========================
3
3
 
4
4
  **CKEditor 5 editing engine** – https://github.com/ckeditor/ckeditor5-engine <br>
5
- Copyright (c) 2003-2021, [CKSource](http://cksource.com) Frederico Knabben. All rights reserved.
5
+ Copyright (c) 2003-2022, [CKSource](http://cksource.com) Holding sp. z o.o. All rights reserved.
6
6
 
7
7
  Licensed under the terms of [GNU General Public License Version 2 or later](http://www.gnu.org/licenses/gpl.html).
8
8
 
@@ -14,4 +14,4 @@ Where not otherwise indicated, all CKEditor content is authored by CKSource engi
14
14
  Trademarks
15
15
  ----------
16
16
 
17
- **CKEditor** is a trademark of [CKSource](http://cksource.com) Frederico Knabben. All other brand and product names are trademarks, registered trademarks or service marks of their respective holders.
17
+ **CKEditor** is a trademark of [CKSource](http://cksource.com) Holding sp. z o.o. All other brand and product names are trademarks, registered trademarks or service marks of their respective holders.
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@ckeditor/ckeditor5-engine",
3
- "version": "29.2.0",
3
+ "version": "32.0.0",
4
4
  "description": "The editing engine of CKEditor 5 – the best browser-based rich text editor.",
5
5
  "keywords": [
6
6
  "wysiwyg",
@@ -23,33 +23,35 @@
23
23
  ],
24
24
  "main": "src/index.js",
25
25
  "dependencies": {
26
- "@ckeditor/ckeditor5-utils": "^29.2.0",
26
+ "@ckeditor/ckeditor5-utils": "^32.0.0",
27
27
  "lodash-es": "^4.17.15"
28
28
  },
29
29
  "devDependencies": {
30
- "@ckeditor/ckeditor5-basic-styles": "^29.2.0",
31
- "@ckeditor/ckeditor5-block-quote": "^29.2.0",
32
- "@ckeditor/ckeditor5-clipboard": "^29.2.0",
33
- "@ckeditor/ckeditor5-core": "^29.2.0",
34
- "@ckeditor/ckeditor5-editor-classic": "^29.2.0",
35
- "@ckeditor/ckeditor5-enter": "^29.2.0",
36
- "@ckeditor/ckeditor5-essentials": "^29.2.0",
37
- "@ckeditor/ckeditor5-heading": "^29.2.0",
38
- "@ckeditor/ckeditor5-image": "^29.2.0",
39
- "@ckeditor/ckeditor5-link": "^29.2.0",
40
- "@ckeditor/ckeditor5-list": "^29.2.0",
41
- "@ckeditor/ckeditor5-paragraph": "^29.2.0",
42
- "@ckeditor/ckeditor5-table": "^29.2.0",
43
- "@ckeditor/ckeditor5-theme-lark": "^29.2.0",
44
- "@ckeditor/ckeditor5-typing": "^29.2.0",
45
- "@ckeditor/ckeditor5-ui": "^29.2.0",
46
- "@ckeditor/ckeditor5-undo": "^29.2.0",
47
- "@ckeditor/ckeditor5-widget": "^29.2.0",
48
- "webpack": "^4.43.0",
49
- "webpack-cli": "^3.3.11"
30
+ "@ckeditor/ckeditor5-basic-styles": "^32.0.0",
31
+ "@ckeditor/ckeditor5-block-quote": "^32.0.0",
32
+ "@ckeditor/ckeditor5-clipboard": "^32.0.0",
33
+ "@ckeditor/ckeditor5-cloud-services": "^32.0.0",
34
+ "@ckeditor/ckeditor5-core": "^32.0.0",
35
+ "@ckeditor/ckeditor5-editor-classic": "^32.0.0",
36
+ "@ckeditor/ckeditor5-enter": "^32.0.0",
37
+ "@ckeditor/ckeditor5-essentials": "^32.0.0",
38
+ "@ckeditor/ckeditor5-heading": "^32.0.0",
39
+ "@ckeditor/ckeditor5-image": "^32.0.0",
40
+ "@ckeditor/ckeditor5-link": "^32.0.0",
41
+ "@ckeditor/ckeditor5-list": "^32.0.0",
42
+ "@ckeditor/ckeditor5-mention": "^32.0.0",
43
+ "@ckeditor/ckeditor5-paragraph": "^32.0.0",
44
+ "@ckeditor/ckeditor5-table": "^32.0.0",
45
+ "@ckeditor/ckeditor5-theme-lark": "^32.0.0",
46
+ "@ckeditor/ckeditor5-typing": "^32.0.0",
47
+ "@ckeditor/ckeditor5-ui": "^32.0.0",
48
+ "@ckeditor/ckeditor5-undo": "^32.0.0",
49
+ "@ckeditor/ckeditor5-widget": "^32.0.0",
50
+ "webpack": "^5.58.1",
51
+ "webpack-cli": "^4.9.0"
50
52
  },
51
53
  "engines": {
52
- "node": ">=12.0.0",
54
+ "node": ">=14.0.0",
53
55
  "npm": ">=5.7.1"
54
56
  },
55
57
  "author": "CKSource (http://cksource.com/)",
@@ -1,5 +1,5 @@
1
1
  /**
2
- * @license Copyright (c) 2003-2021, CKSource - Frederico Knabben. All rights reserved.
2
+ * @license Copyright (c) 2003-2022, CKSource Holding sp. z o.o. All rights reserved.
3
3
  * For licensing, see LICENSE.md or https://ckeditor.com/legal/ckeditor-oss-license
4
4
  */
5
5
 
@@ -145,6 +145,7 @@ export default class DataController {
145
145
 
146
146
  this.decorate( 'init' );
147
147
  this.decorate( 'set' );
148
+ this.decorate( 'get' );
148
149
 
149
150
  // Fire the `ready` event when the initialization has completed. Such low-level listener gives possibility
150
151
  // to plug into the initialization pipeline without interrupting the initialization flow.
@@ -155,7 +156,7 @@ export default class DataController {
155
156
  // Fix empty roots after DataController is 'ready' (note that init method could be decorated and stopped).
156
157
  // We need to handle this event because initial data could be empty and post-fixer would not get triggered.
157
158
  this.on( 'ready', () => {
158
- this.model.enqueueChange( 'transparent', autoParagraphEmptyRoots );
159
+ this.model.enqueueChange( { isUndoable: false }, autoParagraphEmptyRoots );
159
160
  }, { priority: 'lowest' } );
160
161
  }
161
162
 
@@ -163,6 +164,7 @@ export default class DataController {
163
164
  * Returns the model's data converted by downcast dispatchers attached to {@link #downcastDispatcher} and
164
165
  * formatted by the {@link #processor data processor}.
165
166
  *
167
+ * @fires get
166
168
  * @param {Object} [options] Additional configuration for the retrieved data. `DataController` provides two optional
167
169
  * properties: `rootName` and `trim`. Other properties of this object are specified by various editor features.
168
170
  * @param {String} [options.rootName='main'] Root name.
@@ -321,7 +323,7 @@ export default class DataController {
321
323
  throw new CKEditorError( 'datacontroller-init-non-existent-root', this );
322
324
  }
323
325
 
324
- this.model.enqueueChange( 'transparent', writer => {
326
+ this.model.enqueueChange( { isUndoable: false }, writer => {
325
327
  for ( const rootName of Object.keys( initialData ) ) {
326
328
  const modelRoot = this.model.document.getRoot( rootName );
327
329
  writer.insert( this.parse( initialData[ rootName ], modelRoot ), modelRoot, 0 );
@@ -348,17 +350,18 @@ export default class DataController {
348
350
  *
349
351
  * dataController.set( { main: '<p>Foo</p>', title: '<h1>Bar</h1>' } ); // Sets data on the `main` and `title` roots.
350
352
  *
351
- * To set the data with preserved undo stacks and set the current change to this stack, use the `{ batchType: 'default' }` option.
353
+ * To set the data with preserved undo stack and add the change to the undo stack, set `{ isUndoable: true }` as `batchType` option.
352
354
  *
353
- * dataController.set( '<p>Foo</p>', { batchType: 'default' } ); // Sets data as a new change.
355
+ * dataController.set( '<p>Foo</p>', { batchType: { isUndoable: true } } );
354
356
  *
355
357
  * @fires set
356
358
  * @param {String|Object.<String,String>} data Input data as a string or an object containing `rootName` - `data`
357
359
  * pairs to set data on multiple roots at once.
358
360
  * @param {Object} [options={}] Options for setting data.
359
- * @param {'default'|'transparent'} [options.batchType='default'] The batch type that will be used to create a batch for the changes.
360
- * When set to `default`, the undo and redo stacks will be preserved. Note that when not set, the undo feature (when present) will
361
- * override it to `transparent` and all undo steps will be lost.
361
+ * @param {Object} [options.batchType] The batch type that will be used to create a batch for the changes applied by this method.
362
+ * By default, the batch will be set as {@link module:engine/model/batch~Batch#isUndoable not undoable} and the undo stack will be
363
+ * cleared after the new data is applied (all undo steps will be removed). If batch type `isUndoable` flag will be set to `true`,
364
+ * the undo stack will be preserved.
362
365
  */
363
366
  set( data, options = {} ) {
364
367
  let newData = {};
@@ -384,9 +387,7 @@ export default class DataController {
384
387
  throw new CKEditorError( 'datacontroller-set-non-existent-root', this );
385
388
  }
386
389
 
387
- const batchType = options.batchType || 'default';
388
-
389
- this.model.enqueueChange( batchType, writer => {
390
+ this.model.enqueueChange( options.batchType || {}, writer => {
390
391
  writer.setSelection( null );
391
392
  writer.removeSelectionAttribute( this.model.document.selection.getAttributeKeys() );
392
393
 
@@ -523,6 +524,15 @@ export default class DataController {
523
524
  *
524
525
  * @event set
525
526
  */
527
+
528
+ /**
529
+ * Event fired after the {@link #get get() method} has been run.
530
+ *
531
+ * The `get` event is fired by decorated {@link #get} method.
532
+ * See {@link module:utils/observablemixin~ObservableMixin#decorate} for more information and samples.
533
+ *
534
+ * @event get
535
+ */
526
536
  }
527
537
 
528
538
  mix( DataController, ObservableMixin );
@@ -559,5 +569,43 @@ function _getMarkersRelativeToElement( element ) {
559
569
  }
560
570
  }
561
571
 
562
- return result;
572
+ // Sort the markers in a stable fashion to ensure that the order in which they are
573
+ // added to the model's marker collection does not affect how they are
574
+ // downcast. One particular use case that we are targeting here, is one where
575
+ // two markers are adjacent but not overlapping, such as an insertion/deletion
576
+ // suggestion pair representing the replacement of a range of text. In this
577
+ // case, putting the markers in DOM order causes the first marker's end to be
578
+ // serialized right after the second marker's start, while putting the markers
579
+ // in reverse DOM order causes it to be right before the second marker's
580
+ // start. So, we sort these in a way that ensures non-intersecting ranges are in
581
+ // reverse DOM order, and intersecting ranges are in something approximating
582
+ // reverse DOM order (since reverse DOM order doesn't have a precise meaning
583
+ // when working with intersecting ranges).
584
+ return result.sort( ( [ n1, r1 ], [ n2, r2 ] ) => {
585
+ if ( r1.end.compareWith( r2.start ) !== 'after' ) {
586
+ // m1.end <= m2.start -- m1 is entirely <= m2
587
+ return 1;
588
+ } else if ( r1.start.compareWith( r2.end ) !== 'before' ) {
589
+ // m1.start >= m2.end -- m1 is entirely >= m2
590
+ return -1;
591
+ } else {
592
+ // they overlap, so use their start positions as the primary sort key and
593
+ // end positions as the secondary sort key
594
+ switch ( r1.start.compareWith( r2.start ) ) {
595
+ case 'before':
596
+ return 1;
597
+ case 'after':
598
+ return -1;
599
+ default:
600
+ switch ( r1.end.compareWith( r2.end ) ) {
601
+ case 'before':
602
+ return 1;
603
+ case 'after':
604
+ return -1;
605
+ default:
606
+ return n2.localeCompare( n1 );
607
+ }
608
+ }
609
+ }
610
+ } );
563
611
  }
@@ -1,5 +1,5 @@
1
1
  /**
2
- * @license Copyright (c) 2003-2021, CKSource - Frederico Knabben. All rights reserved.
2
+ * @license Copyright (c) 2003-2022, CKSource Holding sp. z o.o. All rights reserved.
3
3
  * For licensing, see LICENSE.md or https://ckeditor.com/legal/ckeditor-oss-license
4
4
  */
5
5
 
@@ -1,5 +1,5 @@
1
1
  /**
2
- * @license Copyright (c) 2003-2021, CKSource - Frederico Knabben. All rights reserved.
2
+ * @license Copyright (c) 2003-2022, CKSource Holding sp. z o.o. All rights reserved.
3
3
  * For licensing, see LICENSE.md or https://ckeditor.com/legal/ckeditor-oss-license
4
4
  */
5
5
 
@@ -1,5 +1,5 @@
1
1
  /**
2
- * @license Copyright (c) 2003-2021, CKSource - Frederico Knabben. All rights reserved.
2
+ * @license Copyright (c) 2003-2022, CKSource Holding sp. z o.o. All rights reserved.
3
3
  * For licensing, see LICENSE.md or https://ckeditor.com/legal/ckeditor-oss-license
4
4
  */
5
5
 
@@ -1,5 +1,5 @@
1
1
  /**
2
- * @license Copyright (c) 2003-2021, CKSource - Frederico Knabben. All rights reserved.
2
+ * @license Copyright (c) 2003-2022, CKSource Holding sp. z o.o. All rights reserved.
3
3
  * For licensing, see LICENSE.md or https://ckeditor.com/legal/ckeditor-oss-license
4
4
  */
5
5
 
@@ -1,5 +1,5 @@
1
1
  /**
2
- * @license Copyright (c) 2003-2021, CKSource - Frederico Knabben. All rights reserved.
2
+ * @license Copyright (c) 2003-2022, CKSource Holding sp. z o.o. All rights reserved.
3
3
  * For licensing, see LICENSE.md or https://ckeditor.com/legal/ckeditor-oss-license
4
4
  */
5
5
 
@@ -1,5 +1,5 @@
1
1
  /**
2
- * @license Copyright (c) 2003-2021, CKSource - Frederico Knabben. All rights reserved.
2
+ * @license Copyright (c) 2003-2022, CKSource Holding sp. z o.o. All rights reserved.
3
3
  * For licensing, see LICENSE.md or https://ckeditor.com/legal/ckeditor-oss-license
4
4
  */
5
5
 
@@ -1,5 +1,5 @@
1
1
  /**
2
- * @license Copyright (c) 2003-2021, CKSource - Frederico Knabben. All rights reserved.
2
+ * @license Copyright (c) 2003-2022, CKSource Holding sp. z o.o. All rights reserved.
3
3
  * For licensing, see LICENSE.md or https://ckeditor.com/legal/ckeditor-oss-license
4
4
  */
5
5
 
@@ -1,5 +1,5 @@
1
1
  /**
2
- * @license Copyright (c) 2003-2021, CKSource - Frederico Knabben. All rights reserved.
2
+ * @license Copyright (c) 2003-2022, CKSource Holding sp. z o.o. All rights reserved.
3
3
  * For licensing, see LICENSE.md or https://ckeditor.com/legal/ckeditor-oss-license
4
4
  */
5
5
 
@@ -1,5 +1,5 @@
1
1
  /**
2
- * @license Copyright (c) 2003-2021, CKSource - Frederico Knabben. All rights reserved.
2
+ * @license Copyright (c) 2003-2022, CKSource Holding sp. z o.o. All rights reserved.
3
3
  * For licensing, see LICENSE.md or https://ckeditor.com/legal/ckeditor-oss-license
4
4
  */
5
5
 
@@ -1,5 +1,5 @@
1
1
  /**
2
- * @license Copyright (c) 2003-2021, CKSource - Frederico Knabben. All rights reserved.
2
+ * @license Copyright (c) 2003-2022, CKSource Holding sp. z o.o. All rights reserved.
3
3
  * For licensing, see LICENSE.md or https://ckeditor.com/legal/ckeditor-oss-license
4
4
  */
5
5
 
@@ -1,5 +1,5 @@
1
1
  /**
2
- * @license Copyright (c) 2003-2021, CKSource - Frederico Knabben. All rights reserved.
2
+ * @license Copyright (c) 2003-2022, CKSource Holding sp. z o.o. All rights reserved.
3
3
  * For licensing, see LICENSE.md or https://ckeditor.com/legal/ckeditor-oss-license
4
4
  */
5
5
 
@@ -1,5 +1,5 @@
1
1
  /**
2
- * @license Copyright (c) 2003-2021, CKSource - Frederico Knabben. All rights reserved.
2
+ * @license Copyright (c) 2003-2022, CKSource Holding sp. z o.o. All rights reserved.
3
3
  * For licensing, see LICENSE.md or https://ckeditor.com/legal/ckeditor-oss-license
4
4
  */
5
5
 
@@ -1,5 +1,5 @@
1
1
  /**
2
- * @license Copyright (c) 2003-2021, CKSource - Frederico Knabben. All rights reserved.
2
+ * @license Copyright (c) 2003-2022, CKSource Holding sp. z o.o. All rights reserved.
3
3
  * For licensing, see LICENSE.md or https://ckeditor.com/legal/ckeditor-oss-license
4
4
  */
5
5
 
@@ -7,7 +7,7 @@
7
7
  * @module engine/dataprocessor/htmldataprocessor
8
8
  */
9
9
 
10
- /* globals document, DOMParser, Node */
10
+ /* globals document, DOMParser */
11
11
 
12
12
  import BasicHtmlWriter from './basichtmlwriter';
13
13
  import DomConverter from '../view/domconverter';
@@ -28,26 +28,23 @@ export default class HtmlDataProcessor {
28
28
  /**
29
29
  * A DOM parser instance used to parse an HTML string to an HTML document.
30
30
  *
31
- * @private
32
31
  * @member {DOMParser}
33
32
  */
34
- this._domParser = new DOMParser();
33
+ this.domParser = new DOMParser();
35
34
 
36
35
  /**
37
36
  * A DOM converter used to convert DOM elements to view elements.
38
37
  *
39
- * @private
40
38
  * @member {module:engine/view/domconverter~DomConverter}
41
39
  */
42
- this._domConverter = new DomConverter( document, { blockFillerMode: 'nbsp' } );
40
+ this.domConverter = new DomConverter( document, { renderingMode: 'data' } );
43
41
 
44
42
  /**
45
43
  * A basic HTML writer instance used to convert DOM elements to an HTML string.
46
44
  *
47
- * @private
48
- * @member {module:engine/dataprocessor/basichtmlwriter~BasicHtmlWriter}
45
+ * @member {module:engine/dataprocessor/htmlwriter~HtmlWriter}
49
46
  */
50
- this._htmlWriter = new BasicHtmlWriter();
47
+ this.htmlWriter = new BasicHtmlWriter();
51
48
  }
52
49
 
53
50
  /**
@@ -59,10 +56,10 @@ export default class HtmlDataProcessor {
59
56
  */
60
57
  toData( viewFragment ) {
61
58
  // Convert view DocumentFragment to DOM DocumentFragment.
62
- const domFragment = this._domConverter.viewToDom( viewFragment, document );
59
+ const domFragment = this.domConverter.viewToDom( viewFragment, document );
63
60
 
64
61
  // Convert DOM DocumentFragment to HTML output.
65
- return this._htmlWriter.getHtml( domFragment );
62
+ return this.htmlWriter.getHtml( domFragment );
66
63
  }
67
64
 
68
65
  /**
@@ -76,7 +73,7 @@ export default class HtmlDataProcessor {
76
73
  const domFragment = this._toDom( data );
77
74
 
78
75
  // Convert DOM DocumentFragment to view DocumentFragment.
79
- return this._domConverter.domToView( domFragment );
76
+ return this.domConverter.domToView( domFragment );
80
77
  }
81
78
 
82
79
  /**
@@ -90,7 +87,7 @@ export default class HtmlDataProcessor {
90
87
  * be treated as raw data.
91
88
  */
92
89
  registerRawContentMatcher( pattern ) {
93
- this._domConverter.registerRawContentMatcher( pattern );
90
+ this.domConverter.registerRawContentMatcher( pattern );
94
91
  }
95
92
 
96
93
  /**
@@ -105,7 +102,7 @@ export default class HtmlDataProcessor {
105
102
  * @param {'default'|'marked'} type Whether to use the default or the marked `&nbsp;` block fillers.
106
103
  */
107
104
  useFillerType( type ) {
108
- this._domConverter.blockFillerMode = type == 'marked' ? 'markedNbsp' : 'nbsp';
105
+ this.domConverter.blockFillerMode = type == 'marked' ? 'markedNbsp' : 'nbsp';
109
106
  }
110
107
 
111
108
  /**
@@ -117,37 +114,15 @@ export default class HtmlDataProcessor {
117
114
  * @returns {DocumentFragment}
118
115
  */
119
116
  _toDom( data ) {
120
- const document = this._domParser.parseFromString( data, 'text/html' );
121
- const fragment = document.createDocumentFragment();
122
-
123
- // The rules for parsing an HTML string can be read on https://html.spec.whatwg.org/multipage/parsing.html#parsing-main-inhtml.
124
- //
125
- // In short, parsing tokens in an HTML string starts with the so-called "initial" insertion mode. When a DOM parser is in this
126
- // state and encounters a comment node, it inserts this comment node as the last child of the newly-created `HTMLDocument` object.
127
- // The parser then proceeds to successive insertion modes during parsing subsequent tokens and appends in the `HTMLDocument` object
128
- // other nodes (like <html>, <head>, <body>). This causes that the first leading comments from HTML string become the first nodes
129
- // in the `HTMLDocument` object, but not in the <body> collection, because they are ultimately located before the <html> element.
130
- //
131
- // Therefore, so that such leading comments do not disappear, they all are moved from the `HTMLDocument` object to the document
132
- // fragment, until the <html> element is encountered.
133
- //
134
- // See: https://github.com/ckeditor/ckeditor5/issues/9861.
135
- let documentChildNode = document.firstChild;
136
-
137
- while ( !documentChildNode.isSameNode( document.documentElement ) ) {
138
- const node = documentChildNode;
139
-
140
- documentChildNode = documentChildNode.nextSibling;
141
-
142
- // It seems that `DOMParser#parseFromString()` adds only comment nodes directly to the `HTMLDocument` object, before the <html>
143
- // node. The condition below is just to be sure we are moving only comment nodes.
144
-
145
- /* istanbul ignore else */
146
- if ( node.nodeType == Node.COMMENT_NODE ) {
147
- fragment.appendChild( node );
148
- }
117
+ // Wrap data with a <body> so leading non-layout nodes (like <script>, <style>, HTML comment)
118
+ // will be preserved in the body collection.
119
+ // Do it only for data that is not a full HTML document.
120
+ if ( !data.match( /<(?:html|body|head|meta)(?:\s[^>]*)?>/i ) ) {
121
+ data = `<body>${ data }</body>`;
149
122
  }
150
123
 
124
+ const document = this.domParser.parseFromString( data, 'text/html' );
125
+ const fragment = document.createDocumentFragment();
151
126
  const bodyChildNodes = document.body.childNodes;
152
127
 
153
128
  while ( bodyChildNodes.length > 0 ) {
@@ -1,5 +1,5 @@
1
1
  /**
2
- * @license Copyright (c) 2003-2021, CKSource - Frederico Knabben. All rights reserved.
2
+ * @license Copyright (c) 2003-2022, CKSource Holding sp. z o.o. All rights reserved.
3
3
  * For licensing, see LICENSE.md or https://ckeditor.com/legal/ckeditor-oss-license
4
4
  */
5
5
 
@@ -1,5 +1,5 @@
1
1
  /**
2
- * @license Copyright (c) 2003-2021, CKSource - Frederico Knabben. All rights reserved.
2
+ * @license Copyright (c) 2003-2022, CKSource Holding sp. z o.o. All rights reserved.
3
3
  * For licensing, see LICENSE.md or https://ckeditor.com/legal/ckeditor-oss-license
4
4
  */
5
5
 
@@ -26,7 +26,7 @@ export default class XmlDataProcessor {
26
26
  *
27
27
  * @param {module:engine/view/document~Document} document The view document instance.
28
28
  * @param {Object} options Configuration options.
29
- * @param {Array<String>} [options.namespaces=[]] A list of namespaces allowed to use in the XML input.
29
+ * @param {Array.<String>} [options.namespaces=[]] A list of namespaces allowed to use in the XML input.
30
30
  */
31
31
  constructor( document, options = {} ) {
32
32
  /**
@@ -35,35 +35,31 @@ export default class XmlDataProcessor {
35
35
  * For example, registering namespaces [ 'attribute', 'container' ] allows to use `<attirbute:tagName></attribute:tagName>`
36
36
  * and `<container:tagName></container:tagName>` input. It is mainly for debugging.
37
37
  *
38
- * @public
39
- * @member {DOMParser}
38
+ * @member {Array.<String>}
40
39
  */
41
40
  this.namespaces = options.namespaces || [];
42
41
 
43
42
  /**
44
43
  * DOM parser instance used to parse an XML string to an XML document.
45
44
  *
46
- * @private
47
45
  * @member {DOMParser}
48
46
  */
49
- this._domParser = new DOMParser();
47
+ this.domParser = new DOMParser();
50
48
 
51
49
  /**
52
50
  * DOM converter used to convert DOM elements to view elements.
53
51
  *
54
- * @private
55
52
  * @member {module:engine/view/domconverter~DomConverter}
56
53
  */
57
- this._domConverter = new DomConverter( document, { blockFillerMode: 'nbsp' } );
54
+ this.domConverter = new DomConverter( document, { renderingMode: 'data' } );
58
55
 
59
56
  /**
60
57
  * A basic HTML writer instance used to convert DOM elements to an XML string.
61
58
  * There is no need to use a dedicated XML writer because the basic HTML writer works well in this case.
62
59
  *
63
- * @private
64
- * @member {module:engine/dataprocessor/basichtmlwriter~BasicHtmlWriter}
60
+ * @member {module:engine/dataprocessor/htmlwriter~HtmlWriter}
65
61
  */
66
- this._htmlWriter = new BasicHtmlWriter();
62
+ this.htmlWriter = new BasicHtmlWriter();
67
63
  }
68
64
 
69
65
  /**
@@ -75,11 +71,11 @@ export default class XmlDataProcessor {
75
71
  */
76
72
  toData( viewFragment ) {
77
73
  // Convert view DocumentFragment to DOM DocumentFragment.
78
- const domFragment = this._domConverter.viewToDom( viewFragment, document );
74
+ const domFragment = this.domConverter.viewToDom( viewFragment, document );
79
75
 
80
76
  // Convert DOM DocumentFragment to XML output.
81
77
  // There is no need to use dedicated for XML serializing method because BasicHtmlWriter works well in this case.
82
- return this._htmlWriter.getHtml( domFragment );
78
+ return this.htmlWriter.getHtml( domFragment );
83
79
  }
84
80
 
85
81
  /**
@@ -93,7 +89,7 @@ export default class XmlDataProcessor {
93
89
  const domFragment = this._toDom( data );
94
90
 
95
91
  // Convert DOM DocumentFragment to view DocumentFragment.
96
- return this._domConverter.domToView( domFragment, { keepOriginalCase: true } );
92
+ return this.domConverter.domToView( domFragment, { keepOriginalCase: true } );
97
93
  }
98
94
 
99
95
  /**
@@ -107,7 +103,7 @@ export default class XmlDataProcessor {
107
103
  * be treated as raw data.
108
104
  */
109
105
  registerRawContentMatcher( pattern ) {
110
- this._domConverter.registerRawContentMatcher( pattern );
106
+ this.domConverter.registerRawContentMatcher( pattern );
111
107
  }
112
108
 
113
109
  /**
@@ -122,7 +118,7 @@ export default class XmlDataProcessor {
122
118
  * @param {'default'|'marked'} type Whether to use the default or the marked `&nbsp;` block fillers.
123
119
  */
124
120
  useFillerType( type ) {
125
- this._domConverter.blockFillerMode = type == 'marked' ? 'markedNbsp' : 'nbsp';
121
+ this.domConverter.blockFillerMode = type == 'marked' ? 'markedNbsp' : 'nbsp';
126
122
  }
127
123
 
128
124
  /**
@@ -140,7 +136,7 @@ export default class XmlDataProcessor {
140
136
  // Wrap data into root element with optional namespace definitions.
141
137
  data = `<xml ${ namespaces }>${ data }</xml>`;
142
138
 
143
- const parsedDocument = this._domParser.parseFromString( data, 'text/xml' );
139
+ const parsedDocument = this.domParser.parseFromString( data, 'text/xml' );
144
140
 
145
141
  // Parse validation.
146
142
  const parserError = parsedDocument.querySelector( 'parsererror' );
@@ -1,5 +1,5 @@
1
1
  /**
2
- * @license Copyright (c) 2003-2021, CKSource - Frederico Knabben. All rights reserved.
2
+ * @license Copyright (c) 2003-2022, CKSource Holding sp. z o.o. All rights reserved.
3
3
  * For licensing, see LICENSE.md or https://ckeditor.com/legal/ckeditor-oss-license
4
4
  */
5
5
 
@@ -102,7 +102,7 @@ getData._stringify = stringify;
102
102
  * name will be used.
103
103
  * @param {Array<Object>} [options.selectionAttributes] A list of attributes which will be passed to the selection.
104
104
  * @param {Boolean} [options.lastRangeBackward=false] If set to `true`, the last range will be added as backward.
105
- * @param {String} [options.batchType='default'] Batch type used for inserting elements.
105
+ * @param {Object} [options.batchType] Batch type used for inserting elements. See {@link module:engine/model/batch~Batch#constructor}.
106
106
  * See {@link module:engine/model/batch~Batch#type}.
107
107
  */
108
108
  export function setData( model, data, options = {} ) {
@@ -128,7 +128,7 @@ export function setData( model, data, options = {} ) {
128
128
  modelDocumentFragment = parsedResult;
129
129
  }
130
130
 
131
- if ( typeof options.batchType === 'string' ) {
131
+ if ( options.batchType !== undefined ) {
132
132
  model.enqueueChange( options.batchType, writeToModel );
133
133
  } else {
134
134
  model.change( writeToModel );
@@ -1,5 +1,5 @@
1
1
  /**
2
- * @license Copyright (c) 2003-2021, CKSource - Frederico Knabben. All rights reserved.
2
+ * @license Copyright (c) 2003-2022, CKSource Holding sp. z o.o. All rights reserved.
3
3
  * For licensing, see LICENSE.md or https://ckeditor.com/legal/ckeditor-oss-license
4
4
  */
5
5
 
@@ -1,5 +1,5 @@
1
1
  /**
2
- * @license Copyright (c) 2003-2021, CKSource - Frederico Knabben. All rights reserved.
2
+ * @license Copyright (c) 2003-2022, CKSource Holding sp. z o.o. All rights reserved.
3
3
  * For licensing, see LICENSE.md or https://ckeditor.com/legal/ckeditor-oss-license
4
4
  */
5
5