@ckeditor/ckeditor5-engine 36.0.0 → 37.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/README.md +1 -1
- package/package.json +24 -23
- package/src/controller/datacontroller.d.ts +331 -0
- package/src/controller/datacontroller.js +62 -109
- package/src/controller/editingcontroller.d.ts +98 -0
- package/src/controller/editingcontroller.js +22 -46
- package/src/conversion/conversion.d.ts +476 -0
- package/src/conversion/conversion.js +328 -347
- package/src/conversion/conversionhelpers.d.ts +26 -0
- package/src/conversion/conversionhelpers.js +1 -5
- package/src/conversion/downcastdispatcher.d.ts +547 -0
- package/src/conversion/downcastdispatcher.js +74 -152
- package/src/conversion/downcasthelpers.d.ts +1226 -0
- package/src/conversion/downcasthelpers.js +843 -762
- package/src/conversion/mapper.d.ts +499 -0
- package/src/conversion/mapper.js +84 -99
- package/src/conversion/modelconsumable.d.ts +201 -0
- package/src/conversion/modelconsumable.js +96 -99
- package/src/conversion/upcastdispatcher.d.ts +492 -0
- package/src/conversion/upcastdispatcher.js +73 -100
- package/src/conversion/upcasthelpers.d.ts +499 -0
- package/src/conversion/upcasthelpers.js +406 -373
- package/src/conversion/viewconsumable.d.ts +177 -0
- package/src/conversion/viewconsumable.js +157 -162
- package/src/dataprocessor/basichtmlwriter.d.ts +18 -0
- package/src/dataprocessor/basichtmlwriter.js +0 -9
- package/src/dataprocessor/dataprocessor.d.ts +61 -0
- package/src/dataprocessor/htmldataprocessor.d.ts +76 -0
- package/src/dataprocessor/htmldataprocessor.js +6 -28
- package/src/dataprocessor/htmlwriter.d.ts +16 -0
- package/src/dataprocessor/xmldataprocessor.d.ts +90 -0
- package/src/dataprocessor/xmldataprocessor.js +8 -40
- package/src/dev-utils/model.d.ts +124 -0
- package/src/dev-utils/model.js +41 -38
- package/src/dev-utils/operationreplayer.d.ts +51 -0
- package/src/dev-utils/operationreplayer.js +6 -14
- package/src/dev-utils/utils.d.ts +37 -0
- package/src/dev-utils/utils.js +5 -18
- package/src/dev-utils/view.d.ts +319 -0
- package/src/dev-utils/view.js +205 -226
- package/src/index.d.ts +105 -0
- package/src/index.js +1 -0
- package/src/model/batch.d.ts +106 -0
- package/src/model/differ.d.ts +329 -0
- package/src/model/document.d.ts +245 -0
- package/src/model/document.js +1 -1
- package/src/model/documentfragment.d.ts +196 -0
- package/src/model/documentfragment.js +2 -2
- package/src/model/documentselection.d.ts +420 -0
- package/src/model/element.d.ts +165 -0
- package/src/model/history.d.ts +114 -0
- package/src/model/item.d.ts +14 -0
- package/src/model/liveposition.d.ts +77 -0
- package/src/model/liverange.d.ts +102 -0
- package/src/model/markercollection.d.ts +335 -0
- package/src/model/model.d.ts +812 -0
- package/src/model/model.js +59 -30
- package/src/model/node.d.ts +256 -0
- package/src/model/nodelist.d.ts +91 -0
- package/src/model/operation/attributeoperation.d.ts +98 -0
- package/src/model/operation/detachoperation.d.ts +55 -0
- package/src/model/operation/insertoperation.d.ts +85 -0
- package/src/model/operation/markeroperation.d.ts +86 -0
- package/src/model/operation/mergeoperation.d.ts +95 -0
- package/src/model/operation/moveoperation.d.ts +91 -0
- package/src/model/operation/nooperation.d.ts +33 -0
- package/src/model/operation/operation.d.ts +89 -0
- package/src/model/operation/operationfactory.d.ts +18 -0
- package/src/model/operation/renameoperation.d.ts +78 -0
- package/src/model/operation/rootattributeoperation.d.ts +97 -0
- package/src/model/operation/rootattributeoperation.js +1 -1
- package/src/model/operation/splitoperation.d.ts +104 -0
- package/src/model/operation/transform.d.ts +100 -0
- package/src/model/operation/utils.d.ts +71 -0
- package/src/model/position.d.ts +539 -0
- package/src/model/position.js +1 -1
- package/src/model/range.d.ts +458 -0
- package/src/model/range.js +1 -1
- package/src/model/rootelement.d.ts +40 -0
- package/src/model/schema.d.ts +1176 -0
- package/src/model/schema.js +15 -15
- package/src/model/selection.d.ts +472 -0
- package/src/model/text.d.ts +66 -0
- package/src/model/text.js +0 -2
- package/src/model/textproxy.d.ts +144 -0
- package/src/model/treewalker.d.ts +186 -0
- package/src/model/treewalker.js +19 -10
- package/src/model/typecheckable.d.ts +255 -0
- package/src/model/utils/autoparagraphing.d.ts +37 -0
- package/src/model/utils/deletecontent.d.ts +58 -0
- package/src/model/utils/findoptimalinsertionrange.d.ts +32 -0
- package/src/model/utils/getselectedcontent.d.ts +30 -0
- package/src/model/utils/insertcontent.d.ts +46 -0
- package/src/model/utils/insertcontent.js +2 -12
- package/src/model/utils/insertobject.d.ts +44 -0
- package/src/model/utils/insertobject.js +3 -14
- package/src/model/utils/modifyselection.d.ts +48 -0
- package/src/model/utils/selection-post-fixer.d.ts +65 -0
- package/src/model/writer.d.ts +726 -0
- package/src/model/writer.js +6 -4
- package/src/view/attributeelement.d.ts +108 -0
- package/src/view/attributeelement.js +25 -69
- package/src/view/containerelement.d.ts +49 -0
- package/src/view/containerelement.js +10 -43
- package/src/view/datatransfer.d.ts +75 -0
- package/src/view/datatransfer.js +24 -27
- package/src/view/document.d.ts +184 -0
- package/src/view/document.js +15 -84
- package/src/view/documentfragment.d.ts +150 -0
- package/src/view/documentfragment.js +40 -81
- package/src/view/documentselection.d.ts +219 -0
- package/src/view/documentselection.js +75 -121
- package/src/view/domconverter.d.ts +620 -0
- package/src/view/domconverter.js +159 -276
- package/src/view/downcastwriter.d.ts +804 -0
- package/src/view/downcastwriter.js +336 -380
- package/src/view/editableelement.d.ts +52 -0
- package/src/view/editableelement.js +9 -49
- package/src/view/element.d.ts +466 -0
- package/src/view/element.js +150 -222
- package/src/view/elementdefinition.d.ts +87 -0
- package/src/view/emptyelement.d.ts +41 -0
- package/src/view/emptyelement.js +11 -44
- package/src/view/filler.d.ts +111 -0
- package/src/view/filler.js +24 -21
- package/src/view/item.d.ts +14 -0
- package/src/view/matcher.d.ts +486 -0
- package/src/view/matcher.js +247 -218
- package/src/view/node.d.ts +160 -0
- package/src/view/node.js +26 -100
- package/src/view/observer/arrowkeysobserver.d.ts +41 -0
- package/src/view/observer/arrowkeysobserver.js +0 -13
- package/src/view/observer/bubblingemittermixin.d.ts +166 -0
- package/src/view/observer/bubblingemittermixin.js +36 -25
- package/src/view/observer/bubblingeventinfo.d.ts +47 -0
- package/src/view/observer/bubblingeventinfo.js +3 -29
- package/src/view/observer/clickobserver.d.ts +43 -0
- package/src/view/observer/clickobserver.js +9 -19
- package/src/view/observer/compositionobserver.d.ts +82 -0
- package/src/view/observer/compositionobserver.js +13 -42
- package/src/view/observer/domeventdata.d.ts +50 -0
- package/src/view/observer/domeventdata.js +5 -30
- package/src/view/observer/domeventobserver.d.ts +69 -0
- package/src/view/observer/domeventobserver.js +19 -21
- package/src/view/observer/fakeselectionobserver.d.ts +46 -0
- package/src/view/observer/fakeselectionobserver.js +2 -15
- package/src/view/observer/focusobserver.d.ts +82 -0
- package/src/view/observer/focusobserver.js +14 -40
- package/src/view/observer/inputobserver.d.ts +86 -0
- package/src/view/observer/inputobserver.js +18 -64
- package/src/view/observer/keyobserver.d.ts +67 -0
- package/src/view/observer/keyobserver.js +8 -42
- package/src/view/observer/mouseobserver.d.ts +89 -0
- package/src/view/observer/mouseobserver.js +8 -28
- package/src/view/observer/mutationobserver.d.ts +82 -0
- package/src/view/observer/mutationobserver.js +7 -37
- package/src/view/observer/observer.d.ts +84 -0
- package/src/view/observer/observer.js +12 -25
- package/src/view/observer/selectionobserver.d.ts +143 -0
- package/src/view/observer/selectionobserver.js +9 -99
- package/src/view/observer/tabobserver.d.ts +42 -0
- package/src/view/observer/tabobserver.js +0 -14
- package/src/view/placeholder.d.ts +85 -0
- package/src/view/placeholder.js +26 -43
- package/src/view/position.d.ts +189 -0
- package/src/view/position.js +36 -83
- package/src/view/range.d.ts +279 -0
- package/src/view/range.js +79 -122
- package/src/view/rawelement.d.ts +73 -0
- package/src/view/rawelement.js +34 -48
- package/src/view/renderer.d.ts +265 -0
- package/src/view/renderer.js +105 -193
- package/src/view/rooteditableelement.d.ts +41 -0
- package/src/view/rooteditableelement.js +12 -40
- package/src/view/selection.d.ts +375 -0
- package/src/view/selection.js +79 -153
- package/src/view/styles/background.d.ts +33 -0
- package/src/view/styles/background.js +14 -12
- package/src/view/styles/border.d.ts +43 -0
- package/src/view/styles/border.js +58 -48
- package/src/view/styles/margin.d.ts +29 -0
- package/src/view/styles/margin.js +13 -11
- package/src/view/styles/padding.d.ts +29 -0
- package/src/view/styles/padding.js +13 -11
- package/src/view/styles/utils.d.ts +93 -0
- package/src/view/styles/utils.js +22 -48
- package/src/view/stylesmap.d.ts +675 -0
- package/src/view/stylesmap.js +249 -244
- package/src/view/text.d.ts +74 -0
- package/src/view/text.js +16 -46
- package/src/view/textproxy.d.ts +97 -0
- package/src/view/textproxy.js +10 -59
- package/src/view/treewalker.d.ts +195 -0
- package/src/view/treewalker.js +43 -106
- package/src/view/typecheckable.d.ts +401 -0
- package/src/view/uielement.d.ts +96 -0
- package/src/view/uielement.js +28 -62
- package/src/view/upcastwriter.d.ts +328 -0
- package/src/view/upcastwriter.js +124 -134
- package/src/view/view.d.ts +327 -0
- package/src/view/view.js +79 -150
|
@@ -14,12 +14,12 @@ import ModelElement from '../model/element';
|
|
|
14
14
|
import ModelPosition from '../model/position';
|
|
15
15
|
import ViewAttributeElement from '../view/attributeelement';
|
|
16
16
|
import ConversionHelpers from './conversionhelpers';
|
|
17
|
-
import { cloneDeep } from 'lodash-es';
|
|
18
17
|
import { CKEditorError, toArray } from '@ckeditor/ckeditor5-utils';
|
|
18
|
+
import { cloneDeep } from 'lodash-es';
|
|
19
19
|
/**
|
|
20
20
|
* Downcast conversion helper functions.
|
|
21
21
|
*
|
|
22
|
-
* Learn more about {@glink framework/
|
|
22
|
+
* Learn more about {@glink framework/deep-dive/conversion/downcast downcast helpers}.
|
|
23
23
|
*
|
|
24
24
|
* @extends module:engine/conversion/conversionhelpers~ConversionHelpers
|
|
25
25
|
*/
|
|
@@ -29,33 +29,35 @@ export default class DowncastHelpers extends ConversionHelpers {
|
|
|
29
29
|
*
|
|
30
30
|
* This conversion results in creating a view element. For example, model `<paragraph>Foo</paragraph>` becomes `<p>Foo</p>` in the view.
|
|
31
31
|
*
|
|
32
|
-
*
|
|
33
|
-
*
|
|
34
|
-
*
|
|
35
|
-
*
|
|
36
|
-
*
|
|
37
|
-
*
|
|
38
|
-
*
|
|
39
|
-
*
|
|
40
|
-
*
|
|
41
|
-
*
|
|
42
|
-
*
|
|
43
|
-
*
|
|
44
|
-
*
|
|
45
|
-
*
|
|
46
|
-
*
|
|
47
|
-
*
|
|
48
|
-
*
|
|
49
|
-
*
|
|
50
|
-
*
|
|
51
|
-
*
|
|
52
|
-
*
|
|
53
|
-
*
|
|
54
|
-
*
|
|
55
|
-
*
|
|
56
|
-
*
|
|
57
|
-
*
|
|
58
|
-
*
|
|
32
|
+
* ```ts
|
|
33
|
+
* editor.conversion.for( 'downcast' ).elementToElement( {
|
|
34
|
+
* model: 'paragraph',
|
|
35
|
+
* view: 'p'
|
|
36
|
+
* } );
|
|
37
|
+
*
|
|
38
|
+
* editor.conversion.for( 'downcast' ).elementToElement( {
|
|
39
|
+
* model: 'paragraph',
|
|
40
|
+
* view: 'div',
|
|
41
|
+
* converterPriority: 'high'
|
|
42
|
+
* } );
|
|
43
|
+
*
|
|
44
|
+
* editor.conversion.for( 'downcast' ).elementToElement( {
|
|
45
|
+
* model: 'fancyParagraph',
|
|
46
|
+
* view: {
|
|
47
|
+
* name: 'p',
|
|
48
|
+
* classes: 'fancy'
|
|
49
|
+
* }
|
|
50
|
+
* } );
|
|
51
|
+
*
|
|
52
|
+
* editor.conversion.for( 'downcast' ).elementToElement( {
|
|
53
|
+
* model: 'heading',
|
|
54
|
+
* view: ( modelElement, conversionApi ) => {
|
|
55
|
+
* const { writer } = conversionApi;
|
|
56
|
+
*
|
|
57
|
+
* return writer.createContainerElement( 'h' + modelElement.getAttribute( 'level' ) );
|
|
58
|
+
* }
|
|
59
|
+
* } );
|
|
60
|
+
* ```
|
|
59
61
|
*
|
|
60
62
|
* The element-to-element conversion supports the reconversion mechanism. It can be enabled by using either the `attributes` or
|
|
61
63
|
* the `children` props on a model description. You will find a couple examples below.
|
|
@@ -63,93 +65,108 @@ export default class DowncastHelpers extends ConversionHelpers {
|
|
|
63
65
|
* In order to reconvert an element if any of its direct children have been added or removed, use the `children` property on a `model`
|
|
64
66
|
* description. For example, this model:
|
|
65
67
|
*
|
|
66
|
-
*
|
|
67
|
-
*
|
|
68
|
-
*
|
|
68
|
+
* ```xml
|
|
69
|
+
* <box>
|
|
70
|
+
* <paragraph>Some text.</paragraph>
|
|
71
|
+
* </box>
|
|
72
|
+
* ```
|
|
69
73
|
*
|
|
70
74
|
* will be converted into this structure in the view:
|
|
71
75
|
*
|
|
72
|
-
*
|
|
73
|
-
*
|
|
74
|
-
*
|
|
76
|
+
* ```html
|
|
77
|
+
* <div class="box" data-type="single">
|
|
78
|
+
* <p>Some text.</p>
|
|
79
|
+
* </div>
|
|
80
|
+
* ```
|
|
75
81
|
*
|
|
76
82
|
* But if more items were inserted in the model:
|
|
77
83
|
*
|
|
78
|
-
*
|
|
79
|
-
*
|
|
80
|
-
*
|
|
81
|
-
*
|
|
84
|
+
* ```xml
|
|
85
|
+
* <box>
|
|
86
|
+
* <paragraph>Some text.</paragraph>
|
|
87
|
+
* <paragraph>Other item.</paragraph>
|
|
88
|
+
* </box>
|
|
89
|
+
* ```
|
|
82
90
|
*
|
|
83
91
|
* it will be converted into this structure in the view (note the element `data-type` change):
|
|
84
92
|
*
|
|
85
|
-
*
|
|
86
|
-
*
|
|
87
|
-
*
|
|
88
|
-
*
|
|
93
|
+
* ```html
|
|
94
|
+
* <div class="box" data-type="multiple">
|
|
95
|
+
* <p>Some text.</p>
|
|
96
|
+
* <p>Other item.</p>
|
|
97
|
+
* </div>
|
|
98
|
+
* ```
|
|
89
99
|
*
|
|
90
100
|
* Such a converter would look like this (note that the `paragraph` elements are converted separately):
|
|
91
101
|
*
|
|
92
|
-
*
|
|
93
|
-
*
|
|
94
|
-
*
|
|
95
|
-
*
|
|
96
|
-
*
|
|
97
|
-
*
|
|
98
|
-
*
|
|
99
|
-
*
|
|
100
|
-
*
|
|
101
|
-
*
|
|
102
|
-
*
|
|
103
|
-
*
|
|
104
|
-
*
|
|
105
|
-
*
|
|
102
|
+
* ```ts
|
|
103
|
+
* editor.conversion.for( 'downcast' ).elementToElement( {
|
|
104
|
+
* model: {
|
|
105
|
+
* name: 'box',
|
|
106
|
+
* children: true
|
|
107
|
+
* },
|
|
108
|
+
* view: ( modelElement, conversionApi ) => {
|
|
109
|
+
* const { writer } = conversionApi;
|
|
110
|
+
*
|
|
111
|
+
* return writer.createContainerElement( 'div', {
|
|
112
|
+
* class: 'box',
|
|
113
|
+
* 'data-type': modelElement.childCount == 1 ? 'single' : 'multiple'
|
|
114
|
+
* } );
|
|
115
|
+
* }
|
|
116
|
+
* } );
|
|
117
|
+
* ```
|
|
106
118
|
*
|
|
107
119
|
* In order to reconvert element if any of its attributes have been updated, use the `attributes` property on a `model`
|
|
108
120
|
* description. For example, this model:
|
|
109
121
|
*
|
|
110
|
-
*
|
|
122
|
+
* ```xml
|
|
123
|
+
* <heading level="2">Some text.</heading>
|
|
124
|
+
* ```
|
|
111
125
|
*
|
|
112
126
|
* will be converted into this structure in the view:
|
|
113
127
|
*
|
|
114
|
-
*
|
|
128
|
+
* ```html
|
|
129
|
+
* <h2>Some text.</h2>
|
|
130
|
+
* ```
|
|
115
131
|
*
|
|
116
132
|
* But if the `heading` element's `level` attribute has been updated to `3` for example, then
|
|
117
133
|
* it will be converted into this structure in the view:
|
|
118
134
|
*
|
|
119
|
-
*
|
|
135
|
+
* ```html
|
|
136
|
+
* <h3>Some text.</h3>
|
|
137
|
+
* ```
|
|
120
138
|
*
|
|
121
139
|
* Such a converter would look as follows:
|
|
122
140
|
*
|
|
123
|
-
*
|
|
124
|
-
*
|
|
125
|
-
*
|
|
126
|
-
*
|
|
127
|
-
*
|
|
128
|
-
*
|
|
129
|
-
*
|
|
141
|
+
* ```ts
|
|
142
|
+
* editor.conversion.for( 'downcast' ).elementToElement( {
|
|
143
|
+
* model: {
|
|
144
|
+
* name: 'heading',
|
|
145
|
+
* attributes: 'level'
|
|
146
|
+
* },
|
|
147
|
+
* view: ( modelElement, conversionApi ) => {
|
|
148
|
+
* const { writer } = conversionApi;
|
|
130
149
|
*
|
|
131
|
-
*
|
|
132
|
-
*
|
|
133
|
-
*
|
|
150
|
+
* return writer.createContainerElement( 'h' + modelElement.getAttribute( 'level' ) );
|
|
151
|
+
* }
|
|
152
|
+
* } );
|
|
153
|
+
* ```
|
|
134
154
|
*
|
|
135
155
|
* See {@link module:engine/conversion/conversion~Conversion#for `conversion.for()`} to learn how to add a converter
|
|
136
156
|
* to the conversion process.
|
|
137
157
|
*
|
|
138
158
|
* You can read more about the element-to-element conversion in the
|
|
139
|
-
* {@glink framework/
|
|
159
|
+
* {@glink framework/deep-dive/conversion/downcast downcast conversion} guide.
|
|
140
160
|
*
|
|
141
|
-
* @
|
|
142
|
-
* @param
|
|
143
|
-
* @param
|
|
144
|
-
* @param {String|Array.<String>} [config.model.attributes] The list of attribute names that should be consumed while creating
|
|
161
|
+
* @param config Conversion configuration.
|
|
162
|
+
* @param config.model The description or a name of the model element to convert.
|
|
163
|
+
* @param config.model.attributes The list of attribute names that should be consumed while creating
|
|
145
164
|
* the view element. Note that the view will be reconverted if any of the listed attributes changes.
|
|
146
|
-
* @param
|
|
165
|
+
* @param config.model.children Specifies whether the view element requires reconversion if the list
|
|
147
166
|
* of the model child nodes changed.
|
|
148
|
-
* @param
|
|
149
|
-
* config.view A view element definition or a function that takes the model element and
|
|
167
|
+
* @param config.view A view element definition or a function that takes the model element and
|
|
150
168
|
* {@link module:engine/conversion/downcastdispatcher~DowncastConversionApi downcast conversion API}
|
|
151
169
|
* as parameters and returns a view container element.
|
|
152
|
-
* @returns {module:engine/conversion/downcasthelpers~DowncastHelpers}
|
|
153
170
|
*/
|
|
154
171
|
elementToElement(config) {
|
|
155
172
|
return this.add(downcastElementToElement(config));
|
|
@@ -160,68 +177,80 @@ export default class DowncastHelpers extends ConversionHelpers {
|
|
|
160
177
|
* This conversion results in creating a view structure with one or more slots defined for the child nodes.
|
|
161
178
|
* For example, a model `<table>` may become this structure in the view:
|
|
162
179
|
*
|
|
163
|
-
*
|
|
164
|
-
*
|
|
165
|
-
*
|
|
166
|
-
*
|
|
167
|
-
*
|
|
180
|
+
* ```html
|
|
181
|
+
* <figure class="table">
|
|
182
|
+
* <table>
|
|
183
|
+
* <tbody>${ slot for table rows }</tbody>
|
|
184
|
+
* </table>
|
|
185
|
+
* </figure>
|
|
186
|
+
* ```
|
|
168
187
|
*
|
|
169
188
|
* The children of the model's `<table>` element will be inserted into the `<tbody>` element.
|
|
170
189
|
* If the `elementToElement()` helper was used, the children would be inserted into the `<figure>`.
|
|
171
190
|
*
|
|
172
191
|
* An example converter that converts the following model structure:
|
|
173
192
|
*
|
|
174
|
-
*
|
|
193
|
+
* ```xml
|
|
194
|
+
* <wrappedParagraph>Some text.</wrappedParagraph>
|
|
195
|
+
* ```
|
|
175
196
|
*
|
|
176
197
|
* into this structure in the view:
|
|
177
198
|
*
|
|
178
|
-
*
|
|
179
|
-
*
|
|
180
|
-
*
|
|
199
|
+
* ```html
|
|
200
|
+
* <div class="wrapper">
|
|
201
|
+
* <p>Some text.</p>
|
|
202
|
+
* </div>
|
|
203
|
+
* ```
|
|
181
204
|
*
|
|
182
205
|
* would look like this:
|
|
183
206
|
*
|
|
184
|
-
*
|
|
185
|
-
*
|
|
186
|
-
*
|
|
187
|
-
*
|
|
207
|
+
* ```ts
|
|
208
|
+
* editor.conversion.for( 'downcast' ).elementToStructure( {
|
|
209
|
+
* model: 'wrappedParagraph',
|
|
210
|
+
* view: ( modelElement, conversionApi ) => {
|
|
211
|
+
* const { writer } = conversionApi;
|
|
188
212
|
*
|
|
189
|
-
*
|
|
190
|
-
*
|
|
213
|
+
* const wrapperViewElement = writer.createContainerElement( 'div', { class: 'wrapper' } );
|
|
214
|
+
* const paragraphViewElement = writer.createContainerElement( 'p' );
|
|
191
215
|
*
|
|
192
|
-
*
|
|
193
|
-
*
|
|
216
|
+
* writer.insert( writer.createPositionAt( wrapperViewElement, 0 ), paragraphViewElement );
|
|
217
|
+
* writer.insert( writer.createPositionAt( paragraphViewElement, 0 ), writer.createSlot() );
|
|
194
218
|
*
|
|
195
|
-
*
|
|
196
|
-
*
|
|
197
|
-
*
|
|
219
|
+
* return wrapperViewElement;
|
|
220
|
+
* }
|
|
221
|
+
* } );
|
|
222
|
+
* ```
|
|
198
223
|
*
|
|
199
224
|
* The `slorFor()` function can also take a callback that allows filtering which children of the model element
|
|
200
225
|
* should be converted into this slot.
|
|
201
226
|
*
|
|
202
227
|
* Imagine a table feature where for this model structure:
|
|
203
228
|
*
|
|
204
|
-
*
|
|
205
|
-
*
|
|
206
|
-
*
|
|
207
|
-
*
|
|
208
|
-
*
|
|
209
|
-
*
|
|
229
|
+
* ```xml
|
|
230
|
+
* <table headingRows="1">
|
|
231
|
+
* <tableRow> ... table cells 1 ... </tableRow>
|
|
232
|
+
* <tableRow> ... table cells 2 ... </tableRow>
|
|
233
|
+
* <tableRow> ... table cells 3 ... </tableRow>
|
|
234
|
+
* <caption>Caption text</caption>
|
|
235
|
+
* </table>
|
|
236
|
+
* ```
|
|
210
237
|
*
|
|
211
238
|
* we want to generate this view structure:
|
|
212
239
|
*
|
|
213
|
-
*
|
|
214
|
-
*
|
|
215
|
-
*
|
|
216
|
-
*
|
|
217
|
-
*
|
|
218
|
-
*
|
|
219
|
-
*
|
|
220
|
-
*
|
|
221
|
-
*
|
|
222
|
-
*
|
|
223
|
-
*
|
|
224
|
-
*
|
|
240
|
+
* ```html
|
|
241
|
+
* <figure class="table">
|
|
242
|
+
* <table>
|
|
243
|
+
* <thead>
|
|
244
|
+
* <tr> ... table cells 1 ... </tr>
|
|
245
|
+
* </thead>
|
|
246
|
+
* <tbody>
|
|
247
|
+
* <tr> ... table cells 2 ... </tr>
|
|
248
|
+
* <tr> ... table cells 3 ... </tr>
|
|
249
|
+
* </tbody>
|
|
250
|
+
* </table>
|
|
251
|
+
* <figcaption>Caption text</figcaption>
|
|
252
|
+
* </figure>
|
|
253
|
+
* ```
|
|
225
254
|
*
|
|
226
255
|
* The converter has to take the `headingRows` attribute into consideration when allocating the `<tableRow>` elements
|
|
227
256
|
* into the `<tbody>` and `<thead>` elements. Hence, we need two slots and need to define proper filter callbacks for them.
|
|
@@ -231,46 +260,48 @@ export default class DowncastHelpers extends ConversionHelpers {
|
|
|
231
260
|
*
|
|
232
261
|
* Such a converter would look like this:
|
|
233
262
|
*
|
|
234
|
-
*
|
|
235
|
-
*
|
|
236
|
-
*
|
|
237
|
-
*
|
|
238
|
-
*
|
|
239
|
-
*
|
|
240
|
-
*
|
|
263
|
+
* ```ts
|
|
264
|
+
* editor.conversion.for( 'downcast' ).elementToStructure( {
|
|
265
|
+
* model: {
|
|
266
|
+
* name: 'table',
|
|
267
|
+
* attributes: [ 'headingRows' ]
|
|
268
|
+
* },
|
|
269
|
+
* view: ( modelElement, conversionApi ) => {
|
|
270
|
+
* const { writer } = conversionApi;
|
|
241
271
|
*
|
|
242
|
-
*
|
|
243
|
-
*
|
|
272
|
+
* const figureElement = writer.createContainerElement( 'figure', { class: 'table' } );
|
|
273
|
+
* const tableElement = writer.createContainerElement( 'table' );
|
|
244
274
|
*
|
|
245
|
-
*
|
|
275
|
+
* writer.insert( writer.createPositionAt( figureElement, 0 ), tableElement );
|
|
246
276
|
*
|
|
247
|
-
*
|
|
277
|
+
* const headingRows = modelElement.getAttribute( 'headingRows' ) || 0;
|
|
248
278
|
*
|
|
249
|
-
*
|
|
250
|
-
*
|
|
279
|
+
* if ( headingRows > 0 ) {
|
|
280
|
+
* const tableHead = writer.createContainerElement( 'thead' );
|
|
251
281
|
*
|
|
252
|
-
*
|
|
282
|
+
* const headSlot = writer.createSlot( node => node.is( 'element', 'tableRow' ) && node.index < headingRows );
|
|
253
283
|
*
|
|
254
|
-
*
|
|
255
|
-
*
|
|
256
|
-
*
|
|
284
|
+
* writer.insert( writer.createPositionAt( tableElement, 'end' ), tableHead );
|
|
285
|
+
* writer.insert( writer.createPositionAt( tableHead, 0 ), headSlot );
|
|
286
|
+
* }
|
|
257
287
|
*
|
|
258
|
-
*
|
|
259
|
-
*
|
|
288
|
+
* if ( headingRows < tableUtils.getRows( table ) ) {
|
|
289
|
+
* const tableBody = writer.createContainerElement( 'tbody' );
|
|
260
290
|
*
|
|
261
|
-
*
|
|
291
|
+
* const bodySlot = writer.createSlot( node => node.is( 'element', 'tableRow' ) && node.index >= headingRows );
|
|
262
292
|
*
|
|
263
|
-
*
|
|
264
|
-
*
|
|
265
|
-
*
|
|
293
|
+
* writer.insert( writer.createPositionAt( tableElement, 'end' ), tableBody );
|
|
294
|
+
* writer.insert( writer.createPositionAt( tableBody, 0 ), bodySlot );
|
|
295
|
+
* }
|
|
266
296
|
*
|
|
267
|
-
*
|
|
297
|
+
* const restSlot = writer.createSlot( node => !node.is( 'element', 'tableRow' ) );
|
|
268
298
|
*
|
|
269
|
-
*
|
|
299
|
+
* writer.insert( writer.createPositionAt( figureElement, 'end' ), restSlot );
|
|
270
300
|
*
|
|
271
|
-
*
|
|
272
|
-
*
|
|
273
|
-
*
|
|
301
|
+
* return figureElement;
|
|
302
|
+
* }
|
|
303
|
+
* } );
|
|
304
|
+
* ```
|
|
274
305
|
*
|
|
275
306
|
* Note: The children of a model element that's being converted must be allocated in the same order in the view
|
|
276
307
|
* in which they are placed in the model.
|
|
@@ -278,16 +309,14 @@ export default class DowncastHelpers extends ConversionHelpers {
|
|
|
278
309
|
* See {@link module:engine/conversion/conversion~Conversion#for `conversion.for()`} to learn how to add a converter
|
|
279
310
|
* to the conversion process.
|
|
280
311
|
*
|
|
281
|
-
* @
|
|
282
|
-
* @param
|
|
283
|
-
* @param
|
|
284
|
-
* @param
|
|
285
|
-
* @param {String|Array.<String>} [config.model.attributes] The list of attribute names that should be consumed while creating
|
|
312
|
+
* @param config Conversion configuration.
|
|
313
|
+
* @param config.model The description or a name of the model element to convert.
|
|
314
|
+
* @param config.model.name The name of the model element to convert.
|
|
315
|
+
* @param config.model.attributes The list of attribute names that should be consumed while creating
|
|
286
316
|
* the view structure. Note that the view will be reconverted if any of the listed attributes will change.
|
|
287
|
-
* @param
|
|
288
|
-
*
|
|
289
|
-
*
|
|
290
|
-
* @returns {module:engine/conversion/downcasthelpers~DowncastHelpers}
|
|
317
|
+
* @param config.view A function that takes the model element and
|
|
318
|
+
* {@link module:engine/conversion/downcastdispatcher~DowncastConversionApi downcast conversion API} as parameters
|
|
319
|
+
* and returns a view container element with slots for model child nodes to be converted into.
|
|
291
320
|
*/
|
|
292
321
|
elementToStructure(config) {
|
|
293
322
|
return this.add(downcastElementToStructure(config));
|
|
@@ -298,86 +327,85 @@ export default class DowncastHelpers extends ConversionHelpers {
|
|
|
298
327
|
* This conversion results in wrapping view nodes with a view attribute element. For example, a model text node with
|
|
299
328
|
* `"Foo"` as data and the `bold` attribute becomes `<strong>Foo</strong>` in the view.
|
|
300
329
|
*
|
|
301
|
-
*
|
|
302
|
-
*
|
|
303
|
-
*
|
|
304
|
-
*
|
|
305
|
-
*
|
|
306
|
-
*
|
|
307
|
-
*
|
|
308
|
-
*
|
|
309
|
-
*
|
|
310
|
-
*
|
|
311
|
-
*
|
|
312
|
-
*
|
|
313
|
-
*
|
|
314
|
-
*
|
|
315
|
-
*
|
|
316
|
-
*
|
|
317
|
-
*
|
|
318
|
-
*
|
|
319
|
-
*
|
|
320
|
-
*
|
|
321
|
-
*
|
|
322
|
-
*
|
|
323
|
-
*
|
|
324
|
-
*
|
|
325
|
-
*
|
|
326
|
-
*
|
|
327
|
-
*
|
|
328
|
-
*
|
|
329
|
-
*
|
|
330
|
-
*
|
|
331
|
-
*
|
|
332
|
-
*
|
|
333
|
-
*
|
|
334
|
-
*
|
|
335
|
-
*
|
|
336
|
-
*
|
|
337
|
-
*
|
|
338
|
-
*
|
|
339
|
-
*
|
|
340
|
-
*
|
|
341
|
-
*
|
|
342
|
-
*
|
|
343
|
-
*
|
|
344
|
-
*
|
|
345
|
-
*
|
|
346
|
-
*
|
|
347
|
-
*
|
|
348
|
-
*
|
|
349
|
-
*
|
|
350
|
-
*
|
|
351
|
-
*
|
|
352
|
-
*
|
|
353
|
-
*
|
|
354
|
-
*
|
|
355
|
-
*
|
|
356
|
-
*
|
|
357
|
-
*
|
|
358
|
-
*
|
|
359
|
-
*
|
|
360
|
-
*
|
|
361
|
-
*
|
|
362
|
-
*
|
|
363
|
-
*
|
|
364
|
-
*
|
|
330
|
+
* ```ts
|
|
331
|
+
* editor.conversion.for( 'downcast' ).attributeToElement( {
|
|
332
|
+
* model: 'bold',
|
|
333
|
+
* view: 'strong'
|
|
334
|
+
* } );
|
|
335
|
+
*
|
|
336
|
+
* editor.conversion.for( 'downcast' ).attributeToElement( {
|
|
337
|
+
* model: 'bold',
|
|
338
|
+
* view: 'b',
|
|
339
|
+
* converterPriority: 'high'
|
|
340
|
+
* } );
|
|
341
|
+
*
|
|
342
|
+
* editor.conversion.for( 'downcast' ).attributeToElement( {
|
|
343
|
+
* model: 'invert',
|
|
344
|
+
* view: {
|
|
345
|
+
* name: 'span',
|
|
346
|
+
* classes: [ 'font-light', 'bg-dark' ]
|
|
347
|
+
* }
|
|
348
|
+
* } );
|
|
349
|
+
*
|
|
350
|
+
* editor.conversion.for( 'downcast' ).attributeToElement( {
|
|
351
|
+
* model: {
|
|
352
|
+
* key: 'fontSize',
|
|
353
|
+
* values: [ 'big', 'small' ]
|
|
354
|
+
* },
|
|
355
|
+
* view: {
|
|
356
|
+
* big: {
|
|
357
|
+
* name: 'span',
|
|
358
|
+
* styles: {
|
|
359
|
+
* 'font-size': '1.2em'
|
|
360
|
+
* }
|
|
361
|
+
* },
|
|
362
|
+
* small: {
|
|
363
|
+
* name: 'span',
|
|
364
|
+
* styles: {
|
|
365
|
+
* 'font-size': '0.8em'
|
|
366
|
+
* }
|
|
367
|
+
* }
|
|
368
|
+
* }
|
|
369
|
+
* } );
|
|
370
|
+
*
|
|
371
|
+
* editor.conversion.for( 'downcast' ).attributeToElement( {
|
|
372
|
+
* model: 'bold',
|
|
373
|
+
* view: ( modelAttributeValue, conversionApi ) => {
|
|
374
|
+
* const { writer } = conversionApi;
|
|
375
|
+
*
|
|
376
|
+
* return writer.createAttributeElement( 'span', {
|
|
377
|
+
* style: 'font-weight:' + modelAttributeValue
|
|
378
|
+
* } );
|
|
379
|
+
* }
|
|
380
|
+
* } );
|
|
381
|
+
*
|
|
382
|
+
* editor.conversion.for( 'downcast' ).attributeToElement( {
|
|
383
|
+
* model: {
|
|
384
|
+
* key: 'color',
|
|
385
|
+
* name: '$text'
|
|
386
|
+
* },
|
|
387
|
+
* view: ( modelAttributeValue, conversionApi ) => {
|
|
388
|
+
* const { writer } = conversionApi;
|
|
389
|
+
*
|
|
390
|
+
* return writer.createAttributeElement( 'span', {
|
|
391
|
+
* style: 'color:' + modelAttributeValue
|
|
392
|
+
* } );
|
|
393
|
+
* }
|
|
394
|
+
* } );
|
|
395
|
+
* ```
|
|
365
396
|
*
|
|
366
397
|
* See {@link module:engine/conversion/conversion~Conversion#for `conversion.for()`} to learn how to add a converter
|
|
367
398
|
* to the conversion process.
|
|
368
399
|
*
|
|
369
|
-
* @
|
|
370
|
-
* @param {
|
|
371
|
-
* @param {String|Object} config.model The key of the attribute to convert from or a `{ key, values }` object. `values` is an array
|
|
400
|
+
* @param config Conversion configuration.
|
|
401
|
+
* @param config.model The key of the attribute to convert from or a `{ key, values }` object. `values` is an array
|
|
372
402
|
* of `String`s with possible values if the model attribute is an enumerable.
|
|
373
|
-
* @param
|
|
374
|
-
* module:engine/conversion/downcasthelpers~AttributeElementCreatorFunction} config.view A view element definition or a function
|
|
403
|
+
* @param config.view A view element definition or a function
|
|
375
404
|
* that takes the model attribute value and
|
|
376
405
|
* {@link module:engine/conversion/downcastdispatcher~DowncastConversionApi downcast conversion API} as parameters and returns a view
|
|
377
406
|
* attribute element. If `config.model.values` is given, `config.view` should be an object assigning values from `config.model.values`
|
|
378
407
|
* to view element definitions or functions.
|
|
379
|
-
* @param
|
|
380
|
-
* @returns {module:engine/conversion/downcasthelpers~DowncastHelpers}
|
|
408
|
+
* @param config.converterPriority Converter priority.
|
|
381
409
|
*/
|
|
382
410
|
attributeToElement(config) {
|
|
383
411
|
return this.add(downcastAttributeToElement(config));
|
|
@@ -388,79 +416,80 @@ export default class DowncastHelpers extends ConversionHelpers {
|
|
|
388
416
|
* This conversion results in adding an attribute to a view node, basing on an attribute from a model node. For example,
|
|
389
417
|
* `<imageInline src='foo.jpg'></imageInline>` is converted to `<img src='foo.jpg'></img>`.
|
|
390
418
|
*
|
|
391
|
-
*
|
|
392
|
-
*
|
|
393
|
-
*
|
|
394
|
-
*
|
|
395
|
-
*
|
|
396
|
-
*
|
|
397
|
-
*
|
|
398
|
-
*
|
|
399
|
-
*
|
|
400
|
-
*
|
|
401
|
-
*
|
|
402
|
-
*
|
|
403
|
-
*
|
|
404
|
-
*
|
|
405
|
-
*
|
|
406
|
-
*
|
|
407
|
-
*
|
|
408
|
-
*
|
|
409
|
-
*
|
|
410
|
-
*
|
|
411
|
-
*
|
|
412
|
-
*
|
|
413
|
-
*
|
|
414
|
-
*
|
|
415
|
-
*
|
|
416
|
-
*
|
|
417
|
-
*
|
|
418
|
-
*
|
|
419
|
-
*
|
|
420
|
-
*
|
|
421
|
-
*
|
|
422
|
-
*
|
|
423
|
-
*
|
|
424
|
-
*
|
|
425
|
-
*
|
|
426
|
-
*
|
|
427
|
-
*
|
|
428
|
-
*
|
|
429
|
-
*
|
|
430
|
-
*
|
|
431
|
-
*
|
|
432
|
-
*
|
|
433
|
-
*
|
|
419
|
+
* ```ts
|
|
420
|
+
* editor.conversion.for( 'downcast' ).attributeToAttribute( {
|
|
421
|
+
* model: 'source',
|
|
422
|
+
* view: 'src'
|
|
423
|
+
* } );
|
|
424
|
+
*
|
|
425
|
+
* editor.conversion.for( 'downcast' ).attributeToAttribute( {
|
|
426
|
+
* model: 'source',
|
|
427
|
+
* view: 'href',
|
|
428
|
+
* converterPriority: 'high'
|
|
429
|
+
* } );
|
|
430
|
+
*
|
|
431
|
+
* editor.conversion.for( 'downcast' ).attributeToAttribute( {
|
|
432
|
+
* model: {
|
|
433
|
+
* name: 'imageInline',
|
|
434
|
+
* key: 'source'
|
|
435
|
+
* },
|
|
436
|
+
* view: 'src'
|
|
437
|
+
* } );
|
|
438
|
+
*
|
|
439
|
+
* editor.conversion.for( 'downcast' ).attributeToAttribute( {
|
|
440
|
+
* model: {
|
|
441
|
+
* name: 'styled',
|
|
442
|
+
* values: [ 'dark', 'light' ]
|
|
443
|
+
* },
|
|
444
|
+
* view: {
|
|
445
|
+
* dark: {
|
|
446
|
+
* key: 'class',
|
|
447
|
+
* value: [ 'styled', 'styled-dark' ]
|
|
448
|
+
* },
|
|
449
|
+
* light: {
|
|
450
|
+
* key: 'class',
|
|
451
|
+
* value: [ 'styled', 'styled-light' ]
|
|
452
|
+
* }
|
|
453
|
+
* }
|
|
454
|
+
* } );
|
|
455
|
+
*
|
|
456
|
+
* editor.conversion.for( 'downcast' ).attributeToAttribute( {
|
|
457
|
+
* model: 'styled',
|
|
458
|
+
* view: modelAttributeValue => ( {
|
|
459
|
+
* key: 'class',
|
|
460
|
+
* value: 'styled-' + modelAttributeValue
|
|
461
|
+
* } )
|
|
462
|
+
* } );
|
|
463
|
+
* ```
|
|
434
464
|
*
|
|
435
465
|
* **Note**: Downcasting to a style property requires providing `value` as an object:
|
|
436
466
|
*
|
|
437
|
-
*
|
|
438
|
-
*
|
|
439
|
-
*
|
|
440
|
-
*
|
|
441
|
-
*
|
|
442
|
-
*
|
|
443
|
-
*
|
|
444
|
-
*
|
|
445
|
-
*
|
|
446
|
-
*
|
|
467
|
+
* ```ts
|
|
468
|
+
* editor.conversion.for( 'downcast' ).attributeToAttribute( {
|
|
469
|
+
* model: 'lineHeight',
|
|
470
|
+
* view: modelAttributeValue => ( {
|
|
471
|
+
* key: 'style',
|
|
472
|
+
* value: {
|
|
473
|
+
* 'line-height': modelAttributeValue,
|
|
474
|
+
* 'border-bottom': '1px dotted #ba2'
|
|
475
|
+
* }
|
|
476
|
+
* } )
|
|
477
|
+
* } );
|
|
478
|
+
* ```
|
|
447
479
|
*
|
|
448
480
|
* See {@link module:engine/conversion/conversion~Conversion#for `conversion.for()`} to learn how to add a converter
|
|
449
481
|
* to the conversion process.
|
|
450
482
|
*
|
|
451
|
-
* @
|
|
452
|
-
* @param {
|
|
453
|
-
* @param {String|Object} config.model The key of the attribute to convert from or a `{ key, values, [ name ] }` object describing
|
|
483
|
+
* @param config Conversion configuration.
|
|
484
|
+
* @param config.model The key of the attribute to convert from or a `{ key, values, [ name ] }` object describing
|
|
454
485
|
* the attribute key, possible values and, optionally, an element name to convert from.
|
|
455
|
-
* @param
|
|
456
|
-
* or a `{ key, value }` object or a function that takes the model attribute value and
|
|
486
|
+
* @param config.view A view attribute key, or a `{ key, value }` object or a function that takes the model attribute value and
|
|
457
487
|
* {@link module:engine/conversion/downcastdispatcher~DowncastConversionApi downcast conversion API}
|
|
458
488
|
* as parameters and returns a `{ key, value }` object. If the `key` is `'class'`, the `value` can be a `String` or an
|
|
459
489
|
* array of `String`s. If the `key` is `'style'`, the `value` is an object with key-value pairs. In other cases, `value` is a `String`.
|
|
460
490
|
* If `config.model.values` is set, `config.view` should be an object assigning values from `config.model.values` to
|
|
461
491
|
* `{ key, value }` objects or a functions.
|
|
462
|
-
* @param
|
|
463
|
-
* @returns {module:engine/conversion/downcasthelpers~DowncastHelpers}
|
|
492
|
+
* @param config.converterPriority Converter priority.
|
|
464
493
|
*/
|
|
465
494
|
attributeToAttribute(config) {
|
|
466
495
|
return this.add(downcastAttributeToAttribute(config));
|
|
@@ -478,38 +507,40 @@ export default class DowncastHelpers extends ConversionHelpers {
|
|
|
478
507
|
* is collapsed, only one element is created. For example, a model marker set like this: `<paragraph>F[oo b]ar</paragraph>`
|
|
479
508
|
* becomes `<p>F<span data-marker="search"></span>oo b<span data-marker="search"></span>ar</p>` in the view.
|
|
480
509
|
*
|
|
481
|
-
*
|
|
482
|
-
*
|
|
483
|
-
*
|
|
484
|
-
*
|
|
485
|
-
*
|
|
486
|
-
*
|
|
487
|
-
*
|
|
488
|
-
*
|
|
489
|
-
*
|
|
490
|
-
*
|
|
491
|
-
*
|
|
492
|
-
*
|
|
493
|
-
*
|
|
494
|
-
*
|
|
495
|
-
*
|
|
496
|
-
*
|
|
497
|
-
*
|
|
498
|
-
*
|
|
499
|
-
*
|
|
500
|
-
*
|
|
501
|
-
*
|
|
502
|
-
*
|
|
503
|
-
*
|
|
504
|
-
*
|
|
505
|
-
*
|
|
506
|
-
*
|
|
507
|
-
*
|
|
508
|
-
*
|
|
509
|
-
*
|
|
510
|
-
*
|
|
511
|
-
*
|
|
512
|
-
*
|
|
510
|
+
* ```ts
|
|
511
|
+
* editor.conversion.for( 'editingDowncast' ).markerToElement( {
|
|
512
|
+
* model: 'search',
|
|
513
|
+
* view: 'marker-search'
|
|
514
|
+
* } );
|
|
515
|
+
*
|
|
516
|
+
* editor.conversion.for( 'editingDowncast' ).markerToElement( {
|
|
517
|
+
* model: 'search',
|
|
518
|
+
* view: 'search-result',
|
|
519
|
+
* converterPriority: 'high'
|
|
520
|
+
* } );
|
|
521
|
+
*
|
|
522
|
+
* editor.conversion.for( 'editingDowncast' ).markerToElement( {
|
|
523
|
+
* model: 'search',
|
|
524
|
+
* view: {
|
|
525
|
+
* name: 'span',
|
|
526
|
+
* attributes: {
|
|
527
|
+
* 'data-marker': 'search'
|
|
528
|
+
* }
|
|
529
|
+
* }
|
|
530
|
+
* } );
|
|
531
|
+
*
|
|
532
|
+
* editor.conversion.for( 'editingDowncast' ).markerToElement( {
|
|
533
|
+
* model: 'search',
|
|
534
|
+
* view: ( markerData, conversionApi ) => {
|
|
535
|
+
* const { writer } = conversionApi;
|
|
536
|
+
*
|
|
537
|
+
* return writer.createUIElement( 'span', {
|
|
538
|
+
* 'data-marker': 'search',
|
|
539
|
+
* 'data-start': markerData.isOpening
|
|
540
|
+
* } );
|
|
541
|
+
* }
|
|
542
|
+
* } );
|
|
543
|
+
* ```
|
|
513
544
|
*
|
|
514
545
|
* If a function is passed as the `config.view` parameter, it will be used to generate both boundary elements. The function
|
|
515
546
|
* receives the `data` object and {@link module:engine/conversion/downcastdispatcher~DowncastConversionApi downcast conversion API}
|
|
@@ -523,14 +554,12 @@ export default class DowncastHelpers extends ConversionHelpers {
|
|
|
523
554
|
* See {@link module:engine/conversion/conversion~Conversion#for `conversion.for()`} to learn how to add a converter
|
|
524
555
|
* to the conversion process.
|
|
525
556
|
*
|
|
526
|
-
* @
|
|
527
|
-
* @param
|
|
528
|
-
* @param
|
|
529
|
-
* @
|
|
530
|
-
*
|
|
531
|
-
*
|
|
532
|
-
* @param {module:utils/priorities~PriorityString} [config.converterPriority='normal'] Converter priority.
|
|
533
|
-
* @returns {module:engine/conversion/downcasthelpers~DowncastHelpers}
|
|
557
|
+
* @param config Conversion configuration.
|
|
558
|
+
* @param config.model The name of the model marker (or model marker group) to convert.
|
|
559
|
+
* @param config.view A view element definition or a function that takes the model marker data and
|
|
560
|
+
* {@link module:engine/conversion/downcastdispatcher~DowncastConversionApi downcast conversion API} as a parameters
|
|
561
|
+
* and returns a view UI element.
|
|
562
|
+
* @param config.converterPriority Converter priority.
|
|
534
563
|
*/
|
|
535
564
|
markerToElement(config) {
|
|
536
565
|
return this.add(downcastMarkerToElement(config));
|
|
@@ -554,26 +583,28 @@ export default class DowncastHelpers extends ConversionHelpers {
|
|
|
554
583
|
* to a container element, it is the container element instance itself that applies values from the highlight descriptor.
|
|
555
584
|
* So, in a sense, the converter takes care of stating what should be applied on what, while the element decides how to apply that.
|
|
556
585
|
*
|
|
557
|
-
*
|
|
558
|
-
*
|
|
559
|
-
*
|
|
560
|
-
*
|
|
561
|
-
*
|
|
562
|
-
*
|
|
563
|
-
*
|
|
564
|
-
*
|
|
565
|
-
*
|
|
566
|
-
*
|
|
567
|
-
*
|
|
568
|
-
*
|
|
569
|
-
*
|
|
570
|
-
*
|
|
571
|
-
*
|
|
572
|
-
*
|
|
573
|
-
*
|
|
574
|
-
*
|
|
575
|
-
*
|
|
576
|
-
*
|
|
586
|
+
* ```ts
|
|
587
|
+
* editor.conversion.for( 'downcast' ).markerToHighlight( { model: 'comment', view: { classes: 'comment' } } );
|
|
588
|
+
*
|
|
589
|
+
* editor.conversion.for( 'downcast' ).markerToHighlight( {
|
|
590
|
+
* model: 'comment',
|
|
591
|
+
* view: { classes: 'comment' },
|
|
592
|
+
* converterPriority: 'high'
|
|
593
|
+
* } );
|
|
594
|
+
*
|
|
595
|
+
* editor.conversion.for( 'downcast' ).markerToHighlight( {
|
|
596
|
+
* model: 'comment',
|
|
597
|
+
* view: ( data, conversionApi ) => {
|
|
598
|
+
* // Assuming that the marker name is in a form of comment:commentType:commentId.
|
|
599
|
+
* const [ , commentType, commentId ] = data.markerName.split( ':' );
|
|
600
|
+
*
|
|
601
|
+
* return {
|
|
602
|
+
* classes: [ 'comment', 'comment-' + commentType ],
|
|
603
|
+
* attributes: { 'data-comment-id': commentId }
|
|
604
|
+
* };
|
|
605
|
+
* }
|
|
606
|
+
* } );
|
|
607
|
+
* ```
|
|
577
608
|
*
|
|
578
609
|
* If a function is passed as the `config.view` parameter, it will be used to generate the highlight descriptor. The function
|
|
579
610
|
* receives the `data` object and {@link module:engine/conversion/downcastdispatcher~DowncastConversionApi downcast conversion API}
|
|
@@ -584,15 +615,12 @@ export default class DowncastHelpers extends ConversionHelpers {
|
|
|
584
615
|
* See {@link module:engine/conversion/conversion~Conversion#for `conversion.for()`} to learn how to add a converter
|
|
585
616
|
* to the conversion process.
|
|
586
617
|
*
|
|
587
|
-
* @
|
|
588
|
-
* @param
|
|
589
|
-
* @param
|
|
590
|
-
* @param {module:engine/conversion/downcasthelpers~HighlightDescriptor|Function} config.view A highlight descriptor
|
|
591
|
-
* that will be used for highlighting or a function that takes the model marker data and
|
|
618
|
+
* @param config Conversion configuration.
|
|
619
|
+
* @param config.model The name of the model marker (or model marker group) to convert.
|
|
620
|
+
* @param config.view A highlight descriptor that will be used for highlighting or a function that takes the model marker data and
|
|
592
621
|
* {@link module:engine/conversion/downcastdispatcher~DowncastConversionApi downcast conversion API} as a parameters
|
|
593
622
|
* and returns a highlight descriptor.
|
|
594
|
-
* @param
|
|
595
|
-
* @returns {module:engine/conversion/downcasthelpers~DowncastHelpers}
|
|
623
|
+
* @param config.converterPriority Converter priority.
|
|
596
624
|
*/
|
|
597
625
|
markerToHighlight(config) {
|
|
598
626
|
return this.add(downcastMarkerToHighlight(config));
|
|
@@ -625,87 +653,97 @@ export default class DowncastHelpers extends ConversionHelpers {
|
|
|
625
653
|
*
|
|
626
654
|
* Basic usage:
|
|
627
655
|
*
|
|
628
|
-
*
|
|
629
|
-
*
|
|
630
|
-
*
|
|
631
|
-
*
|
|
632
|
-
*
|
|
633
|
-
*
|
|
634
|
-
*
|
|
656
|
+
* ```ts
|
|
657
|
+
* // Using the default conversion.
|
|
658
|
+
* // In this case, all markers with names starting with 'comment:' will be converted.
|
|
659
|
+
* // The `group` parameter will be set to `comment`.
|
|
660
|
+
* // The `name` parameter will be the rest of the marker name (without the `:`).
|
|
661
|
+
* editor.conversion.for( 'dataDowncast' ).markerToData( {
|
|
662
|
+
* model: 'comment'
|
|
663
|
+
* } );
|
|
664
|
+
* ```
|
|
635
665
|
*
|
|
636
666
|
* An example of a view that may be generated by this conversion (assuming a marker with the name `comment:commentId:uid` marked
|
|
637
667
|
* by `[]`):
|
|
638
668
|
*
|
|
639
|
-
*
|
|
640
|
-
*
|
|
641
|
-
*
|
|
669
|
+
* ```
|
|
670
|
+
* // Model:
|
|
671
|
+
* <paragraph>Foo[bar</paragraph>
|
|
672
|
+
* <imageBlock src="abc.jpg"></imageBlock>]
|
|
642
673
|
*
|
|
643
|
-
*
|
|
644
|
-
*
|
|
645
|
-
*
|
|
674
|
+
* // View:
|
|
675
|
+
* <p>Foo<comment-start name="commentId:uid"></comment-start>bar</p>
|
|
676
|
+
* <figure data-comment-end-after="commentId:uid" class="image"><img src="abc.jpg" /></figure>
|
|
677
|
+
* ```
|
|
646
678
|
*
|
|
647
679
|
* In the example above, the comment starts before "bar" and ends after the image.
|
|
648
680
|
*
|
|
649
681
|
* If the `name` part is empty, the following view may be generated:
|
|
650
682
|
*
|
|
651
|
-
*
|
|
652
|
-
*
|
|
683
|
+
* ```html
|
|
684
|
+
* <p>Foo <myMarker-start></myMarker-start>bar</p>
|
|
685
|
+
* <figure data-myMarker-end-after="" class="image"><img src="abc.jpg" /></figure>
|
|
686
|
+
* ```
|
|
653
687
|
*
|
|
654
688
|
* **Note:** A situation where some markers have the `name` part and some do not, is incorrect and should be avoided.
|
|
655
689
|
*
|
|
656
690
|
* Examples where `data-group-start-after` and `data-group-end-before` are used:
|
|
657
691
|
*
|
|
658
|
-
*
|
|
659
|
-
*
|
|
692
|
+
* ```
|
|
693
|
+
* // Model:
|
|
694
|
+
* <blockQuote>[]<paragraph>Foo</paragraph></blockQuote>
|
|
660
695
|
*
|
|
661
|
-
*
|
|
662
|
-
*
|
|
696
|
+
* // View:
|
|
697
|
+
* <blockquote><p data-group-end-before="name" data-group-start-before="name">Foo</p></blockquote>
|
|
698
|
+
* ```
|
|
663
699
|
*
|
|
664
700
|
* Similarly, when a marker is collapsed after the last element:
|
|
665
701
|
*
|
|
666
|
-
*
|
|
667
|
-
*
|
|
702
|
+
* ```
|
|
703
|
+
* // Model:
|
|
704
|
+
* <blockQuote><paragraph>Foo</paragraph>[]</blockQuote>
|
|
668
705
|
*
|
|
669
|
-
*
|
|
670
|
-
*
|
|
706
|
+
* // View:
|
|
707
|
+
* <blockquote><p data-group-end-after="name" data-group-start-after="name">Foo</p></blockquote>
|
|
708
|
+
* ```
|
|
671
709
|
*
|
|
672
710
|
* When there are multiple markers from the same group stored in the same attribute of the same element, their
|
|
673
711
|
* name parts are put together in the attribute value, for example: `data-group-start-before="name1,name2,name3"`.
|
|
674
712
|
*
|
|
675
713
|
* Other examples of usage:
|
|
676
714
|
*
|
|
677
|
-
*
|
|
678
|
-
*
|
|
679
|
-
*
|
|
680
|
-
*
|
|
681
|
-
*
|
|
682
|
-
*
|
|
683
|
-
*
|
|
684
|
-
*
|
|
685
|
-
*
|
|
686
|
-
*
|
|
687
|
-
*
|
|
688
|
-
*
|
|
689
|
-
*
|
|
690
|
-
*
|
|
691
|
-
*
|
|
692
|
-
*
|
|
693
|
-
*
|
|
694
|
-
*
|
|
715
|
+
* ```ts
|
|
716
|
+
* // Using a custom function which is the same as the default conversion:
|
|
717
|
+
* editor.conversion.for( 'dataDowncast' ).markerToData( {
|
|
718
|
+
* model: 'comment'
|
|
719
|
+
* view: markerName => ( {
|
|
720
|
+
* group: 'comment',
|
|
721
|
+
* name: markerName.substr( 8 ) // Removes 'comment:' part.
|
|
722
|
+
* } )
|
|
723
|
+
* } );
|
|
724
|
+
*
|
|
725
|
+
* // Using the converter priority:
|
|
726
|
+
* editor.conversion.for( 'dataDowncast' ).markerToData( {
|
|
727
|
+
* model: 'comment'
|
|
728
|
+
* view: markerName => ( {
|
|
729
|
+
* group: 'comment',
|
|
730
|
+
* name: markerName.substr( 8 ) // Removes 'comment:' part.
|
|
731
|
+
* } ),
|
|
732
|
+
* converterPriority: 'high'
|
|
733
|
+
* } );
|
|
734
|
+
* ```
|
|
695
735
|
*
|
|
696
736
|
* This kind of conversion is useful for saving data into the database, so it should be used in the data conversion pipeline.
|
|
697
737
|
*
|
|
698
738
|
* See the {@link module:engine/conversion/conversion~Conversion#for `conversion.for()`} API guide to learn how to
|
|
699
739
|
* add a converter to the conversion process.
|
|
700
740
|
*
|
|
701
|
-
* @
|
|
702
|
-
* @param
|
|
703
|
-
* @param
|
|
704
|
-
* @param {Function} [config.view] A function that takes the model marker name and
|
|
741
|
+
* @param config Conversion configuration.
|
|
742
|
+
* @param config.model The name of the model marker (or the model marker group) to convert.
|
|
743
|
+
* @param config.view A function that takes the model marker name and
|
|
705
744
|
* {@link module:engine/conversion/downcastdispatcher~DowncastConversionApi downcast conversion API} as the parameters
|
|
706
745
|
* and returns an object with the `group` and `name` properties.
|
|
707
|
-
* @param
|
|
708
|
-
* @returns {module:engine/conversion/downcasthelpers~DowncastHelpers}
|
|
746
|
+
* @param config.converterPriority Converter priority.
|
|
709
747
|
*/
|
|
710
748
|
markerToData(config) {
|
|
711
749
|
return this.add(downcastMarkerToData(config));
|
|
@@ -717,9 +755,11 @@ export default class DowncastHelpers extends ConversionHelpers {
|
|
|
717
755
|
* The converter automatically consumes the corresponding value from the consumables list and stops the event (see
|
|
718
756
|
* {@link module:engine/conversion/downcastdispatcher~DowncastDispatcher}).
|
|
719
757
|
*
|
|
720
|
-
*
|
|
758
|
+
* ```ts
|
|
759
|
+
* modelDispatcher.on( 'insert:$text', insertText() );
|
|
760
|
+
* ```
|
|
721
761
|
*
|
|
722
|
-
* @returns
|
|
762
|
+
* @returns Insert text event converter.
|
|
723
763
|
*/
|
|
724
764
|
export function insertText() {
|
|
725
765
|
return (evt, data, conversionApi) => {
|
|
@@ -735,7 +775,7 @@ export function insertText() {
|
|
|
735
775
|
/**
|
|
736
776
|
* Function factory that creates a default downcast converter for triggering attributes and children conversion.
|
|
737
777
|
*
|
|
738
|
-
* @returns
|
|
778
|
+
* @returns The converter.
|
|
739
779
|
*/
|
|
740
780
|
export function insertAttributesAndChildren() {
|
|
741
781
|
return (evt, data, conversionApi) => {
|
|
@@ -750,9 +790,11 @@ export function insertAttributesAndChildren() {
|
|
|
750
790
|
/**
|
|
751
791
|
* Function factory that creates a default downcast converter for node remove changes.
|
|
752
792
|
*
|
|
753
|
-
*
|
|
793
|
+
* ```ts
|
|
794
|
+
* modelDispatcher.on( 'remove', remove() );
|
|
795
|
+
* ```
|
|
754
796
|
*
|
|
755
|
-
* @returns
|
|
797
|
+
* @returns Remove event converter.
|
|
756
798
|
*/
|
|
757
799
|
export function remove() {
|
|
758
800
|
return (evt, data, conversionApi) => {
|
|
@@ -774,10 +816,6 @@ export function remove() {
|
|
|
774
816
|
* Creates a `<span>` {@link module:engine/view/attributeelement~AttributeElement view attribute element} from the information
|
|
775
817
|
* provided by the {@link module:engine/conversion/downcasthelpers~HighlightDescriptor highlight descriptor} object. If the priority
|
|
776
818
|
* is not provided in the descriptor, the default priority will be used.
|
|
777
|
-
*
|
|
778
|
-
* @param {module:engine/view/downcastwriter~DowncastWriter} writer
|
|
779
|
-
* @param {module:engine/conversion/downcasthelpers~HighlightDescriptor} descriptor
|
|
780
|
-
* @returns {module:engine/view/attributeelement~AttributeElement}
|
|
781
819
|
*/
|
|
782
820
|
export function createViewElementFromHighlightDescriptor(writer, descriptor) {
|
|
783
821
|
const viewElement = writer.createAttributeElement('span', descriptor.attributes);
|
|
@@ -795,9 +833,11 @@ export function createViewElementFromHighlightDescriptor(writer, descriptor) {
|
|
|
795
833
|
* to a {@link module:engine/view/documentselection~DocumentSelection view selection}. The converter consumes appropriate
|
|
796
834
|
* value from the `consumable` object and maps model positions from the selection to view positions.
|
|
797
835
|
*
|
|
798
|
-
*
|
|
836
|
+
* ```ts
|
|
837
|
+
* modelDispatcher.on( 'selection', convertRangeSelection() );
|
|
838
|
+
* ```
|
|
799
839
|
*
|
|
800
|
-
* @returns
|
|
840
|
+
* @returns Selection converter.
|
|
801
841
|
*/
|
|
802
842
|
export function convertRangeSelection() {
|
|
803
843
|
return (evt, data, conversionApi) => {
|
|
@@ -821,12 +861,16 @@ export function convertRangeSelection() {
|
|
|
821
861
|
* value from the `consumable` object, maps the model selection position to the view position and breaks
|
|
822
862
|
* {@link module:engine/view/attributeelement~AttributeElement attribute elements} at the selection position.
|
|
823
863
|
*
|
|
824
|
-
*
|
|
864
|
+
* ```ts
|
|
865
|
+
* modelDispatcher.on( 'selection', convertCollapsedSelection() );
|
|
866
|
+
* ```
|
|
825
867
|
*
|
|
826
868
|
* An example of the view state before and after converting the collapsed selection:
|
|
827
869
|
*
|
|
828
|
-
*
|
|
829
|
-
*
|
|
870
|
+
* ```
|
|
871
|
+
* <p><strong>f^oo<strong>bar</p>
|
|
872
|
+
* -> <p><strong>f</strong>^<strong>oo</strong>bar</p>
|
|
873
|
+
* ```
|
|
830
874
|
*
|
|
831
875
|
* By breaking attribute elements like `<strong>`, the selection is in a correct element. Then, when the selection attribute is
|
|
832
876
|
* converted, broken attributes might be merged again, or the position where the selection is may be wrapped
|
|
@@ -835,7 +879,7 @@ export function convertRangeSelection() {
|
|
|
835
879
|
* See also {@link module:engine/conversion/downcasthelpers~clearAttributes} which does a clean-up
|
|
836
880
|
* by merging attributes.
|
|
837
881
|
*
|
|
838
|
-
* @returns
|
|
882
|
+
* @returns Selection converter.
|
|
839
883
|
*/
|
|
840
884
|
export function convertCollapsedSelection() {
|
|
841
885
|
return (evt, data, conversionApi) => {
|
|
@@ -859,23 +903,27 @@ export function convertCollapsedSelection() {
|
|
|
859
903
|
* {@link module:engine/view/attributeelement~AttributeElement view attribute elements} and merges sibling attributes at all start and end
|
|
860
904
|
* positions of all ranges.
|
|
861
905
|
*
|
|
862
|
-
*
|
|
863
|
-
*
|
|
906
|
+
* ```
|
|
907
|
+
* <p><strong>^</strong></p>
|
|
908
|
+
* -> <p>^</p>
|
|
864
909
|
*
|
|
865
|
-
*
|
|
866
|
-
*
|
|
910
|
+
* <p><strong>foo</strong>^<strong>bar</strong>bar</p>
|
|
911
|
+
* -> <p><strong>foo^bar<strong>bar</p>
|
|
867
912
|
*
|
|
868
|
-
*
|
|
869
|
-
*
|
|
913
|
+
* <p><strong>foo</strong><em>^</em><strong>bar</strong>bar</p>
|
|
914
|
+
* -> <p><strong>foo^bar<strong>bar</p>
|
|
915
|
+
* ```
|
|
870
916
|
*
|
|
871
917
|
* This listener should be assigned before any converter for the new selection:
|
|
872
918
|
*
|
|
873
|
-
*
|
|
919
|
+
* ```ts
|
|
920
|
+
* modelDispatcher.on( 'selection', clearAttributes() );
|
|
921
|
+
* ```
|
|
874
922
|
*
|
|
875
923
|
* See {@link module:engine/conversion/downcasthelpers~convertCollapsedSelection}
|
|
876
924
|
* which does the opposite by breaking attributes in the selection position.
|
|
877
925
|
*
|
|
878
|
-
* @returns
|
|
926
|
+
* @returns Selection converter.
|
|
879
927
|
*/
|
|
880
928
|
export function clearAttributes() {
|
|
881
929
|
return (evt, data, conversionApi) => {
|
|
@@ -902,10 +950,12 @@ export function clearAttributes() {
|
|
|
902
950
|
* model elements having the given attribute. This is useful for attributes like `bold` that may be set on text nodes in the model
|
|
903
951
|
* but are represented as an element in the view:
|
|
904
952
|
*
|
|
905
|
-
*
|
|
906
|
-
*
|
|
907
|
-
*
|
|
908
|
-
*
|
|
953
|
+
* ```
|
|
954
|
+
* [paragraph] MODEL ====> VIEW <p>
|
|
955
|
+
* |- a {bold: true} |- <b>
|
|
956
|
+
* |- b {bold: true} | |- ab
|
|
957
|
+
* |- c |- c
|
|
958
|
+
* ```
|
|
909
959
|
*
|
|
910
960
|
* Passed `Function` will be provided with the attribute value and then all the parameters of the
|
|
911
961
|
* {@link module:engine/conversion/downcastdispatcher~DowncastDispatcher#event:attribute `attribute` event}.
|
|
@@ -916,13 +966,15 @@ export function clearAttributes() {
|
|
|
916
966
|
* The converter automatically consumes the corresponding value from the consumables list and stops the event (see
|
|
917
967
|
* {@link module:engine/conversion/downcastdispatcher~DowncastDispatcher}).
|
|
918
968
|
*
|
|
919
|
-
*
|
|
920
|
-
*
|
|
921
|
-
*
|
|
969
|
+
* ```ts
|
|
970
|
+
* modelDispatcher.on( 'attribute:bold', wrap( ( modelAttributeValue, { writer } ) => {
|
|
971
|
+
* return writer.createAttributeElement( 'strong' );
|
|
972
|
+
* } );
|
|
973
|
+
* ```
|
|
922
974
|
*
|
|
923
|
-
* @
|
|
924
|
-
* @param
|
|
925
|
-
* @returns
|
|
975
|
+
* @internal
|
|
976
|
+
* @param elementCreator Function returning a view element that will be used for wrapping.
|
|
977
|
+
* @returns Set/change attribute converter.
|
|
926
978
|
*/
|
|
927
979
|
export function wrap(elementCreator) {
|
|
928
980
|
return (evt, data, conversionApi) => {
|
|
@@ -966,23 +1018,25 @@ export function wrap(elementCreator) {
|
|
|
966
1018
|
*
|
|
967
1019
|
* The converter automatically consumes the corresponding value from the consumables list and binds the model and view elements.
|
|
968
1020
|
*
|
|
969
|
-
*
|
|
970
|
-
*
|
|
971
|
-
*
|
|
972
|
-
*
|
|
973
|
-
*
|
|
1021
|
+
* ```ts
|
|
1022
|
+
* downcastDispatcher.on(
|
|
1023
|
+
* 'insert:myElem',
|
|
1024
|
+
* insertElement( ( modelItem, { writer } ) => {
|
|
1025
|
+
* const text = writer.createText( 'myText' );
|
|
1026
|
+
* const myElem = writer.createElement( 'myElem', { myAttr: 'my-' + modelItem.getAttribute( 'myAttr' ) }, text );
|
|
974
1027
|
*
|
|
975
|
-
*
|
|
1028
|
+
* // Do something fancy with `myElem` using `modelItem` or other parameters.
|
|
976
1029
|
*
|
|
977
|
-
*
|
|
978
|
-
*
|
|
979
|
-
*
|
|
1030
|
+
* return myElem;
|
|
1031
|
+
* }
|
|
1032
|
+
* ) );
|
|
1033
|
+
* ```
|
|
980
1034
|
*
|
|
981
|
-
* @
|
|
982
|
-
* @param
|
|
983
|
-
* @param
|
|
1035
|
+
* @internal
|
|
1036
|
+
* @param elementCreator Function returning a view element, which will be inserted.
|
|
1037
|
+
* @param consumer Function defining element consumption process.
|
|
984
1038
|
* By default this function just consume passed item insertion.
|
|
985
|
-
* @returns
|
|
1039
|
+
* @returns Insert element event converter.
|
|
986
1040
|
*/
|
|
987
1041
|
export function insertElement(elementCreator, consumer = defaultConsumer) {
|
|
988
1042
|
return (evt, data, conversionApi) => {
|
|
@@ -1012,12 +1066,11 @@ export function insertElement(elementCreator, consumer = defaultConsumer) {
|
|
|
1012
1066
|
*
|
|
1013
1067
|
* @see module:engine/conversion/downcasthelpers~DowncastHelpers#elementToStructure
|
|
1014
1068
|
*
|
|
1015
|
-
* @
|
|
1016
|
-
* @param
|
|
1017
|
-
*
|
|
1018
|
-
* @param {module:engine/conversion/downcasthelpers~ConsumerFunction} consumer A callback that is expected to consume all the consumables
|
|
1069
|
+
* @internal
|
|
1070
|
+
* @param elementCreator Function returning a view structure, which will be inserted.
|
|
1071
|
+
* @param consumer A callback that is expected to consume all the consumables
|
|
1019
1072
|
* that were used by the element creator.
|
|
1020
|
-
* @returns
|
|
1073
|
+
* @returns Insert element event converter.
|
|
1021
1074
|
*/
|
|
1022
1075
|
export function insertStructure(elementCreator, consumer) {
|
|
1023
1076
|
return (evt, data, conversionApi) => {
|
|
@@ -1055,10 +1108,9 @@ export function insertStructure(elementCreator, consumer) {
|
|
|
1055
1108
|
*
|
|
1056
1109
|
* This converter binds created UI elements with the marker name using {@link module:engine/conversion/mapper~Mapper#bindElementToMarker}.
|
|
1057
1110
|
*
|
|
1058
|
-
* @
|
|
1059
|
-
* @param
|
|
1060
|
-
*
|
|
1061
|
-
* @returns {Function} Insert element event converter.
|
|
1111
|
+
* @internal
|
|
1112
|
+
* @param elementCreator A view UI element or a function returning the view element that will be inserted.
|
|
1113
|
+
* @returns Insert element event converter.
|
|
1062
1114
|
*/
|
|
1063
1115
|
export function insertUIElement(elementCreator) {
|
|
1064
1116
|
return (evt, data, conversionApi) => {
|
|
@@ -1097,12 +1149,14 @@ export function insertUIElement(elementCreator) {
|
|
|
1097
1149
|
evt.stop();
|
|
1098
1150
|
};
|
|
1099
1151
|
}
|
|
1100
|
-
|
|
1101
|
-
|
|
1102
|
-
|
|
1103
|
-
|
|
1104
|
-
|
|
1105
|
-
|
|
1152
|
+
/**
|
|
1153
|
+
* Function factory that returns a default downcast converter for removing a {@link module:engine/view/uielement~UIElement UI element}
|
|
1154
|
+
* based on marker remove change.
|
|
1155
|
+
*
|
|
1156
|
+
* This converter unbinds elements from the marker name.
|
|
1157
|
+
*
|
|
1158
|
+
* @returns Removed UI element converter.
|
|
1159
|
+
*/
|
|
1106
1160
|
function removeUIElement() {
|
|
1107
1161
|
return (evt, data, conversionApi) => {
|
|
1108
1162
|
const elements = conversionApi.mapper.markerNameToElements(data.markerName);
|
|
@@ -1117,14 +1171,16 @@ function removeUIElement() {
|
|
|
1117
1171
|
evt.stop();
|
|
1118
1172
|
};
|
|
1119
1173
|
}
|
|
1120
|
-
|
|
1121
|
-
|
|
1122
|
-
|
|
1123
|
-
|
|
1124
|
-
|
|
1125
|
-
|
|
1126
|
-
|
|
1127
|
-
|
|
1174
|
+
/**
|
|
1175
|
+
* Function factory that creates a default converter for model markers.
|
|
1176
|
+
*
|
|
1177
|
+
* See {@link DowncastHelpers#markerToData} for more information what type of view is generated.
|
|
1178
|
+
*
|
|
1179
|
+
* This converter binds created UI elements and affected view elements with the marker name
|
|
1180
|
+
* using {@link module:engine/conversion/mapper~Mapper#bindElementToMarker}.
|
|
1181
|
+
*
|
|
1182
|
+
* @returns Add marker converter.
|
|
1183
|
+
*/
|
|
1128
1184
|
function insertMarkerData(viewCreator) {
|
|
1129
1185
|
return (evt, data, conversionApi) => {
|
|
1130
1186
|
const viewMarkerData = viewCreator(data.markerName, conversionApi);
|
|
@@ -1141,7 +1197,9 @@ function insertMarkerData(viewCreator) {
|
|
|
1141
1197
|
evt.stop();
|
|
1142
1198
|
};
|
|
1143
1199
|
}
|
|
1144
|
-
|
|
1200
|
+
/**
|
|
1201
|
+
* Helper function for `insertMarkerData()` that marks a marker boundary at the beginning or end of given `range`.
|
|
1202
|
+
*/
|
|
1145
1203
|
function handleMarkerBoundary(range, isStart, conversionApi, data, viewMarkerData) {
|
|
1146
1204
|
const modelPosition = isStart ? range.start : range.end;
|
|
1147
1205
|
const elementAfter = modelPosition.nodeAfter && modelPosition.nodeAfter.is('element') ? modelPosition.nodeAfter : null;
|
|
@@ -1173,7 +1231,9 @@ function handleMarkerBoundary(range, isStart, conversionApi, data, viewMarkerDat
|
|
|
1173
1231
|
const viewPosition = conversionApi.mapper.toViewPosition(modelPosition);
|
|
1174
1232
|
insertMarkerAsElement(viewPosition, isStart, conversionApi, data, viewMarkerData);
|
|
1175
1233
|
}
|
|
1176
|
-
|
|
1234
|
+
/**
|
|
1235
|
+
* Helper function for `insertMarkerData()` that marks a marker boundary in the view as an attribute on a view element.
|
|
1236
|
+
*/
|
|
1177
1237
|
function insertMarkerAsAttribute(viewElement, isStart, isBefore, conversionApi, data, viewMarkerData) {
|
|
1178
1238
|
const attributeName = `data-${viewMarkerData.group}-${isStart ? 'start' : 'end'}-${isBefore ? 'before' : 'after'}`;
|
|
1179
1239
|
const markerNames = viewElement.hasAttribute(attributeName) ? viewElement.getAttribute(attributeName).split(',') : [];
|
|
@@ -1182,7 +1242,9 @@ function insertMarkerAsAttribute(viewElement, isStart, isBefore, conversionApi,
|
|
|
1182
1242
|
conversionApi.writer.setAttribute(attributeName, markerNames.join(','), viewElement);
|
|
1183
1243
|
conversionApi.mapper.bindElementToMarker(viewElement, data.markerName);
|
|
1184
1244
|
}
|
|
1185
|
-
|
|
1245
|
+
/**
|
|
1246
|
+
* Helper function for `insertMarkerData()` that marks a marker boundary in the view as a separate view ui element.
|
|
1247
|
+
*/
|
|
1186
1248
|
function insertMarkerAsElement(position, isStart, conversionApi, data, viewMarkerData) {
|
|
1187
1249
|
const viewElementName = `${viewMarkerData.group}-${isStart ? 'start' : 'end'}`;
|
|
1188
1250
|
const attrs = viewMarkerData.name ? { 'name': viewMarkerData.name } : null;
|
|
@@ -1190,9 +1252,11 @@ function insertMarkerAsElement(position, isStart, conversionApi, data, viewMarke
|
|
|
1190
1252
|
conversionApi.writer.insert(position, viewElement);
|
|
1191
1253
|
conversionApi.mapper.bindElementToMarker(viewElement, data.markerName);
|
|
1192
1254
|
}
|
|
1193
|
-
|
|
1194
|
-
|
|
1195
|
-
|
|
1255
|
+
/**
|
|
1256
|
+
* Function factory that creates a converter for removing a model marker data added by the {@link #insertMarkerData} converter.
|
|
1257
|
+
*
|
|
1258
|
+
* @returns Remove marker converter.
|
|
1259
|
+
*/
|
|
1196
1260
|
function removeMarkerData(viewCreator) {
|
|
1197
1261
|
return (evt, data, conversionApi) => {
|
|
1198
1262
|
const viewData = viewCreator(data.markerName, conversionApi);
|
|
@@ -1231,35 +1295,39 @@ function removeMarkerData(viewCreator) {
|
|
|
1231
1295
|
}
|
|
1232
1296
|
};
|
|
1233
1297
|
}
|
|
1234
|
-
|
|
1235
|
-
|
|
1236
|
-
|
|
1237
|
-
|
|
1238
|
-
|
|
1239
|
-
|
|
1240
|
-
|
|
1241
|
-
|
|
1242
|
-
|
|
1243
|
-
|
|
1244
|
-
|
|
1245
|
-
|
|
1246
|
-
|
|
1247
|
-
|
|
1248
|
-
//
|
|
1249
|
-
|
|
1250
|
-
|
|
1251
|
-
|
|
1252
|
-
//
|
|
1253
|
-
|
|
1254
|
-
|
|
1255
|
-
|
|
1256
|
-
|
|
1257
|
-
//
|
|
1258
|
-
|
|
1259
|
-
|
|
1260
|
-
|
|
1261
|
-
|
|
1262
|
-
|
|
1298
|
+
/**
|
|
1299
|
+
* Function factory that creates a converter which converts the set/change/remove attribute changes from the model to the view.
|
|
1300
|
+
*
|
|
1301
|
+
* Attributes from the model are converted to the view element attributes in the view. You may provide a custom function to generate
|
|
1302
|
+
* a key-value attribute pair to add/change/remove. If not provided, model attributes will be converted to view element
|
|
1303
|
+
* attributes on a one-to-one basis.
|
|
1304
|
+
*
|
|
1305
|
+
* *Note:** The provided attribute creator should always return the same `key` for a given attribute from the model.
|
|
1306
|
+
*
|
|
1307
|
+
* The converter automatically consumes the corresponding value from the consumables list and stops the event (see
|
|
1308
|
+
* {@link module:engine/conversion/downcastdispatcher~DowncastDispatcher}).
|
|
1309
|
+
*
|
|
1310
|
+
* ```ts
|
|
1311
|
+
* modelDispatcher.on( 'attribute:customAttr:myElem', changeAttribute( ( value, data ) => {
|
|
1312
|
+
* // Change attribute key from `customAttr` to `class` in the view.
|
|
1313
|
+
* const key = 'class';
|
|
1314
|
+
* let value = data.attributeNewValue;
|
|
1315
|
+
*
|
|
1316
|
+
* // Force attribute value to 'empty' if the model element is empty.
|
|
1317
|
+
* if ( data.item.childCount === 0 ) {
|
|
1318
|
+
* value = 'empty';
|
|
1319
|
+
* }
|
|
1320
|
+
*
|
|
1321
|
+
* // Return the key-value pair.
|
|
1322
|
+
* return { key, value };
|
|
1323
|
+
* } ) );
|
|
1324
|
+
* ```
|
|
1325
|
+
*
|
|
1326
|
+
* @param attributeCreator Function returning an object with two properties: `key` and `value`, which
|
|
1327
|
+
* represent the attribute key and attribute value to be set on a {@link module:engine/view/element~Element view element}.
|
|
1328
|
+
* The function is passed the model attribute value as the first parameter and additional data about the change as the second parameter.
|
|
1329
|
+
* @returns Set/change attribute converter.
|
|
1330
|
+
*/
|
|
1263
1331
|
function changeAttribute(attributeCreator) {
|
|
1264
1332
|
return (evt, data, conversionApi) => {
|
|
1265
1333
|
if (!conversionApi.consumable.test(data.item, evt.name)) {
|
|
@@ -1281,32 +1349,38 @@ function changeAttribute(attributeCreator) {
|
|
|
1281
1349
|
* by an {@link module:engine/conversion/conversion~Conversion#attributeToAttribute `Attribute to Attribute converter`}.
|
|
1282
1350
|
* In most cases it is caused by converters misconfiguration when only "generic" converter is defined:
|
|
1283
1351
|
*
|
|
1284
|
-
*
|
|
1285
|
-
*
|
|
1286
|
-
*
|
|
1287
|
-
*
|
|
1352
|
+
* ```ts
|
|
1353
|
+
* editor.conversion.for( 'downcast' ).attributeToAttribute( {
|
|
1354
|
+
* model: 'attribute-name',
|
|
1355
|
+
* view: 'attribute-name'
|
|
1356
|
+
* } ) );
|
|
1357
|
+
* ```
|
|
1288
1358
|
*
|
|
1289
1359
|
* and given attribute is used on text node, for example:
|
|
1290
1360
|
*
|
|
1291
|
-
*
|
|
1292
|
-
*
|
|
1293
|
-
*
|
|
1361
|
+
* ```ts
|
|
1362
|
+
* model.change( writer => {
|
|
1363
|
+
* writer.insertText( 'Foo', { 'attribute-name': 'bar' }, parent, 0 );
|
|
1364
|
+
* } );
|
|
1365
|
+
* ```
|
|
1294
1366
|
*
|
|
1295
1367
|
* In such cases, to convert the same attribute for both {@link module:engine/model/element~Element}
|
|
1296
1368
|
* and {@link module:engine/model/textproxy~TextProxy `Text`} nodes, text specific
|
|
1297
1369
|
* {@link module:engine/conversion/conversion~Conversion#attributeToElement `Attribute to Element converter`}
|
|
1298
1370
|
* with higher {@link module:utils/priorities~PriorityString priority} must also be defined:
|
|
1299
1371
|
*
|
|
1300
|
-
*
|
|
1301
|
-
*
|
|
1302
|
-
*
|
|
1303
|
-
*
|
|
1304
|
-
*
|
|
1305
|
-
*
|
|
1306
|
-
*
|
|
1307
|
-
*
|
|
1308
|
-
*
|
|
1309
|
-
*
|
|
1372
|
+
* ```ts
|
|
1373
|
+
* editor.conversion.for( 'downcast' ).attributeToElement( {
|
|
1374
|
+
* model: {
|
|
1375
|
+
* key: 'attribute-name',
|
|
1376
|
+
* name: '$text'
|
|
1377
|
+
* },
|
|
1378
|
+
* view: ( value, { writer } ) => {
|
|
1379
|
+
* return writer.createAttributeElement( 'span', { 'attribute-name': value } );
|
|
1380
|
+
* },
|
|
1381
|
+
* converterPriority: 'high'
|
|
1382
|
+
* } ) );
|
|
1383
|
+
* ```
|
|
1310
1384
|
*
|
|
1311
1385
|
* @error conversion-attribute-to-attribute-on-text
|
|
1312
1386
|
*/
|
|
@@ -1350,22 +1424,21 @@ function changeAttribute(attributeCreator) {
|
|
|
1350
1424
|
}
|
|
1351
1425
|
};
|
|
1352
1426
|
}
|
|
1353
|
-
|
|
1354
|
-
|
|
1355
|
-
|
|
1356
|
-
|
|
1357
|
-
|
|
1358
|
-
|
|
1359
|
-
|
|
1360
|
-
|
|
1361
|
-
|
|
1362
|
-
|
|
1363
|
-
|
|
1364
|
-
|
|
1365
|
-
|
|
1366
|
-
|
|
1367
|
-
|
|
1368
|
-
// @returns {Function}
|
|
1427
|
+
/**
|
|
1428
|
+
* Function factory that creates a converter which converts the text inside marker's range. The converter wraps the text with
|
|
1429
|
+
* {@link module:engine/view/attributeelement~AttributeElement} created from the provided descriptor.
|
|
1430
|
+
* See {link module:engine/conversion/downcasthelpers~createViewElementFromHighlightDescriptor}.
|
|
1431
|
+
*
|
|
1432
|
+
* It can also be used to convert the selection that is inside a marker. In that case, an empty attribute element will be
|
|
1433
|
+
* created and the selection will be put inside it.
|
|
1434
|
+
*
|
|
1435
|
+
* If the highlight descriptor does not provide the `priority` property, `10` will be used.
|
|
1436
|
+
*
|
|
1437
|
+
* If the highlight descriptor does not provide the `id` property, the name of the marker will be used.
|
|
1438
|
+
*
|
|
1439
|
+
* This converter binds the created {@link module:engine/view/attributeelement~AttributeElement attribute elemens} with the marker name
|
|
1440
|
+
* using the {@link module:engine/conversion/mapper~Mapper#bindElementToMarker} method.
|
|
1441
|
+
*/
|
|
1369
1442
|
function highlightText(highlightDescriptor) {
|
|
1370
1443
|
return (evt, data, conversionApi) => {
|
|
1371
1444
|
if (!data.item) {
|
|
@@ -1401,24 +1474,23 @@ function highlightText(highlightDescriptor) {
|
|
|
1401
1474
|
}
|
|
1402
1475
|
};
|
|
1403
1476
|
}
|
|
1404
|
-
|
|
1405
|
-
|
|
1406
|
-
|
|
1407
|
-
|
|
1408
|
-
|
|
1409
|
-
|
|
1410
|
-
|
|
1411
|
-
|
|
1412
|
-
|
|
1413
|
-
|
|
1414
|
-
|
|
1415
|
-
|
|
1416
|
-
|
|
1417
|
-
|
|
1418
|
-
|
|
1419
|
-
|
|
1420
|
-
|
|
1421
|
-
// @returns {Function}
|
|
1477
|
+
/**
|
|
1478
|
+
* Converter function factory. It creates a function which applies the marker's highlight to an element inside the marker's range.
|
|
1479
|
+
*
|
|
1480
|
+
* The converter checks if an element has the `addHighlight` function stored as a
|
|
1481
|
+
* {@link module:engine/view/element~Element#_setCustomProperty custom property} and, if so, uses it to apply the highlight.
|
|
1482
|
+
* In such case the converter will consume all element's children, assuming that they were handled by the element itself.
|
|
1483
|
+
*
|
|
1484
|
+
* When the `addHighlight` custom property is not present, the element is not converted in any special way.
|
|
1485
|
+
* This means that converters will proceed to convert the element's child nodes.
|
|
1486
|
+
*
|
|
1487
|
+
* If the highlight descriptor does not provide the `priority` property, `10` will be used.
|
|
1488
|
+
*
|
|
1489
|
+
* If the highlight descriptor does not provide the `id` property, the name of the marker will be used.
|
|
1490
|
+
*
|
|
1491
|
+
* This converter binds altered {@link module:engine/view/containerelement~ContainerElement container elements} with the marker name using
|
|
1492
|
+
* the {@link module:engine/conversion/mapper~Mapper#bindElementToMarker} method.
|
|
1493
|
+
*/
|
|
1422
1494
|
function highlightElement(highlightDescriptor) {
|
|
1423
1495
|
return (evt, data, conversionApi) => {
|
|
1424
1496
|
if (!data.item) {
|
|
@@ -1448,28 +1520,27 @@ function highlightElement(highlightDescriptor) {
|
|
|
1448
1520
|
}
|
|
1449
1521
|
};
|
|
1450
1522
|
}
|
|
1451
|
-
|
|
1452
|
-
|
|
1453
|
-
|
|
1454
|
-
|
|
1455
|
-
|
|
1456
|
-
|
|
1457
|
-
|
|
1458
|
-
|
|
1459
|
-
|
|
1460
|
-
|
|
1461
|
-
|
|
1462
|
-
|
|
1463
|
-
|
|
1464
|
-
|
|
1465
|
-
|
|
1466
|
-
|
|
1467
|
-
|
|
1468
|
-
|
|
1469
|
-
|
|
1470
|
-
|
|
1471
|
-
|
|
1472
|
-
// @returns {Function}
|
|
1523
|
+
/**
|
|
1524
|
+
* Function factory that creates a converter which converts the removing model marker to the view.
|
|
1525
|
+
*
|
|
1526
|
+
* Both text nodes and elements are handled by this converter but they are handled a bit differently.
|
|
1527
|
+
*
|
|
1528
|
+
* Text nodes are unwrapped using the {@link module:engine/view/attributeelement~AttributeElement attribute element} created from the
|
|
1529
|
+
* provided highlight descriptor. See {link module:engine/conversion/downcasthelpers~HighlightDescriptor}.
|
|
1530
|
+
*
|
|
1531
|
+
* For elements, the converter checks if an element has the `removeHighlight` function stored as a
|
|
1532
|
+
* {@link module:engine/view/element~Element#_setCustomProperty custom property}. If so, it uses it to remove the highlight.
|
|
1533
|
+
* In such case, the children of that element will not be converted.
|
|
1534
|
+
*
|
|
1535
|
+
* When `removeHighlight` is not present, the element is not converted in any special way.
|
|
1536
|
+
* The converter will proceed to convert the element's child nodes instead.
|
|
1537
|
+
*
|
|
1538
|
+
* If the highlight descriptor does not provide the `priority` property, `10` will be used.
|
|
1539
|
+
*
|
|
1540
|
+
* If the highlight descriptor does not provide the `id` property, the name of the marker will be used.
|
|
1541
|
+
*
|
|
1542
|
+
* This converter unbinds elements from the marker name.
|
|
1543
|
+
*/
|
|
1473
1544
|
function removeHighlight(highlightDescriptor) {
|
|
1474
1545
|
return (evt, data, conversionApi) => {
|
|
1475
1546
|
// This conversion makes sense only for non-collapsed range.
|
|
@@ -1502,17 +1573,17 @@ function removeHighlight(highlightDescriptor) {
|
|
|
1502
1573
|
evt.stop();
|
|
1503
1574
|
};
|
|
1504
1575
|
}
|
|
1505
|
-
|
|
1506
|
-
|
|
1507
|
-
|
|
1508
|
-
|
|
1509
|
-
|
|
1510
|
-
|
|
1511
|
-
|
|
1512
|
-
|
|
1513
|
-
|
|
1514
|
-
|
|
1515
|
-
|
|
1576
|
+
/**
|
|
1577
|
+
* Model element to view element conversion helper.
|
|
1578
|
+
*
|
|
1579
|
+
* See {@link ~DowncastHelpers#elementToElement `.elementToElement()` downcast helper} for examples and config params description.
|
|
1580
|
+
*
|
|
1581
|
+
* @param config Conversion configuration.
|
|
1582
|
+
* @param config.model The description or a name of the model element to convert.
|
|
1583
|
+
* @param config.model.attributes List of attributes triggering element reconversion.
|
|
1584
|
+
* @param config.model.children Should reconvert element if the list of model child nodes changed.
|
|
1585
|
+
* @returns Conversion helper.
|
|
1586
|
+
*/
|
|
1516
1587
|
function downcastElementToElement(config) {
|
|
1517
1588
|
const model = normalizeModelElementConfig(config.model);
|
|
1518
1589
|
const view = normalizeToElementConfig(config.view, 'container');
|
|
@@ -1528,16 +1599,14 @@ function downcastElementToElement(config) {
|
|
|
1528
1599
|
}
|
|
1529
1600
|
};
|
|
1530
1601
|
}
|
|
1531
|
-
|
|
1532
|
-
|
|
1533
|
-
|
|
1534
|
-
|
|
1535
|
-
|
|
1536
|
-
|
|
1537
|
-
|
|
1538
|
-
|
|
1539
|
-
// @param {module:engine/conversion/downcasthelpers~StructureCreatorFunction} config.view
|
|
1540
|
-
// @returns {Function} Conversion helper.
|
|
1602
|
+
/**
|
|
1603
|
+
* Model element to view structure conversion helper.
|
|
1604
|
+
*
|
|
1605
|
+
* See {@link ~DowncastHelpers#elementToStructure `.elementToStructure()` downcast helper} for examples and config params description.
|
|
1606
|
+
*
|
|
1607
|
+
* @param config Conversion configuration.
|
|
1608
|
+
* @returns Conversion helper.
|
|
1609
|
+
*/
|
|
1541
1610
|
function downcastElementToStructure(config) {
|
|
1542
1611
|
const model = normalizeModelElementConfig(config.model);
|
|
1543
1612
|
const view = normalizeToElementConfig(config.view, 'container');
|
|
@@ -1552,34 +1621,38 @@ function downcastElementToStructure(config) {
|
|
|
1552
1621
|
* allowed to host `$text` by the {@link module:engine/model/schema~Schema model schema}.
|
|
1553
1622
|
*
|
|
1554
1623
|
* For instance, this may be the result of `myElement` allowing the content of
|
|
1555
|
-
* {@glink framework/
|
|
1624
|
+
* {@glink framework/deep-dive/schema#generic-items `$block`} in its schema definition:
|
|
1556
1625
|
*
|
|
1557
|
-
*
|
|
1558
|
-
*
|
|
1559
|
-
*
|
|
1626
|
+
* ```ts
|
|
1627
|
+
* // Element definition in schema.
|
|
1628
|
+
* schema.register( 'myElement', {
|
|
1629
|
+
* allowContentOf: '$block',
|
|
1560
1630
|
*
|
|
1561
|
-
*
|
|
1562
|
-
*
|
|
1631
|
+
* // ...
|
|
1632
|
+
* } );
|
|
1563
1633
|
*
|
|
1564
|
-
*
|
|
1634
|
+
* // ...
|
|
1565
1635
|
*
|
|
1566
|
-
*
|
|
1567
|
-
*
|
|
1568
|
-
*
|
|
1569
|
-
*
|
|
1570
|
-
*
|
|
1571
|
-
*
|
|
1572
|
-
*
|
|
1636
|
+
* // Conversion of myElement with the use of elementToStructure().
|
|
1637
|
+
* editor.conversion.for( 'downcast' ).elementToStructure( {
|
|
1638
|
+
* model: 'myElement',
|
|
1639
|
+
* view: ( modelElement, { writer } ) => {
|
|
1640
|
+
* // ...
|
|
1641
|
+
* }
|
|
1642
|
+
* } );
|
|
1643
|
+
* ```
|
|
1573
1644
|
*
|
|
1574
1645
|
* In such case, {@link module:engine/conversion/downcasthelpers~DowncastHelpers#elementToElement `elementToElement()`} helper
|
|
1575
1646
|
* can be used instead to get around this problem:
|
|
1576
1647
|
*
|
|
1577
|
-
*
|
|
1578
|
-
*
|
|
1579
|
-
*
|
|
1580
|
-
*
|
|
1581
|
-
*
|
|
1582
|
-
*
|
|
1648
|
+
* ```ts
|
|
1649
|
+
* editor.conversion.for( 'downcast' ).elementToElement( {
|
|
1650
|
+
* model: 'myElement',
|
|
1651
|
+
* view: ( modelElement, { writer } ) => {
|
|
1652
|
+
* // ...
|
|
1653
|
+
* }
|
|
1654
|
+
* } );
|
|
1655
|
+
* ```
|
|
1583
1656
|
*
|
|
1584
1657
|
* @error conversion-element-to-structure-disallowed-text
|
|
1585
1658
|
* @param {String} elementName The name of the element the structure is to be created for.
|
|
@@ -1590,20 +1663,21 @@ function downcastElementToStructure(config) {
|
|
|
1590
1663
|
dispatcher.on('reduceChanges', createChangeReducer(model), { priority: 'low' });
|
|
1591
1664
|
};
|
|
1592
1665
|
}
|
|
1593
|
-
|
|
1594
|
-
|
|
1595
|
-
|
|
1596
|
-
|
|
1597
|
-
|
|
1598
|
-
|
|
1599
|
-
|
|
1600
|
-
|
|
1601
|
-
|
|
1602
|
-
|
|
1603
|
-
|
|
1604
|
-
|
|
1605
|
-
|
|
1606
|
-
|
|
1666
|
+
/**
|
|
1667
|
+
* Model attribute to view element conversion helper.
|
|
1668
|
+
*
|
|
1669
|
+
* See {@link ~DowncastHelpers#attributeToElement `.attributeToElement()` downcast helper} for examples.
|
|
1670
|
+
*
|
|
1671
|
+
* @param config Conversion configuration.
|
|
1672
|
+
* @param config.model The key of the attribute to convert from or a `{ key, values }` object. `values` is an array
|
|
1673
|
+
* of `String`s with possible values if the model attribute is an enumerable.
|
|
1674
|
+
* @param config.view A view element definition or a function that takes the model attribute value and
|
|
1675
|
+
* {@link module:engine/view/downcastwriter~DowncastWriter view downcast writer} as parameters and returns a view attribute element.
|
|
1676
|
+
* If `config.model.values` is given, `config.view` should be an object assigning values from `config.model.values` to view element
|
|
1677
|
+
* definitions or functions.
|
|
1678
|
+
* @param config.converterPriority Converter priority.
|
|
1679
|
+
* @returns Conversion helper.
|
|
1680
|
+
*/
|
|
1607
1681
|
function downcastAttributeToElement(config) {
|
|
1608
1682
|
config = cloneDeep(config);
|
|
1609
1683
|
let model = config.model;
|
|
@@ -1627,21 +1701,23 @@ function downcastAttributeToElement(config) {
|
|
|
1627
1701
|
dispatcher.on(eventName, wrap(elementCreator), { priority: config.converterPriority || 'normal' });
|
|
1628
1702
|
};
|
|
1629
1703
|
}
|
|
1630
|
-
|
|
1631
|
-
|
|
1632
|
-
|
|
1633
|
-
|
|
1634
|
-
|
|
1635
|
-
|
|
1636
|
-
|
|
1637
|
-
|
|
1638
|
-
|
|
1639
|
-
|
|
1640
|
-
|
|
1641
|
-
|
|
1642
|
-
|
|
1643
|
-
|
|
1644
|
-
|
|
1704
|
+
/**
|
|
1705
|
+
* Model attribute to view attribute conversion helper.
|
|
1706
|
+
*
|
|
1707
|
+
* See {@link ~DowncastHelpers#attributeToAttribute `.attributeToAttribute()` downcast helper} for examples.
|
|
1708
|
+
*
|
|
1709
|
+
* @param config Conversion configuration.
|
|
1710
|
+
* @param config.model The key of the attribute to convert from or a `{ key, values, [ name ] }` object describing
|
|
1711
|
+
* the attribute key, possible values and, optionally, an element name to convert from.
|
|
1712
|
+
* @param config.view A view attribute key, or a `{ key, value }` object or a function that takes the model attribute value and returns
|
|
1713
|
+
* a `{ key, value }` object.
|
|
1714
|
+
* If `key` is `'class'`, `value` can be a `String` or an array of `String`s. If `key` is `'style'`, `value` is an object with
|
|
1715
|
+
* key-value pairs. In other cases, `value` is a `String`.
|
|
1716
|
+
* If `config.model.values` is set, `config.view` should be an object assigning values from `config.model.values` to
|
|
1717
|
+
* `{ key, value }` objects or a functions.
|
|
1718
|
+
* @param config.converterPriority Converter priority.
|
|
1719
|
+
* @returns Conversion helper.
|
|
1720
|
+
*/
|
|
1645
1721
|
function downcastAttributeToAttribute(config) {
|
|
1646
1722
|
config = cloneDeep(config);
|
|
1647
1723
|
let model = config.model;
|
|
@@ -1665,16 +1741,17 @@ function downcastAttributeToAttribute(config) {
|
|
|
1665
1741
|
dispatcher.on(eventName, changeAttribute(elementCreator), { priority: config.converterPriority || 'normal' });
|
|
1666
1742
|
};
|
|
1667
1743
|
}
|
|
1668
|
-
|
|
1669
|
-
|
|
1670
|
-
|
|
1671
|
-
|
|
1672
|
-
|
|
1673
|
-
|
|
1674
|
-
|
|
1675
|
-
|
|
1676
|
-
|
|
1677
|
-
|
|
1744
|
+
/**
|
|
1745
|
+
* Model marker to view element conversion helper.
|
|
1746
|
+
*
|
|
1747
|
+
* See {@link ~DowncastHelpers#markerToElement `.markerToElement()` downcast helper} for examples.
|
|
1748
|
+
*
|
|
1749
|
+
* @param config Conversion configuration.
|
|
1750
|
+
* @param config.model The name of the model marker (or model marker group) to convert.
|
|
1751
|
+
* @param config.view A view element definition or a function that takes the model marker data as a parameter and returns a view UI element.
|
|
1752
|
+
* @param config.converterPriority Converter priority.
|
|
1753
|
+
* @returns Conversion helper.
|
|
1754
|
+
*/
|
|
1678
1755
|
function downcastMarkerToElement(config) {
|
|
1679
1756
|
const view = normalizeToElementConfig(config.view, 'ui');
|
|
1680
1757
|
return (dispatcher) => {
|
|
@@ -1682,15 +1759,13 @@ function downcastMarkerToElement(config) {
|
|
|
1682
1759
|
dispatcher.on(`removeMarker:${config.model}`, removeUIElement(), { priority: config.converterPriority || 'normal' });
|
|
1683
1760
|
};
|
|
1684
1761
|
}
|
|
1685
|
-
|
|
1686
|
-
|
|
1687
|
-
|
|
1688
|
-
|
|
1689
|
-
|
|
1690
|
-
|
|
1691
|
-
|
|
1692
|
-
// @param {module:utils/priorities~PriorityString} [config.converterPriority='normal']
|
|
1693
|
-
// @returns {Function} Conversion helper.
|
|
1762
|
+
/**
|
|
1763
|
+
* Model marker to view data conversion helper.
|
|
1764
|
+
*
|
|
1765
|
+
* See {@link ~DowncastHelpers#markerToData `markerToData()` downcast helper} to learn more.
|
|
1766
|
+
*
|
|
1767
|
+
* @returns Conversion helper.
|
|
1768
|
+
*/
|
|
1694
1769
|
function downcastMarkerToData(config) {
|
|
1695
1770
|
config = cloneDeep(config);
|
|
1696
1771
|
const group = config.model;
|
|
@@ -1707,16 +1782,18 @@ function downcastMarkerToData(config) {
|
|
|
1707
1782
|
dispatcher.on(`removeMarker:${group}`, removeMarkerData(view), { priority: config.converterPriority || 'normal' });
|
|
1708
1783
|
};
|
|
1709
1784
|
}
|
|
1710
|
-
|
|
1711
|
-
|
|
1712
|
-
|
|
1713
|
-
|
|
1714
|
-
|
|
1715
|
-
|
|
1716
|
-
|
|
1717
|
-
|
|
1718
|
-
|
|
1719
|
-
|
|
1785
|
+
/**
|
|
1786
|
+
* Model marker to highlight conversion helper.
|
|
1787
|
+
*
|
|
1788
|
+
* See {@link ~DowncastHelpers#markerToElement `.markerToElement()` downcast helper} for examples.
|
|
1789
|
+
*
|
|
1790
|
+
* @param config Conversion configuration.
|
|
1791
|
+
* @param config.model The name of the model marker (or model marker group) to convert.
|
|
1792
|
+
* @param config.view A highlight descriptor that will be used for highlighting or a function that takes
|
|
1793
|
+
* the model marker data as a parameter and returns a highlight descriptor.
|
|
1794
|
+
* @param config.converterPriority Converter priority.
|
|
1795
|
+
* @returns Conversion helper.
|
|
1796
|
+
*/
|
|
1720
1797
|
function downcastMarkerToHighlight(config) {
|
|
1721
1798
|
return (dispatcher) => {
|
|
1722
1799
|
dispatcher.on(`addMarker:${config.model}`, highlightText(config.view), { priority: config.converterPriority || 'normal' });
|
|
@@ -1724,13 +1801,11 @@ function downcastMarkerToHighlight(config) {
|
|
|
1724
1801
|
dispatcher.on(`removeMarker:${config.model}`, removeHighlight(config.view), { priority: config.converterPriority || 'normal' });
|
|
1725
1802
|
};
|
|
1726
1803
|
}
|
|
1727
|
-
|
|
1728
|
-
|
|
1729
|
-
|
|
1730
|
-
|
|
1731
|
-
|
|
1732
|
-
// @param {Boolean} [model.children]
|
|
1733
|
-
// @returns {Object}
|
|
1804
|
+
/**
|
|
1805
|
+
* Takes `config.model`, and converts it to an object with normalized structure.
|
|
1806
|
+
*
|
|
1807
|
+
* @param model Model configuration or element name.
|
|
1808
|
+
*/
|
|
1734
1809
|
function normalizeModelElementConfig(model) {
|
|
1735
1810
|
if (typeof model == 'string') {
|
|
1736
1811
|
model = { name: model };
|
|
@@ -1746,12 +1821,14 @@ function normalizeModelElementConfig(model) {
|
|
|
1746
1821
|
model.children = !!model.children;
|
|
1747
1822
|
return model;
|
|
1748
1823
|
}
|
|
1749
|
-
|
|
1750
|
-
|
|
1751
|
-
|
|
1752
|
-
|
|
1753
|
-
|
|
1754
|
-
|
|
1824
|
+
/**
|
|
1825
|
+
* Takes `config.view`, and if it is an {@link module:engine/view/elementdefinition~ElementDefinition}, converts it
|
|
1826
|
+
* to a function (because lower level converters accept only element creator functions).
|
|
1827
|
+
*
|
|
1828
|
+
* @param view View configuration.
|
|
1829
|
+
* @param viewElementType View element type to create.
|
|
1830
|
+
* @returns Element creator function to use in lower level converters.
|
|
1831
|
+
*/
|
|
1755
1832
|
function normalizeToElementConfig(view, viewElementType) {
|
|
1756
1833
|
if (typeof view == 'function') {
|
|
1757
1834
|
// If `view` is already a function, don't do anything.
|
|
@@ -1759,12 +1836,9 @@ function normalizeToElementConfig(view, viewElementType) {
|
|
|
1759
1836
|
}
|
|
1760
1837
|
return ((modelData, conversionApi) => createViewElementFromDefinition(view, conversionApi, viewElementType));
|
|
1761
1838
|
}
|
|
1762
|
-
|
|
1763
|
-
|
|
1764
|
-
|
|
1765
|
-
// @param {module:engine/view/downcastwriter~DowncastWriter} viewWriter
|
|
1766
|
-
// @param {'container'|'attribute'|'ui'} viewElementType
|
|
1767
|
-
// @returns {module:engine/view/element~Element}
|
|
1839
|
+
/**
|
|
1840
|
+
* Creates a view element instance from the provided {@link module:engine/view/elementdefinition~ElementDefinition} and class.
|
|
1841
|
+
*/
|
|
1768
1842
|
function createViewElementFromDefinition(viewElementDefinition, conversionApi, viewElementType) {
|
|
1769
1843
|
if (typeof viewElementDefinition == 'string') {
|
|
1770
1844
|
// If `viewElementDefinition` is given as a `String`, normalize it to an object with `name` property.
|
|
@@ -1819,10 +1893,12 @@ function getFromAttributeCreator(config) {
|
|
|
1819
1893
|
return config.view;
|
|
1820
1894
|
}
|
|
1821
1895
|
}
|
|
1822
|
-
|
|
1823
|
-
|
|
1824
|
-
|
|
1825
|
-
|
|
1896
|
+
/**
|
|
1897
|
+
* Takes the configuration, adds default parameters if they do not exist and normalizes other parameters to be used in downcast converters
|
|
1898
|
+
* for generating a view attribute.
|
|
1899
|
+
*
|
|
1900
|
+
* @param view View configuration.
|
|
1901
|
+
*/
|
|
1826
1902
|
function normalizeToAttributeConfig(view) {
|
|
1827
1903
|
if (typeof view == 'string') {
|
|
1828
1904
|
return modelAttributeValue => ({ key: view, value: modelAttributeValue });
|
|
@@ -1842,7 +1918,9 @@ function normalizeToAttributeConfig(view) {
|
|
|
1842
1918
|
return view;
|
|
1843
1919
|
}
|
|
1844
1920
|
}
|
|
1845
|
-
|
|
1921
|
+
/**
|
|
1922
|
+
* Helper function for `highlight`. Prepares the actual descriptor object using value passed to the converter.
|
|
1923
|
+
*/
|
|
1846
1924
|
function prepareDescriptor(highlightDescriptor, data, conversionApi) {
|
|
1847
1925
|
// If passed descriptor is a creator function, call it. If not, just use passed value.
|
|
1848
1926
|
const descriptor = typeof highlightDescriptor == 'function' ?
|
|
@@ -1861,13 +1939,14 @@ function prepareDescriptor(highlightDescriptor, data, conversionApi) {
|
|
|
1861
1939
|
}
|
|
1862
1940
|
return descriptor;
|
|
1863
1941
|
}
|
|
1864
|
-
|
|
1865
|
-
|
|
1866
|
-
|
|
1867
|
-
|
|
1868
|
-
|
|
1869
|
-
|
|
1870
|
-
|
|
1942
|
+
/**
|
|
1943
|
+
* Creates a function that checks a single differ diff item whether it should trigger reconversion.
|
|
1944
|
+
*
|
|
1945
|
+
* @param model A normalized `config.model` converter configuration.
|
|
1946
|
+
* @param model.name The name of element.
|
|
1947
|
+
* @param model.attributes The list of attribute names that should trigger reconversion.
|
|
1948
|
+
* @param model.children Whether the child list change should trigger reconversion.
|
|
1949
|
+
*/
|
|
1871
1950
|
function createChangeReducerCallback(model) {
|
|
1872
1951
|
return (node, change) => {
|
|
1873
1952
|
if (!node.is('element', model.name)) {
|
|
@@ -1887,13 +1966,14 @@ function createChangeReducerCallback(model) {
|
|
|
1887
1966
|
return false;
|
|
1888
1967
|
};
|
|
1889
1968
|
}
|
|
1890
|
-
|
|
1891
|
-
|
|
1892
|
-
|
|
1893
|
-
|
|
1894
|
-
|
|
1895
|
-
|
|
1896
|
-
|
|
1969
|
+
/**
|
|
1970
|
+
* Creates a `reduceChanges` event handler for reconversion.
|
|
1971
|
+
*
|
|
1972
|
+
* @param model A normalized `config.model` converter configuration.
|
|
1973
|
+
* @param model.name The name of element.
|
|
1974
|
+
* @param model.attributes The list of attribute names that should trigger reconversion.
|
|
1975
|
+
* @param model.children Whether the child list change should trigger reconversion.
|
|
1976
|
+
*/
|
|
1897
1977
|
function createChangeReducer(model) {
|
|
1898
1978
|
const shouldReplace = createChangeReducerCallback(model);
|
|
1899
1979
|
return (evt, data) => {
|
|
@@ -1913,7 +1993,20 @@ function createChangeReducer(model) {
|
|
|
1913
1993
|
if (!data.reconvertedElements.has(node)) {
|
|
1914
1994
|
data.reconvertedElements.add(node);
|
|
1915
1995
|
const position = ModelPosition._createBefore(node);
|
|
1916
|
-
reducedChanges.
|
|
1996
|
+
let changeIndex = reducedChanges.length;
|
|
1997
|
+
// We need to insert remove+reinsert before any other change on and inside the re-converted element.
|
|
1998
|
+
// This is important because otherwise we would remove element that had already been modified by the previous change.
|
|
1999
|
+
// Note that there could be some element removed before the re-converted element, so we must not break this behavior.
|
|
2000
|
+
for (let i = reducedChanges.length - 1; i >= 0; i--) {
|
|
2001
|
+
const change = reducedChanges[i];
|
|
2002
|
+
const changePosition = change.type == 'attribute' ? change.range.start : change.position;
|
|
2003
|
+
const positionRelation = changePosition.compareWith(position);
|
|
2004
|
+
if (positionRelation == 'before' || change.type == 'remove' && positionRelation == 'same') {
|
|
2005
|
+
break;
|
|
2006
|
+
}
|
|
2007
|
+
changeIndex = i;
|
|
2008
|
+
}
|
|
2009
|
+
reducedChanges.splice(changeIndex, 0, {
|
|
1917
2010
|
type: 'remove',
|
|
1918
2011
|
name: node.name,
|
|
1919
2012
|
position,
|
|
@@ -1929,13 +2022,14 @@ function createChangeReducer(model) {
|
|
|
1929
2022
|
data.changes = reducedChanges;
|
|
1930
2023
|
};
|
|
1931
2024
|
}
|
|
1932
|
-
|
|
1933
|
-
|
|
1934
|
-
|
|
1935
|
-
|
|
1936
|
-
|
|
1937
|
-
|
|
1938
|
-
|
|
2025
|
+
/**
|
|
2026
|
+
* Creates a function that checks if an element and its watched attributes can be consumed and consumes them.
|
|
2027
|
+
*
|
|
2028
|
+
* @param model A normalized `config.model` converter configuration.
|
|
2029
|
+
* @param model.name The name of element.
|
|
2030
|
+
* @param model.attributes The list of attribute names that should trigger reconversion.
|
|
2031
|
+
* @param model.children Whether the child list change should trigger reconversion.
|
|
2032
|
+
*/
|
|
1939
2033
|
function createConsumer(model) {
|
|
1940
2034
|
return (node, consumable, options = {}) => {
|
|
1941
2035
|
const events = ['insert'];
|
|
@@ -1954,14 +2048,13 @@ function createConsumer(model) {
|
|
|
1954
2048
|
return true;
|
|
1955
2049
|
};
|
|
1956
2050
|
}
|
|
1957
|
-
|
|
1958
|
-
|
|
1959
|
-
|
|
1960
|
-
|
|
1961
|
-
|
|
1962
|
-
// @returns {Function} Exposed by writer as createSlot().
|
|
2051
|
+
/**
|
|
2052
|
+
* Creates a function that create view slots.
|
|
2053
|
+
*
|
|
2054
|
+
* @returns Function exposed by writer as createSlot().
|
|
2055
|
+
*/
|
|
1963
2056
|
function createSlotFactory(element, slotsMap, conversionApi) {
|
|
1964
|
-
return (writer, modeOrFilter
|
|
2057
|
+
return (writer, modeOrFilter) => {
|
|
1965
2058
|
const slot = writer.createContainerElement('$slot');
|
|
1966
2059
|
let children = null;
|
|
1967
2060
|
if (modeOrFilter === 'children') {
|
|
@@ -1982,11 +2075,9 @@ function createSlotFactory(element, slotsMap, conversionApi) {
|
|
|
1982
2075
|
return slot;
|
|
1983
2076
|
};
|
|
1984
2077
|
}
|
|
1985
|
-
|
|
1986
|
-
|
|
1987
|
-
|
|
1988
|
-
// @param {Map.<module:engine/view/element~Element,Array.<module:engine/model/node~Node>>} slotsMap
|
|
1989
|
-
// @param {module:engine/conversion/downcastdispatcher~DowncastConversionApi} conversionApi
|
|
2078
|
+
/**
|
|
2079
|
+
* Checks if all children are covered by slots and there is no child that landed in multiple slots.
|
|
2080
|
+
*/
|
|
1990
2081
|
function validateSlotsChildren(element, slotsMap, conversionApi) {
|
|
1991
2082
|
const childrenInSlots = Array.from(slotsMap.values()).flat();
|
|
1992
2083
|
const uniqueChildrenInSlots = new Set(childrenInSlots);
|
|
@@ -2012,13 +2103,9 @@ function validateSlotsChildren(element, slotsMap, conversionApi) {
|
|
|
2012
2103
|
throw new CKEditorError('conversion-slot-filter-incomplete', conversionApi.dispatcher, { element });
|
|
2013
2104
|
}
|
|
2014
2105
|
}
|
|
2015
|
-
|
|
2016
|
-
|
|
2017
|
-
|
|
2018
|
-
// @param {Map.<module:engine/view/element~Element,Array.<module:engine/model/node~Node>>} slotsMap
|
|
2019
|
-
// @param {module:engine/conversion/downcastdispatcher~DowncastConversionApi} conversionApi
|
|
2020
|
-
// @param {Object} options
|
|
2021
|
-
// @param {Boolean} [options.reconversion]
|
|
2106
|
+
/**
|
|
2107
|
+
* Fill slots with appropriate view elements.
|
|
2108
|
+
*/
|
|
2022
2109
|
function fillSlots(viewElement, slotsMap, conversionApi, options) {
|
|
2023
2110
|
// Set temporary position mapping to redirect child view elements into a proper slots.
|
|
2024
2111
|
conversionApi.mapper.on('modelToViewPosition', toViewPositionMapping, { priority: 'highest' });
|
|
@@ -2041,14 +2128,10 @@ function fillSlots(viewElement, slotsMap, conversionApi, options) {
|
|
|
2041
2128
|
data.viewPosition = data.mapper.findPositionIn(currentSlot, index);
|
|
2042
2129
|
}
|
|
2043
2130
|
}
|
|
2044
|
-
|
|
2045
|
-
|
|
2046
|
-
|
|
2047
|
-
|
|
2048
|
-
// @param {Iterable.<module:engine/model/element~Element>} modelNodes
|
|
2049
|
-
// @param {module:engine/conversion/downcastdispatcher~DowncastConversionApi} conversionApi
|
|
2050
|
-
// @param {Object} options
|
|
2051
|
-
// @param {Boolean} [options.reconversion]
|
|
2131
|
+
/**
|
|
2132
|
+
* Inserts view representation of `nodes` into the `viewElement` either by bringing back just removed view nodes
|
|
2133
|
+
* or by triggering conversion for them.
|
|
2134
|
+
*/
|
|
2052
2135
|
function reinsertOrConvertNodes(viewElement, modelNodes, conversionApi, options) {
|
|
2053
2136
|
// Fill with nested view nodes.
|
|
2054
2137
|
for (const modelChildNode of modelNodes) {
|
|
@@ -2059,14 +2142,11 @@ function reinsertOrConvertNodes(viewElement, modelNodes, conversionApi, options)
|
|
|
2059
2142
|
}
|
|
2060
2143
|
}
|
|
2061
2144
|
}
|
|
2062
|
-
|
|
2063
|
-
|
|
2064
|
-
|
|
2065
|
-
|
|
2066
|
-
|
|
2067
|
-
// @param {Object} options
|
|
2068
|
-
// @param {Boolean} [options.reconversion]
|
|
2069
|
-
// @returns {Boolean} `false` if view element can't be reused.
|
|
2145
|
+
/**
|
|
2146
|
+
* Checks if the view for the given model element could be reused and reinserts it to the view.
|
|
2147
|
+
*
|
|
2148
|
+
* @returns `false` if view element can't be reused.
|
|
2149
|
+
*/
|
|
2070
2150
|
function reinsertNode(viewRoot, modelNode, conversionApi, options) {
|
|
2071
2151
|
const { writer, mapper } = conversionApi;
|
|
2072
2152
|
// Don't reinsert if this is not a reconversion...
|
|
@@ -2086,12 +2166,13 @@ function reinsertNode(viewRoot, modelNode, conversionApi, options) {
|
|
|
2086
2166
|
writer.move(writer.createRangeOn(viewChildNode), mapper.toViewPosition(ModelPosition._createBefore(modelNode)));
|
|
2087
2167
|
return true;
|
|
2088
2168
|
}
|
|
2089
|
-
|
|
2090
|
-
|
|
2091
|
-
|
|
2092
|
-
|
|
2093
|
-
|
|
2094
|
-
|
|
2169
|
+
/**
|
|
2170
|
+
* The default consumer for insert events.
|
|
2171
|
+
*
|
|
2172
|
+
* @param item Model item.
|
|
2173
|
+
* @param consumable The model consumable.
|
|
2174
|
+
* @param options.preflight Whether should consume or just check if can be consumed.
|
|
2175
|
+
*/
|
|
2095
2176
|
function defaultConsumer(item, consumable, { preflight } = {}) {
|
|
2096
2177
|
if (preflight) {
|
|
2097
2178
|
return consumable.test(item, 'insert');
|