From 09acfe949892abaa9e6161518553fb39ed148f2a Mon Sep 17 00:00:00 2001 From: Kamil Piechaczek Date: Thu, 30 Jan 2020 09:11:53 +0100 Subject: [PATCH 01/34] Added "#document" property to "view.Node" (and inherited classes) and "view.DocumentFragment". --- src/dev-utils/view.js | 11 ++++++++--- src/view/attributeelement.js | 9 +++++++-- src/view/containerelement.js | 9 +++++++-- src/view/documentfragment.js | 18 +++++++++++++----- src/view/domconverter.js | 9 ++++++--- src/view/downcastwriter.js | 14 +++++++------- src/view/element.js | 5 +++-- src/view/emptyelement.js | 9 ++++++--- src/view/node.js | 27 ++++++++++++++++++--------- src/view/text.js | 7 ++++--- src/view/uielement.js | 9 ++++++--- tests/view/downcastwriter/insert.js | 1 + 12 files changed, 86 insertions(+), 42 deletions(-) diff --git a/src/dev-utils/view.js b/src/dev-utils/view.js index 89a6c40c6..4cbeddb8a 100644 --- a/src/dev-utils/view.js +++ b/src/dev-utils/view.js @@ -471,7 +471,9 @@ class RangeParser { } text = text.replace( regexp, '' ); + node._data = text; + const index = node.index; const parent = node.parent; @@ -927,7 +929,10 @@ class ViewStringify { function _convertViewElements( rootNode ) { if ( rootNode.is( 'element' ) || rootNode.is( 'documentFragment' ) ) { // Convert element or leave document fragment. - const convertedElement = rootNode.is( 'documentFragment' ) ? new ViewDocumentFragment() : _convertElement( rootNode ); + + const convertedElement = rootNode.is( 'documentFragment' ) ? + new ViewDocumentFragment( rootNode.document ) : + _convertElement( rootNode.document, rootNode ); // Convert all child nodes. // Cache the nodes in array. Otherwise, we would skip some nodes because during iteration we move nodes @@ -973,10 +978,10 @@ function _convertViewElements( rootNode ) { // module:engine/view/emptyelement~EmptyElement|module:engine/view/uielement~UIElement| // module:engine/view/containerelement~ContainerElement} A tree view // element converted according to its name. -function _convertElement( viewElement ) { +function _convertElement( viewDocument, viewElement ) { const info = _convertElementNameAndInfo( viewElement ); const ElementConstructor = allowedTypes[ info.type ]; - const newElement = ElementConstructor ? new ElementConstructor( info.name ) : new ViewElement( info.name ); + const newElement = ElementConstructor ? new ElementConstructor( viewDocument, info.name ) : new ViewElement( viewDocument, info.name ); if ( newElement.is( 'attributeElement' ) ) { if ( info.priority !== null ) { diff --git a/src/view/attributeelement.js b/src/view/attributeelement.js index a63c3e56c..52e981f11 100644 --- a/src/view/attributeelement.js +++ b/src/view/attributeelement.js @@ -33,9 +33,14 @@ export default class AttributeElement extends Element { * @see module:engine/view/downcastwriter~DowncastWriter#createAttributeElement * @see module:engine/view/element~Element * @protected + * @param {module:engine/view/document~Document} document A document where the element belongs to. + * @param {String} name Node name. + * @param {Object|Iterable} [attrs] Collection of attributes. + * @param {module:engine/view/node~Node|Iterable.} [children] + * A list of nodes to be inserted into created element. */ - constructor( name, attrs, children ) { - super( name, attrs, children ); + constructor( document, name, attrs, children ) { + super( document, name, attrs, children ); /** * Returns block {@link module:engine/view/filler filler} offset or `null` if block filler is not needed. diff --git a/src/view/containerelement.js b/src/view/containerelement.js index d06a4e0c2..ab501d0a9 100644 --- a/src/view/containerelement.js +++ b/src/view/containerelement.js @@ -37,9 +37,14 @@ export default class ContainerElement extends Element { * @see module:engine/view/downcastwriter~DowncastWriter#createContainerElement * @see module:engine/view/element~Element * @protected + * @param {module:engine/view/document~Document} document A document where the element belongs to. + * @param {String} name Node name. + * @param {Object|Iterable} [attrs] Collection of attributes. + * @param {module:engine/view/node~Node|Iterable.} [children] + * A list of nodes to be inserted into created element. */ - constructor( name, attrs, children ) { - super( name, attrs, children ); + constructor( document, name, attrs, children ) { + super( document, name, attrs, children ); /** * Returns block {@link module:engine/view/filler filler} offset or `null` if block filler is not needed. diff --git a/src/view/documentfragment.js b/src/view/documentfragment.js index ae55450d6..effc215cd 100644 --- a/src/view/documentfragment.js +++ b/src/view/documentfragment.js @@ -25,10 +25,18 @@ export default class DocumentFragment { * Creates new DocumentFragment instance. * * @protected + * @param {module:engine/view/document~Document} document A document where the document fragment belongs to. * @param {module:engine/view/node~Node|Iterable.} [children] * A list of nodes to be inserted into the created document fragment. */ - constructor( children ) { + constructor( document, children ) { + /** + * A document where the document fragment belongs to. + * + * @member {module:engine/view/document~Document} + */ + this.document = document; + /** * Array of child nodes. * @@ -164,7 +172,7 @@ export default class DocumentFragment { this._fireChange( 'children', this ); let count = 0; - const nodes = normalize( items ); + const nodes = normalize( this.document, items ); for ( const node of nodes ) { // If node that is being added to this element is already inside another element, first remove it from the old parent. @@ -238,7 +246,7 @@ mix( DocumentFragment, EmitterMixin ); // // @param {String|module:engine/view/item~Item|Iterable.} // @returns {Iterable.} -function normalize( nodes ) { +function normalize( document, nodes ) { // Separate condition because string is iterable. if ( typeof nodes == 'string' ) { return [ new Text( nodes ) ]; @@ -252,11 +260,11 @@ function normalize( nodes ) { return Array.from( nodes ) .map( node => { if ( typeof node == 'string' ) { - return new Text( node ); + return new Text( document, node ); } if ( node instanceof TextProxy ) { - return new Text( node.data ); + return new Text( document, node.data ); } return node; diff --git a/src/view/domconverter.js b/src/view/domconverter.js index d71d0ef78..6d92db3cd 100644 --- a/src/view/domconverter.js +++ b/src/view/domconverter.js @@ -14,6 +14,7 @@ import ViewElement from './element'; import ViewPosition from './position'; import ViewRange from './range'; import ViewSelection from './selection'; +import ViewDocument from './document'; import ViewDocumentFragment from './documentfragment'; import ViewTreeWalker from './treewalker'; import { BR_FILLER, getDataWithoutFiller, INLINE_FILLER_LENGTH, isInlineFiller, NBSP_FILLER, startsWithFiller } from './filler'; @@ -386,6 +387,8 @@ export default class DomConverter { return null; } + const viewDocument = new ViewDocument(); + // When node is inside UIElement return that UIElement as it's view representation. const uiElement = this.getParentUIElement( domNode, this._domToViewMapping ); @@ -399,7 +402,7 @@ export default class DomConverter { } else { const textData = this._processDataFromDomText( domNode ); - return textData === '' ? null : new ViewText( textData ); + return textData === '' ? null : new ViewText( viewDocument, textData ); } } else if ( this.isComment( domNode ) ) { return null; @@ -412,7 +415,7 @@ export default class DomConverter { if ( this.isDocumentFragment( domNode ) ) { // Create view document fragment. - viewElement = new ViewDocumentFragment(); + viewElement = new ViewDocumentFragment( viewDocument ); if ( options.bind ) { this.bindDocumentFragments( domNode, viewElement ); @@ -420,7 +423,7 @@ export default class DomConverter { } else { // Create view element. const viewName = options.keepOriginalCase ? domNode.tagName : domNode.tagName.toLowerCase(); - viewElement = new ViewElement( viewName ); + viewElement = new ViewElement( viewDocument, viewName ); if ( options.bind ) { this.bindElements( domNode, viewElement ); diff --git a/src/view/downcastwriter.js b/src/view/downcastwriter.js index c6bd7916f..0ad0e84ac 100644 --- a/src/view/downcastwriter.js +++ b/src/view/downcastwriter.js @@ -145,7 +145,7 @@ export default class DowncastWriter { * @returns {module:engine/view/text~Text} The created text node. */ createText( data ) { - return new Text( data ); + return new Text( this.document, data ); } /** @@ -168,7 +168,7 @@ export default class DowncastWriter { * @returns {module:engine/view/attributeelement~AttributeElement} Created element. */ createAttributeElement( name, attributes, options = {} ) { - const attributeElement = new AttributeElement( name, attributes ); + const attributeElement = new AttributeElement( this.document, name, attributes ); if ( options.priority ) { attributeElement._priority = options.priority; @@ -200,7 +200,7 @@ export default class DowncastWriter { * @returns {module:engine/view/containerelement~ContainerElement} Created element. */ createContainerElement( name, attributes ) { - return new ContainerElement( name, attributes ); + return new ContainerElement( this.document, name, attributes ); } /** @@ -214,7 +214,7 @@ export default class DowncastWriter { * @returns {module:engine/view/editableelement~EditableElement} Created element. */ createEditableElement( name, attributes ) { - const editableElement = new EditableElement( name, attributes ); + const editableElement = new EditableElement( this.document, name, attributes ); editableElement._document = this.document; return editableElement; @@ -231,7 +231,7 @@ export default class DowncastWriter { * @returns {module:engine/view/emptyelement~EmptyElement} Created element. */ createEmptyElement( name, attributes ) { - return new EmptyElement( name, attributes ); + return new EmptyElement( this.document, name, attributes ); } /** @@ -255,7 +255,7 @@ export default class DowncastWriter { * @returns {module:engine/view/uielement~UIElement} Created element. */ createUIElement( name, attributes, renderFunction ) { - const uiElement = new UIElement( name, attributes ); + const uiElement = new UIElement( this.document, name, attributes ); if ( renderFunction ) { uiElement.render = renderFunction; @@ -1807,7 +1807,7 @@ function breakTextNode( position ) { position.parent._data = position.parent.data.slice( 0, position.offset ); // Insert new text node after position's parent text node. - position.parent.parent._insertChild( position.parent.index + 1, new Text( textToMove ) ); + position.parent.parent._insertChild( position.parent.index + 1, new Text( position.parent.document, textToMove ) ); // Return new position between two newly created text nodes. return new Position( position.parent.parent, position.parent.index + 1 ); diff --git a/src/view/element.js b/src/view/element.js index be74c983b..097886e38 100644 --- a/src/view/element.js +++ b/src/view/element.js @@ -53,13 +53,14 @@ export default class Element extends Node { * new Element( 'div', mapOfAttributes ); // map * * @protected + * @param {module:engine/view/document~Document} document A document where the element belongs to. * @param {String} name Node name. * @param {Object|Iterable} [attrs] Collection of attributes. * @param {module:engine/view/node~Node|Iterable.} [children] * A list of nodes to be inserted into created element. */ - constructor( name, attrs, children ) { - super(); + constructor( document, name, attrs, children ) { + super( document ); /** * Name of the element. diff --git a/src/view/emptyelement.js b/src/view/emptyelement.js index 2d8d4ea9b..b6af5ae99 100644 --- a/src/view/emptyelement.js +++ b/src/view/emptyelement.js @@ -28,11 +28,14 @@ export default class EmptyElement extends Element { * * @see module:engine/view/downcastwriter~DowncastWriter#createEmptyElement * @protected + * @param {module:engine/view/document~Document} document A document where the element belongs to. * @param {String} name Node name. - * @param {Object|Iterable} [attributes] Collection of attributes. + * @param {Object|Iterable} [attrs] Collection of attributes. + * @param {module:engine/view/node~Node|Iterable.} [children] + * A list of nodes to be inserted into created element. */ - constructor( name, attributes, children ) { - super( name, attributes, children ); + constructor( document, name, attrs, children ) { + super( document, name, attrs, children ); /** * Returns `null` because filler is not needed for EmptyElements. diff --git a/src/view/node.js b/src/view/node.js index 1e109df4c..788f6a9a3 100644 --- a/src/view/node.js +++ b/src/view/node.js @@ -28,8 +28,17 @@ import '@ckeditor/ckeditor5-utils/src/version'; export default class Node { /** * Creates a tree view node. + * + * @param {module:engine/view/document~Document} document A document where the node belongs to. */ - constructor() { + constructor( document ) { + /** + * A document where the node belongs to. + * + * @member {module:engine/view/document~Document} + */ + this.document = document; + /** * Parent element. Null by default. Set by {@link module:engine/view/element~Element#_insertChild}. * @@ -115,14 +124,14 @@ export default class Node { * @readonly * @type {module:engine/view/document~Document|null} */ - get document() { - // Parent might be Node, null or DocumentFragment. - if ( this.parent instanceof Node ) { - return this.parent.document; - } else { - return null; - } - } + // get document() { + // // Parent might be Node, null or DocumentFragment. + // if ( this.parent instanceof Node ) { + // return this.parent.document; + // } else { + // return null; + // } + // } /** * Gets a path to the node. The path is an array containing indices of consecutive ancestors of this node, diff --git a/src/view/text.js b/src/view/text.js index f0c5a85e5..86b4ab3c7 100644 --- a/src/view/text.js +++ b/src/view/text.js @@ -25,10 +25,11 @@ export default class Text extends Node { * Creates a tree view text node. * * @protected + * @param {module:engine/view/document~Document} document A document where the text belongs to. * @param {String} data The text's data. */ - constructor( data ) { - super(); + constructor( document, data ) { + super( document ); /** * The text content. @@ -125,7 +126,7 @@ export default class Text extends Node { * @returns {module:engine/view/text~Text} Text node that is a clone of this node. */ _clone() { - return new Text( this.data ); + return new Text( this.document, this.data ); } // @if CK_DEBUG_ENGINE // toString() { diff --git a/src/view/uielement.js b/src/view/uielement.js index 3cae1c14d..fd5ee27c3 100644 --- a/src/view/uielement.js +++ b/src/view/uielement.js @@ -41,11 +41,14 @@ export default class UIElement extends Element { * * @see module:engine/view/downcastwriter~DowncastWriter#createUIElement * @protected + * @param {module:engine/view/document~Document} document A document where the element belongs to. * @param {String} name Node name. - * @param {Object|Iterable} [attributes] Collection of attributes. + * @param {Object|Iterable} [attrs] Collection of attributes. + * @param {module:engine/view/node~Node|Iterable.} [children] + * A list of nodes to be inserted into created element. */ - constructor( name, attributes, children ) { - super( name, attributes, children ); + constructor( document, name, attrs, children ) { + super( document, name, attrs, children ); /** * Returns `null` because filler is not needed for UIElements. diff --git a/tests/view/downcastwriter/insert.js b/tests/view/downcastwriter/insert.js index d50df6cd1..707ddfe96 100644 --- a/tests/view/downcastwriter/insert.js +++ b/tests/view/downcastwriter/insert.js @@ -29,6 +29,7 @@ describe( 'DowncastWriter', () => { const { view, selection } = parse( input ); const newRange = writer.insert( selection.getFirstPosition(), nodesToInsert ); + expect( stringify( view.root, newRange, { showType: true, showPriority: true } ) ).to.equal( expected ); } From 3ffb904bc7711dc93196afc83d4c1bbda86acb5c Mon Sep 17 00:00:00 2001 From: Kamil Piechaczek Date: Mon, 3 Feb 2020 09:31:13 +0100 Subject: [PATCH 02/34] Corrected view.DowncastWriter() tests. --- tests/view/downcastwriter/breakattributes.js | 26 ++++++++-------- tests/view/downcastwriter/breakcontainer.js | 7 +++-- tests/view/downcastwriter/clear.js | 30 +++++++++--------- tests/view/downcastwriter/insert.js | 26 ++++++++-------- tests/view/downcastwriter/mergeattributes.js | 11 ++++--- tests/view/downcastwriter/move.js | 31 ++++++++++--------- tests/view/downcastwriter/remove.js | 22 +++++++------- tests/view/downcastwriter/unwrap.js | 26 ++++++++-------- tests/view/downcastwriter/wrap.js | 32 ++++++++++---------- 9 files changed, 107 insertions(+), 104 deletions(-) diff --git a/tests/view/downcastwriter/breakattributes.js b/tests/view/downcastwriter/breakattributes.js index 7dca60459..ef9bcaf04 100644 --- a/tests/view/downcastwriter/breakattributes.js +++ b/tests/view/downcastwriter/breakattributes.js @@ -152,8 +152,8 @@ describe( 'DowncastWriter', () => { } it( 'should throw when range placed in two containers', () => { - const p1 = new ContainerElement( 'p' ); - const p2 = new ContainerElement( 'p' ); + const p1 = new ContainerElement( document, 'p' ); + const p2 = new ContainerElement( document, 'p' ); expectToThrowCKEditorError( () => { writer.breakAttributes( Range._createFromParentsAndOffsets( p1, 0, p2, 0 ) ); @@ -161,7 +161,7 @@ describe( 'DowncastWriter', () => { } ); it( 'should throw when range has no parent container', () => { - const el = new AttributeElement( 'b' ); + const el = new AttributeElement( document, 'b' ); expectToThrowCKEditorError( () => { writer.breakAttributes( Range._createFromParentsAndOffsets( el, 0, el, 0 ) ); @@ -241,8 +241,8 @@ describe( 'DowncastWriter', () => { } ); it( 'should throw if breaking inside EmptyElement #1', () => { - const img = new EmptyElement( 'img' ); - new ContainerElement( 'p', null, img ); // eslint-disable-line no-new + const img = new EmptyElement( document, 'img' ); + new ContainerElement( document, 'p', null, img ); // eslint-disable-line no-new const position = new Position( img, 0 ); expectToThrowCKEditorError( () => { @@ -251,9 +251,9 @@ describe( 'DowncastWriter', () => { } ); it( 'should throw if breaking inside EmptyElement #2', () => { - const img = new EmptyElement( 'img' ); - const b = new AttributeElement( 'b' ); - new ContainerElement( 'p', null, [ img, b ] ); // eslint-disable-line no-new + const img = new EmptyElement( document, 'img' ); + const b = new AttributeElement( document, 'b' ); + new ContainerElement( document, 'p', null, [ img, b ] ); // eslint-disable-line no-new const range = Range._createFromParentsAndOffsets( img, 0, b, 0 ); expectToThrowCKEditorError( () => { @@ -262,8 +262,8 @@ describe( 'DowncastWriter', () => { } ); it( 'should throw if breaking inside UIElement #1', () => { - const span = new UIElement( 'span' ); - new ContainerElement( 'p', null, span ); // eslint-disable-line no-new + const span = new UIElement( document, 'span' ); + new ContainerElement( document, 'p', null, span ); // eslint-disable-line no-new const position = new Position( span, 0 ); expectToThrowCKEditorError( () => { @@ -272,9 +272,9 @@ describe( 'DowncastWriter', () => { } ); it( 'should throw if breaking inside UIElement #2', () => { - const span = new UIElement( 'span' ); - const b = new AttributeElement( 'b' ); - new ContainerElement( 'p', null, [ span, b ] ); // eslint-disable-line no-new + const span = new UIElement( document, 'span' ); + const b = new AttributeElement( document, 'b' ); + new ContainerElement( document, 'p', null, [ span, b ] ); // eslint-disable-line no-new const range = Range._createFromParentsAndOffsets( span, 0, b, 0 ); expectToThrowCKEditorError( () => { diff --git a/tests/view/downcastwriter/breakcontainer.js b/tests/view/downcastwriter/breakcontainer.js index e25c7293f..047192e9b 100644 --- a/tests/view/downcastwriter/breakcontainer.js +++ b/tests/view/downcastwriter/breakcontainer.js @@ -13,7 +13,7 @@ import { expectToThrowCKEditorError } from '@ckeditor/ckeditor5-utils/tests/_uti describe( 'DowncastWriter', () => { describe( 'breakContainer()', () => { - let writer; + let writer, document; // Executes test using `parse` and `stringify` utils functions. Uses range delimiters `[]{}` to create and // test break position. @@ -28,7 +28,8 @@ describe( 'DowncastWriter', () => { } before( () => { - writer = new DowncastWriter( new Document() ); + document = new Document(); + writer = new DowncastWriter( document ); } ); it( 'break inside element - should break container element at given position', () => { @@ -73,7 +74,7 @@ describe( 'DowncastWriter', () => { } ); it( 'should throw if position parent is root', () => { - const element = new ContainerElement( 'div' ); + const element = new ContainerElement( document, 'div' ); const position = Position._createAt( element, 0 ); expectToThrowCKEditorError( () => { diff --git a/tests/view/downcastwriter/clear.js b/tests/view/downcastwriter/clear.js index 477f08c5b..cd8583f81 100644 --- a/tests/view/downcastwriter/clear.js +++ b/tests/view/downcastwriter/clear.js @@ -37,8 +37,8 @@ describe( 'DowncastWriter', () => { } ); it( 'should throw when range placed in two containers', () => { - const p1 = new ContainerElement( 'p' ); - const p2 = new ContainerElement( 'p' ); + const p1 = new ContainerElement( document, 'p' ); + const p2 = new ContainerElement( document, 'p' ); expectToThrowCKEditorError( () => { writer.clear( Range._createFromParentsAndOffsets( p1, 0, p2, 0 ) ); @@ -46,7 +46,7 @@ describe( 'DowncastWriter', () => { } ); it( 'should throw when range has no parent container', () => { - const el = new AttributeElement( 'b' ); + const el = new AttributeElement( document, 'b' ); expectToThrowCKEditorError( () => { writer.clear( Range._createFromParentsAndOffsets( el, 0, el, 0 ) ); @@ -54,7 +54,7 @@ describe( 'DowncastWriter', () => { } ); it( 'should remove matched element from range', () => { - const elementToRemove = new AttributeElement( 'b' ); + const elementToRemove = new AttributeElement( document, 'b' ); test( elementToRemove, @@ -64,7 +64,7 @@ describe( 'DowncastWriter', () => { } ); it( 'should remove matched element from range when range is inside text node', () => { - const elementToRemove = new AttributeElement( 'b' ); + const elementToRemove = new AttributeElement( document, 'b' ); test( elementToRemove, @@ -74,7 +74,7 @@ describe( 'DowncastWriter', () => { } ); it( 'should remove multiple matched elements from range', () => { - const elementToRemove = new AttributeElement( 'b' ); + const elementToRemove = new AttributeElement( document, 'b' ); test( elementToRemove, @@ -84,7 +84,7 @@ describe( 'DowncastWriter', () => { } ); it( 'should remove multiple matched elements from range when range is inside text node', () => { - const elementToRemove = new AttributeElement( 'b' ); + const elementToRemove = new AttributeElement( document, 'b' ); test( elementToRemove, @@ -94,7 +94,7 @@ describe( 'DowncastWriter', () => { } ); it( 'should remove only matched element', () => { - const elementToRemove = new AttributeElement( 'b' ); + const elementToRemove = new AttributeElement( document, 'b' ); test( elementToRemove, @@ -104,7 +104,7 @@ describe( 'DowncastWriter', () => { } ); it( 'should remove part of node when range ends inside this node', () => { - const elementToRemove = new AttributeElement( 'b' ); + const elementToRemove = new AttributeElement( document, 'b' ); test( elementToRemove, @@ -114,7 +114,7 @@ describe( 'DowncastWriter', () => { } ); it( 'should remove part of node when range starts inside this node', () => { - const elementToRemove = new AttributeElement( 'b' ); + const elementToRemove = new AttributeElement( document, 'b' ); test( elementToRemove, @@ -124,7 +124,7 @@ describe( 'DowncastWriter', () => { } ); it( 'should remove part of node when range starts and ends inside this node', () => { - const elementToRemove = new AttributeElement( 'b' ); + const elementToRemove = new AttributeElement( document, 'b' ); test( elementToRemove, @@ -134,7 +134,7 @@ describe( 'DowncastWriter', () => { } ); it( 'should merge after removing', () => { - const elementToRemove = new AttributeElement( 'b' ); + const elementToRemove = new AttributeElement( document, 'b' ); test( elementToRemove, @@ -146,7 +146,7 @@ describe( 'DowncastWriter', () => { } ); it( 'should remove EmptyElement', () => { - const elementToRemove = new EmptyElement( 'img' ); + const elementToRemove = new EmptyElement( document, 'img' ); test( elementToRemove, @@ -156,7 +156,7 @@ describe( 'DowncastWriter', () => { } ); it( 'should remove UIElement', () => { - const elementToRemove = new UIElement( 'span' ); + const elementToRemove = new UIElement( document, 'span' ); test( elementToRemove, @@ -166,7 +166,7 @@ describe( 'DowncastWriter', () => { } ); it( 'should remove ContainerElement', () => { - const elementToRemove = new ContainerElement( 'p' ); + const elementToRemove = new ContainerElement( document, 'p' ); test( elementToRemove, diff --git a/tests/view/downcastwriter/insert.js b/tests/view/downcastwriter/insert.js index 707ddfe96..3e773d2be 100644 --- a/tests/view/downcastwriter/insert.js +++ b/tests/view/downcastwriter/insert.js @@ -155,8 +155,8 @@ describe( 'DowncastWriter', () => { } ); it( 'should throw when inserting Element', () => { - const element = new Element( 'b' ); - const container = new ContainerElement( 'p' ); + const element = new Element( document, 'b' ); + const container = new ContainerElement( document, 'p' ); const position = new Position( container, 0 ); expectToThrowCKEditorError( () => { @@ -165,9 +165,9 @@ describe( 'DowncastWriter', () => { } ); it( 'should throw when Element is inserted as child node', () => { - const element = new Element( 'b' ); - const root = new ContainerElement( 'p', null, element ); - const container = new ContainerElement( 'p' ); + const element = new Element( document, 'b' ); + const root = new ContainerElement( document, 'p', null, element ); + const container = new ContainerElement( document, 'p' ); const position = new Position( container, 0 ); expectToThrowCKEditorError( () => { @@ -176,9 +176,9 @@ describe( 'DowncastWriter', () => { } ); it( 'should throw when position is not placed inside container', () => { - const element = new Element( 'b' ); + const element = new Element( document, 'b' ); const position = new Position( element, 0 ); - const attributeElement = new AttributeElement( 'i' ); + const attributeElement = new AttributeElement( document, 'i' ); expectToThrowCKEditorError( () => { writer.insert( position, attributeElement ); @@ -194,10 +194,10 @@ describe( 'DowncastWriter', () => { } ); it( 'should throw if trying to insert inside EmptyElement', () => { - const emptyElement = new EmptyElement( 'img' ); - new ContainerElement( 'p', null, emptyElement ); // eslint-disable-line no-new + const emptyElement = new EmptyElement( document, 'img' ); + new ContainerElement( document, 'p', null, emptyElement ); // eslint-disable-line no-new const position = new Position( emptyElement, 0 ); - const attributeElement = new AttributeElement( 'i' ); + const attributeElement = new AttributeElement( document, 'i' ); expectToThrowCKEditorError( () => { writer.insert( position, attributeElement ); @@ -205,10 +205,10 @@ describe( 'DowncastWriter', () => { } ); it( 'should throw if trying to insert inside UIElement', () => { - const uiElement = new UIElement( 'span' ); - new ContainerElement( 'p', null, uiElement ); // eslint-disable-line no-new + const uiElement = new UIElement( document, 'span' ); + new ContainerElement( document, 'p', null, uiElement ); // eslint-disable-line no-new const position = new Position( uiElement, 0 ); - const attributeElement = new AttributeElement( 'i' ); + const attributeElement = new AttributeElement( document, 'i' ); expectToThrowCKEditorError( () => { writer.insert( position, attributeElement ); diff --git a/tests/view/downcastwriter/mergeattributes.js b/tests/view/downcastwriter/mergeattributes.js index 976a8a474..cf7094690 100644 --- a/tests/view/downcastwriter/mergeattributes.js +++ b/tests/view/downcastwriter/mergeattributes.js @@ -12,7 +12,7 @@ import Document from '../../../src/view/document'; describe( 'DowncastWriter', () => { describe( 'mergeAttributes', () => { - let writer; + let writer, document; // Executes test using `parse` and `stringify` utils functions. Uses range delimiters `[]{}` to create and // test merge position. @@ -26,7 +26,8 @@ describe( 'DowncastWriter', () => { } before( () => { - writer = new DowncastWriter( new Document() ); + document = new Document(); + writer = new DowncastWriter( document ); } ); it( 'should not merge if inside text node', () => { @@ -63,9 +64,9 @@ describe( 'DowncastWriter', () => { it( 'should merge when placed between two text nodes', () => { //

foobar

->

foo|bar

- const t1 = new Text( 'foo' ); - const t2 = new Text( 'bar' ); - const p = new ContainerElement( 'p', null, [ t1, t2 ] ); + const t1 = new Text( document, 'foo' ); + const t2 = new Text( document, 'bar' ); + const p = new ContainerElement( document, 'p', null, [ t1, t2 ] ); const position = new Position( p, 1 ); const newPosition = writer.mergeAttributes( position ); diff --git a/tests/view/downcastwriter/move.js b/tests/view/downcastwriter/move.js index da38969c5..e0c65e351 100644 --- a/tests/view/downcastwriter/move.js +++ b/tests/view/downcastwriter/move.js @@ -19,7 +19,7 @@ import { expectToThrowCKEditorError } from '@ckeditor/ckeditor5-utils/tests/_uti describe( 'DowncastWriter', () => { describe( 'move()', () => { - let writer; + let writer, document; // Executes test using `parse` and `stringify` utils functions. Uses range delimiters `[]{}` to create and // test ranges. @@ -38,7 +38,8 @@ describe( 'DowncastWriter', () => { } before( () => { - writer = new DowncastWriter( new Document() ); + document = new Document(); + writer = new DowncastWriter( document ); } ); it( 'should move single text node', () => { @@ -148,12 +149,12 @@ describe( 'DowncastWriter', () => { } ); it( 'should throw if trying to move to EmptyElement', () => { - const srcAttribute = new AttributeElement( 'b' ); - const srcContainer = new ContainerElement( 'p', null, srcAttribute ); + const srcAttribute = new AttributeElement( document, 'b' ); + const srcContainer = new ContainerElement( document, 'p', null, srcAttribute ); const srcRange = Range._createFromParentsAndOffsets( srcContainer, 0, srcContainer, 1 ); - const dstEmpty = new EmptyElement( 'img' ); - new ContainerElement( 'p', null, dstEmpty ); // eslint-disable-line no-new + const dstEmpty = new EmptyElement( document, 'img' ); + new ContainerElement( document, 'p', null, dstEmpty ); // eslint-disable-line no-new const dstPosition = new Position( dstEmpty, 0 ); expectToThrowCKEditorError( () => { @@ -171,12 +172,12 @@ describe( 'DowncastWriter', () => { } ); it( 'should throw if trying to move to UIElement', () => { - const srcAttribute = new AttributeElement( 'b' ); - const srcContainer = new ContainerElement( 'p', null, srcAttribute ); + const srcAttribute = new AttributeElement( document, 'b' ); + const srcContainer = new ContainerElement( document, 'p', null, srcAttribute ); const srcRange = Range._createFromParentsAndOffsets( srcContainer, 0, srcContainer, 1 ); - const dstUI = new UIElement( 'span' ); - new ContainerElement( 'p', null, dstUI ); // eslint-disable-line no-new + const dstUI = new UIElement( document, 'span' ); + new ContainerElement( document, 'p', null, dstUI ); // eslint-disable-line no-new const dstPosition = new Position( dstUI, 0 ); expectToThrowCKEditorError( () => { @@ -187,16 +188,16 @@ describe( 'DowncastWriter', () => { it( 'should not break marker mappings if marker element was split and the original element was removed', () => { const mapper = new Mapper(); - const srcContainer = new ContainerElement( 'p' ); - const dstContainer = new ContainerElement( 'p' ); + const srcContainer = new ContainerElement( document, 'p' ); + const dstContainer = new ContainerElement( document, 'p' ); - const root = new RootEditableElement( 'div' ); + const root = new RootEditableElement( document, 'div' ); root._appendChild( [ srcContainer, dstContainer ] ); - const attrElemA = new AttributeElement( 'span' ); + const attrElemA = new AttributeElement( document, 'span' ); attrElemA._id = 'foo'; - const attrElemB = new AttributeElement( 'span' ); + const attrElemB = new AttributeElement( document, 'span' ); attrElemB._id = 'foo'; writer.insert( new Position( srcContainer, 0 ), [ attrElemA, attrElemB ] ); diff --git a/tests/view/downcastwriter/remove.js b/tests/view/downcastwriter/remove.js index 6736d2318..461c8112c 100644 --- a/tests/view/downcastwriter/remove.js +++ b/tests/view/downcastwriter/remove.js @@ -43,8 +43,8 @@ describe( 'DowncastWriter', () => { } ); it( 'should throw when range placed in two containers', () => { - const p1 = new ContainerElement( 'p' ); - const p2 = new ContainerElement( 'p' ); + const p1 = new ContainerElement( document, 'p' ); + const p2 = new ContainerElement( document, 'p' ); expectToThrowCKEditorError( () => { writer.remove( Range._createFromParentsAndOffsets( p1, 0, p2, 0 ) ); @@ -52,7 +52,7 @@ describe( 'DowncastWriter', () => { } ); it( 'should throw when range has no parent container', () => { - const el = new AttributeElement( 'b' ); + const el = new AttributeElement( document, 'b' ); expectToThrowCKEditorError( () => { writer.remove( Range._createFromParentsAndOffsets( el, 0, el, 0 ) ); @@ -60,7 +60,7 @@ describe( 'DowncastWriter', () => { } ); it( 'should return empty DocumentFragment when range is collapsed', () => { - const p = new ContainerElement( 'p' ); + const p = new ContainerElement( document, 'p' ); const range = Range._createFromParentsAndOffsets( p, 0, p, 0 ); const fragment = writer.remove( range ); @@ -130,9 +130,9 @@ describe( 'DowncastWriter', () => { } ); it( 'should throw if range is placed inside EmptyElement', () => { - const emptyElement = new EmptyElement( 'img' ); - const attributeElement = new AttributeElement( 'b' ); - new ContainerElement( 'p', null, [ emptyElement, attributeElement ] ); // eslint-disable-line no-new + const emptyElement = new EmptyElement( document, 'img' ); + const attributeElement = new AttributeElement( document, 'b' ); + new ContainerElement( document, 'p', null, [ emptyElement, attributeElement ] ); // eslint-disable-line no-new const range = Range._createFromParentsAndOffsets( emptyElement, 0, attributeElement, 0 ); expectToThrowCKEditorError( () => { @@ -149,9 +149,9 @@ describe( 'DowncastWriter', () => { } ); it( 'should throw if range is placed inside UIElement', () => { - const uiElement = new UIElement( 'span' ); - const attributeElement = new AttributeElement( 'b' ); - new ContainerElement( 'p', null, [ uiElement, attributeElement ] ); // eslint-disable-line no-new + const uiElement = new UIElement( document, 'span' ); + const attributeElement = new AttributeElement( document, 'b' ); + new ContainerElement( document, 'p', null, [ uiElement, attributeElement ] ); // eslint-disable-line no-new const range = Range._createFromParentsAndOffsets( uiElement, 0, attributeElement, 0 ); expectToThrowCKEditorError( () => { @@ -201,7 +201,7 @@ describe( 'DowncastWriter', () => { } ); it( 'should throw when item has no parent container', () => { - const el = new AttributeElement( 'b' ); + const el = new AttributeElement( document, 'b' ); expectToThrowCKEditorError( () => { writer.remove( el ); diff --git a/tests/view/downcastwriter/unwrap.js b/tests/view/downcastwriter/unwrap.js index 943d8f70c..71a39e2fe 100644 --- a/tests/view/downcastwriter/unwrap.js +++ b/tests/view/downcastwriter/unwrap.js @@ -55,12 +55,12 @@ describe( 'DowncastWriter', () => { } ); it( 'should throw error when element is not instance of AttributeElement', () => { - const container = new ContainerElement( 'p', null, new AttributeElement( 'b', null, new Text( 'foo' ) ) ); + const container = new ContainerElement( document, 'p', null, new AttributeElement( document, 'b', null, new Text( 'foo' ) ) ); const range = new Range( new Position( container, 0 ), new Position( container, 1 ) ); - const b = new Element( 'b' ); + const b = new Element( document, 'b' ); expectToThrowCKEditorError( () => { writer.unwrap( range, b ); @@ -68,13 +68,13 @@ describe( 'DowncastWriter', () => { } ); it( 'should throw error when range placed in two containers', () => { - const container1 = new ContainerElement( 'p' ); - const container2 = new ContainerElement( 'p' ); + const container1 = new ContainerElement( document, 'p' ); + const container2 = new ContainerElement( document, 'p' ); const range = new Range( new Position( container1, 0 ), new Position( container2, 1 ) ); - const b = new AttributeElement( 'b' ); + const b = new AttributeElement( document, 'b' ); expectToThrowCKEditorError( () => { writer.unwrap( range, b ); @@ -82,8 +82,8 @@ describe( 'DowncastWriter', () => { } ); it( 'should throw when range has no parent container', () => { - const el = new AttributeElement( 'b' ); - const b = new AttributeElement( 'b' ); + const el = new AttributeElement( document, 'b' ); + const b = new AttributeElement( document, 'b' ); expectToThrowCKEditorError( () => { writer.unwrap( Range._createFromParentsAndOffsets( el, 0, el, 0 ), b ); @@ -396,9 +396,9 @@ describe( 'DowncastWriter', () => { } ); it( 'should throw if range is inside EmptyElement', () => { - const empty = new EmptyElement( 'img' ); - const attribute = new AttributeElement( 'b' ); - const container = new ContainerElement( 'p', null, [ empty, attribute ] ); + const empty = new EmptyElement( document, 'img' ); + const attribute = new AttributeElement( document, 'b' ); + const container = new ContainerElement( document, 'p', null, [ empty, attribute ] ); const range = Range._createFromParentsAndOffsets( empty, 0, container, 2 ); expectToThrowCKEditorError( () => { @@ -415,9 +415,9 @@ describe( 'DowncastWriter', () => { } ); it( 'should throw if range is placed inside UIElement', () => { - const uiElement = new UIElement( 'span' ); - const attribute = new AttributeElement( 'b' ); - const container = new ContainerElement( 'p', null, [ uiElement, attribute ] ); + const uiElement = new UIElement( document, 'span' ); + const attribute = new AttributeElement( document, 'b' ); + const container = new ContainerElement( document, 'p', null, [ uiElement, attribute ] ); const range = Range._createFromParentsAndOffsets( uiElement, 0, container, 2 ); expectToThrowCKEditorError( () => { diff --git a/tests/view/downcastwriter/wrap.js b/tests/view/downcastwriter/wrap.js index fc301c343..48ba9adcb 100644 --- a/tests/view/downcastwriter/wrap.js +++ b/tests/view/downcastwriter/wrap.js @@ -62,12 +62,12 @@ describe( 'DowncastWriter', () => { } ); it( 'should throw error when element is not instance of AttributeElement', () => { - const container = new ContainerElement( 'p', null, new Text( 'foo' ) ); + const container = new ContainerElement( document, 'p', null, new Text( 'foo' ) ); const range = new Range( new Position( container, 0 ), new Position( container, 1 ) ); - const b = new Element( 'b' ); + const b = new Element( document, 'b' ); expectToThrowCKEditorError( () => { writer.wrap( range, b ); @@ -75,13 +75,13 @@ describe( 'DowncastWriter', () => { } ); it( 'should throw error when range placed in two containers', () => { - const container1 = new ContainerElement( 'p' ); - const container2 = new ContainerElement( 'p' ); + const container1 = new ContainerElement( document, 'p' ); + const container2 = new ContainerElement( document, 'p' ); const range = new Range( new Position( container1, 0 ), new Position( container2, 1 ) ); - const b = new AttributeElement( 'b' ); + const b = new AttributeElement( document, 'b' ); expectToThrowCKEditorError( () => { writer.wrap( range, b ); @@ -89,8 +89,8 @@ describe( 'DowncastWriter', () => { } ); it( 'should throw when range has no parent container', () => { - const el = new AttributeElement( 'b' ); - const b = new AttributeElement( 'b' ); + const el = new AttributeElement( document, 'b' ); + const b = new AttributeElement( document, 'b' ); expectToThrowCKEditorError( () => { writer.wrap( Range._createFromParentsAndOffsets( el, 0, el, 0 ), b ); @@ -394,12 +394,12 @@ describe( 'DowncastWriter', () => { } ); it( 'should throw if range is inside EmptyElement', () => { - const emptyElement = new EmptyElement( 'img' ); - const container = new ContainerElement( 'p', null, emptyElement ); + const emptyElement = new EmptyElement( document, 'img' ); + const container = new ContainerElement( document, 'p', null, emptyElement ); const range = Range._createFromParentsAndOffsets( emptyElement, 0, container, 1 ); expectToThrowCKEditorError( () => { - writer.wrap( range, new AttributeElement( 'b' ) ); + writer.wrap( range, new AttributeElement( document, 'b' ) ); }, 'view-writer-cannot-break-empty-element', document ); } ); @@ -412,12 +412,12 @@ describe( 'DowncastWriter', () => { } ); it( 'should throw if range is inside UIElement', () => { - const uiElement = new UIElement( 'span' ); - const container = new ContainerElement( 'p', null, uiElement ); + const uiElement = new UIElement( document, 'span' ); + const container = new ContainerElement( document, 'p', null, uiElement ); const range = Range._createFromParentsAndOffsets( uiElement, 0, container, 1 ); expectToThrowCKEditorError( () => { - writer.wrap( range, new AttributeElement( 'b' ) ); + writer.wrap( range, new AttributeElement( document, 'b' ) ); }, 'view-writer-cannot-break-ui-element', document ); } ); @@ -543,15 +543,15 @@ describe( 'DowncastWriter', () => { const newPosition = writer.wrap( selection.getFirstRange(), parse( wrapAttribute ) ); // Moving parsed elements to a document fragment so the view root is not shown in `stringify`. - const viewChildren = new DocumentFragment( view.getChildren() ); + const viewChildren = new DocumentFragment( viewDocument, view.getChildren() ); expect( stringify( viewChildren, newPosition, { showType: true, showPriority: true } ) ).to.equal( expected ); } it( 'should throw error when element is not instance of AttributeElement', () => { - const container = new ContainerElement( 'p', null, new Text( 'foo' ) ); + const container = new ContainerElement( document, 'p', null, new Text( 'foo' ) ); const position = new Position( container, 0 ); - const b = new Element( 'b' ); + const b = new Element( document, 'b' ); expectToThrowCKEditorError( () => { writer.wrap( new Range( position ), b ); From 2d99f8f7be9ea756678be527f238eb56938890df Mon Sep 17 00:00:00 2001 From: Kamil Piechaczek Date: Mon, 3 Feb 2020 10:24:24 +0100 Subject: [PATCH 03/34] Added #document property to view.UpcastWriter(). --- src/view/upcastwriter.js | 18 +++++++++++++----- tests/view/upcastwriter.js | 22 ++++++++++++---------- 2 files changed, 25 insertions(+), 15 deletions(-) diff --git a/src/view/upcastwriter.js b/src/view/upcastwriter.js index e5d90ccdb..0777b2345 100644 --- a/src/view/upcastwriter.js +++ b/src/view/upcastwriter.js @@ -29,12 +29,20 @@ import Selection from './selection'; * Unlike `DowncastWriter`, which is available in the {@link module:engine/view/view~View#change `View#change()`} block, * `UpcastWriter` can be created wherever you need it: * - * const writer = new UpcastWriter(); + * const writer = new UpcastWriter( viewDocument ); * const text = writer.createText( 'foo!' ); * * writer.appendChild( text, someViewElement ); */ export default class UpcastWriter { + constructor( document ) { + /** + * @readonly + * @type {module:engine/view/document~Document} + */ + this.document = document; + } + /** * Creates a new {@link module:engine/view/documentfragment~DocumentFragment} instance. * @@ -43,7 +51,7 @@ export default class UpcastWriter { * @returns {module:engine/view/documentfragment~DocumentFragment} The created document fragment. */ createDocumentFragment( children ) { - return new DocumentFragment( children ); + return new DocumentFragment( this.document, children ); } /** @@ -62,7 +70,7 @@ export default class UpcastWriter { * @returns {module:engine/view/element~Element} Created element. */ createElement( name, attrs, children ) { - return new Element( name, attrs, children ); + return new Element( this.document, name, attrs, children ); } /** @@ -72,7 +80,7 @@ export default class UpcastWriter { * @returns {module:engine/view/text~Text} The created text node. */ createText( data ) { - return new Text( data ); + return new Text( this.document, data ); } /** @@ -201,7 +209,7 @@ export default class UpcastWriter { * was not replaced (happens for detached elements). */ rename( newName, element ) { - const newElement = new Element( newName, element.getAttributes(), element.getChildren() ); + const newElement = new Element( this.document, newName, element.getAttributes(), element.getChildren() ); return this.replace( element, newElement ) ? newElement : null; } diff --git a/tests/view/upcastwriter.js b/tests/view/upcastwriter.js index 73c082b66..314ef4bcd 100644 --- a/tests/view/upcastwriter.js +++ b/tests/view/upcastwriter.js @@ -11,12 +11,14 @@ import HtmlDataProcessor from '../../src/dataprocessor/htmldataprocessor'; import ViewPosition from '../../src/view/position'; import ViewRange from '../../src/view/range'; import ViewSelection from '../../src/view/selection'; +import Document from '../../src/view/document'; describe( 'UpcastWriter', () => { - let writer, view, dataprocessor; + let writer, view, dataprocessor, document; before( () => { - writer = new UpcastWriter(); + document = new Document(); + writer = new UpcastWriter( document ); dataprocessor = new HtmlDataProcessor(); } ); @@ -350,7 +352,7 @@ describe( 'UpcastWriter', () => { } ); it( 'should do nothing for elements without parent', () => { - const element = new Element( 'p', null, 'foo' ); + const element = new Element( document, 'p', null, 'foo' ); writer.unwrapElement( element ); @@ -382,7 +384,7 @@ describe( 'UpcastWriter', () => { } ); it( 'should have no effect on detached element', () => { - const el = new Element( 'h2' ); + const el = new Element( document, 'h2' ); const renamed = writer.rename( 'h3', el ); @@ -581,41 +583,41 @@ describe( 'UpcastWriter', () => { describe( 'createPositionAt()', () => { it( 'should return instance of Position', () => { - const span = new Element( 'span' ); + const span = new Element( document, 'span' ); expect( writer.createPositionAt( span, 0 ) ).to.be.instanceof( ViewPosition ); } ); } ); describe( 'createPositionAfter()', () => { it( 'should return instance of Position', () => { - const span = new Element( 'span', undefined, new Element( 'span' ) ); + const span = new Element( document, 'span', undefined, new Element( document, 'span' ) ); expect( writer.createPositionAfter( span.getChild( 0 ) ) ).to.be.instanceof( ViewPosition ); } ); } ); describe( 'createPositionBefore()', () => { it( 'should return instance of Position', () => { - const span = new Element( 'span', undefined, new Element( 'span' ) ); + const span = new Element( document, 'span', undefined, new Element( document, 'span' ) ); expect( writer.createPositionBefore( span.getChild( 0 ) ) ).to.be.instanceof( ViewPosition ); } ); } ); describe( 'createRange()', () => { it( 'should return instance of Range', () => { - expect( writer.createRange( writer.createPositionAt( new Element( 'span' ), 0 ) ) ).to.be.instanceof( ViewRange ); + expect( writer.createRange( writer.createPositionAt( new Element( document, 'span' ), 0 ) ) ).to.be.instanceof( ViewRange ); } ); } ); describe( 'createRangeIn()', () => { it( 'should return instance of Range', () => { - const span = new Element( 'span', undefined, new Element( 'span' ) ); + const span = new Element( document, 'span', undefined, new Element( document, 'span' ) ); expect( writer.createRangeIn( span.getChild( 0 ) ) ).to.be.instanceof( ViewRange ); } ); } ); describe( 'createRangeOn()', () => { it( 'should return instance of Range', () => { - const span = new Element( 'span', undefined, new Element( 'span' ) ); + const span = new Element( document, 'span', undefined, new Element( document, 'span' ) ); expect( writer.createRangeOn( span.getChild( 0 ) ) ).to.be.instanceof( ViewRange ); } ); } ); From 414f1c100cc4e22d4504d584d1f01ff50c51c2e2 Mon Sep 17 00:00:00 2001 From: Kamil Piechaczek Date: Mon, 17 Feb 2020 12:11:07 +0100 Subject: [PATCH 04/34] Adjusted tests and fixed "view.Text#_clone()" and "view.Element#_clone()" methods. --- src/controller/datacontroller.js | 5 +- src/controller/editingcontroller.js | 3 +- src/conversion/downcasthelpers.js | 9 +- src/dev-utils/model.js | 5 +- src/view/documentfragment.js | 2 +- src/view/downcastwriter.js | 6 +- src/view/editableelement.js | 69 ++----- src/view/element.js | 12 +- src/view/placeholder.js | 1 + src/view/rooteditableelement.js | 5 +- tests/controller/datacontroller.js | 6 +- tests/conversion/downcastdispatcher.js | 4 +- tests/conversion/downcasthelpers.js | 63 +++--- tests/conversion/mapper.js | 131 +++++++------ tests/conversion/upcastdispatcher.js | 70 +++---- tests/conversion/upcasthelpers.js | 187 ++++++++++-------- tests/conversion/viewconsumable.js | 46 ++--- tests/dev-utils/view.js | 215 ++++++++++---------- tests/view/_utils/createroot.js | 3 +- tests/view/attributeelement.js | 40 ++-- tests/view/containerelement.js | 11 +- tests/view/documentfragment.js | 81 ++++---- tests/view/documentselection.js | 31 +-- tests/view/domconverter/binding.js | 30 +-- tests/view/domconverter/dom-to-view.js | 14 +- tests/view/domconverter/domconverter.js | 10 +- tests/view/domconverter/uielement.js | 12 +- tests/view/domconverter/view-to-dom.js | 251 ++++++++++++------------ tests/view/editableelement.js | 77 +++----- tests/view/element.js | 127 ++++++------ tests/view/emptyelement.js | 14 +- tests/view/matcher.js | 85 ++++---- tests/view/node.js | 99 ++++------ tests/view/observer/domeventobserver.js | 2 +- tests/view/placeholder.js | 2 +- tests/view/position.js | 166 ++++++++-------- tests/view/range.js | 45 +++-- tests/view/renderer.js | 139 +++++++------ tests/view/rooteditableelement.js | 21 +- tests/view/selection.js | 33 ++-- tests/view/text.js | 23 ++- tests/view/textproxy.js | 30 ++- tests/view/treewalker.js | 24 +-- tests/view/uielement.js | 15 +- tests/view/view/jumpoveruielement.js | 58 +++--- tests/view/view/view.js | 4 +- 46 files changed, 1171 insertions(+), 1115 deletions(-) diff --git a/src/controller/datacontroller.js b/src/controller/datacontroller.js index 963bd3c39..0e0a36a81 100644 --- a/src/controller/datacontroller.js +++ b/src/controller/datacontroller.js @@ -187,12 +187,13 @@ export default class DataController { // First, convert elements. const modelRange = ModelRange._createIn( modelElementOrFragment ); + const viewDocument = new ViewDocument(); - const viewDocumentFragment = new ViewDocumentFragment(); + const viewDocumentFragment = new ViewDocumentFragment( viewDocument ); // Create separate ViewDowncastWriter just for data conversion purposes. // We have no view controller and rendering do DOM in DataController so view.change() block is not used here. - const viewWriter = new ViewDowncastWriter( new ViewDocument() ); + const viewWriter = new ViewDowncastWriter( viewDocument ); this.mapper.bindElements( modelElementOrFragment, viewDocumentFragment ); this.downcastDispatcher.convertInsert( modelRange, viewWriter ); diff --git a/src/controller/editingcontroller.js b/src/controller/editingcontroller.js index 37c4d45c7..819a2cebc 100644 --- a/src/controller/editingcontroller.js +++ b/src/controller/editingcontroller.js @@ -115,10 +115,9 @@ export default class EditingController { return null; } - const viewRoot = new RootEditableElement( root.name ); + const viewRoot = new RootEditableElement( this.view.document, root.name ); viewRoot.rootName = root.rootName; - viewRoot._document = this.view.document; this.mapper.bindElements( root, viewRoot ); return viewRoot; diff --git a/src/conversion/downcasthelpers.js b/src/conversion/downcasthelpers.js index 1f14f3e62..5ae3e060e 100644 --- a/src/conversion/downcasthelpers.js +++ b/src/conversion/downcasthelpers.js @@ -416,11 +416,12 @@ export function remove() { * provided by the {@link module:engine/conversion/downcasthelpers~HighlightDescriptor highlight descriptor} object. If a priority * is not provided in the descriptor, the default priority will be used. * + * @param {module:engine/view/document~Document} document * @param {module:engine/conversion/downcasthelpers~HighlightDescriptor} descriptor * @returns {module:engine/view/attributeelement~AttributeElement} */ -export function createViewElementFromHighlightDescriptor( descriptor ) { - const viewElement = new ViewAttributeElement( 'span', descriptor.attributes ); +export function createViewElementFromHighlightDescriptor( document, descriptor ) { + const viewElement = new ViewAttributeElement( document, 'span', descriptor.attributes ); if ( descriptor.classes ) { viewElement._addClass( descriptor.classes ); @@ -919,8 +920,8 @@ function highlightText( highlightDescriptor ) { return; } - const viewElement = createViewElementFromHighlightDescriptor( descriptor ); const viewWriter = conversionApi.writer; + const viewElement = createViewElementFromHighlightDescriptor( viewWriter.document, descriptor ); const viewSelection = viewWriter.document.selection; if ( data.item instanceof ModelSelection || data.item instanceof DocumentSelection ) { @@ -1034,7 +1035,7 @@ function removeHighlight( highlightDescriptor ) { } // View element that will be used to unwrap `AttributeElement`s. - const viewHighlightElement = createViewElementFromHighlightDescriptor( descriptor ); + const viewHighlightElement = createViewElementFromHighlightDescriptor( conversionApi.writer.document, descriptor ); // Get all elements bound with given marker name. const elements = conversionApi.mapper.markerNameToElements( data.markerName ); diff --git a/src/dev-utils/model.js b/src/dev-utils/model.js index 35e9b1b97..1d47d267d 100644 --- a/src/dev-utils/model.js +++ b/src/dev-utils/model.js @@ -212,10 +212,9 @@ export function stringify( node, selectionOrPositionOrRange = null, markers = nu // Create a temporary view controller. const view = new View(); const viewDocument = view.document; - const viewRoot = new ViewRootEditableElement( 'div' ); + const viewRoot = new ViewRootEditableElement( viewDocument, 'div' ); // Create a temporary root element in view document. - viewRoot._document = view.document; viewRoot.rootName = 'main'; viewDocument.roots.add( viewRoot ); @@ -242,7 +241,7 @@ export function stringify( node, selectionOrPositionOrRange = null, markers = nu // Stringify object types values for properly display as an output string. const attributes = convertAttributes( modelItem.getAttributes(), stringifyAttributeValue ); - return new ViewContainerElement( modelItem.name, attributes ); + return new ViewContainerElement( viewDocument, modelItem.name, attributes ); } ) ); downcastDispatcher.on( 'selection', convertRangeSelection() ); diff --git a/src/view/documentfragment.js b/src/view/documentfragment.js index effc215cd..1ff1bab52 100644 --- a/src/view/documentfragment.js +++ b/src/view/documentfragment.js @@ -249,7 +249,7 @@ mix( DocumentFragment, EmitterMixin ); function normalize( document, nodes ) { // Separate condition because string is iterable. if ( typeof nodes == 'string' ) { - return [ new Text( nodes ) ]; + return [ new Text( document, nodes ) ]; } if ( !isIterable( nodes ) ) { diff --git a/src/view/downcastwriter.js b/src/view/downcastwriter.js index 0ad0e84ac..4455c5ddd 100644 --- a/src/view/downcastwriter.js +++ b/src/view/downcastwriter.js @@ -686,7 +686,7 @@ export default class DowncastWriter { // If range is collapsed - nothing to remove. if ( range.isCollapsed ) { - return new DocumentFragment(); + return new DocumentFragment( this.document ); } // Break attributes at range start and end. @@ -708,7 +708,7 @@ export default class DowncastWriter { range.end = mergePosition.clone(); // Return removed nodes. - return new DocumentFragment( removed ); + return new DocumentFragment( this.document, removed ); } /** @@ -914,7 +914,7 @@ export default class DowncastWriter { * @param {module:engine/view/containerelement~ContainerElement} viewElement Element to be renamed. */ rename( newName, viewElement ) { - const newElement = new ContainerElement( newName, viewElement.getAttributes() ); + const newElement = new ContainerElement( this.document, newName, viewElement.getAttributes() ); this.insert( Position._createAfter( viewElement ), newElement ); this.move( Range._createIn( viewElement ), Position._createAt( newElement, 0 ) ); diff --git a/src/view/editableelement.js b/src/view/editableelement.js index 8a9b61641..b6ca91c6f 100644 --- a/src/view/editableelement.js +++ b/src/view/editableelement.js @@ -8,12 +8,9 @@ */ import ContainerElement from './containerelement'; -import CKEditorError from '@ckeditor/ckeditor5-utils/src/ckeditorerror'; import mix from '@ckeditor/ckeditor5-utils/src/mix'; import ObservableMixin from '@ckeditor/ckeditor5-utils/src/observablemixin'; -const documentSymbol = Symbol( 'document' ); - /** * Editable element which can be a {@link module:engine/view/rooteditableelement~RootEditableElement root} * or nested editable area in the editor. @@ -33,8 +30,8 @@ export default class EditableElement extends ContainerElement { * @see module:engine/view/downcastwriter~DowncastWriter#createEditableElement * @protected */ - constructor( name, attrs, children ) { - super( name, attrs, children ); + constructor( document, name, attrs, children ) { + super( document, name, attrs, children ); /** * Whether the editable is in read-write or read-only mode. @@ -56,14 +53,18 @@ export default class EditableElement extends ContainerElement { */ this.set( 'isFocused', false ); - /** - * The {@link module:engine/view/document~Document} which is an owner of this root. - * Can only by set once. - * Throws {@link module:utils/ckeditorerror~CKEditorError CKEditorError} `view-editableelement-document-already-set` - * when document is already set. - * - * @member {module:engine/view/document~Document} #document - */ + this.bind( 'isReadOnly' ).to( document ); + + this.bind( 'isFocused' ).to( + document, + 'isFocused', + isFocused => isFocused && document.selection.editableElement == this + ); + + // Update focus state based on selection changes. + this.listenTo( document.selection, 'change', () => { + this.isFocused = document.isFocused && document.selection.editableElement == this; + } ); } /** @@ -105,48 +106,6 @@ export default class EditableElement extends ContainerElement { destroy() { this.stopListening(); } - - /** - * Returns document associated with the editable. - * - * @readonly - * @returns {module:engine/view/document~Document} - */ - get document() { - return this.getCustomProperty( documentSymbol ); - } - - /** - * Sets document of this editable element. - * - * @protected - * @param {module:engine/view/document~Document} document - */ - set _document( document ) { - if ( this.getCustomProperty( documentSymbol ) ) { - /** - * View document is already set. It can only be set once. - * - * @error view-editableelement-document-already-set - */ - throw new CKEditorError( 'view-editableelement-document-already-set: View document is already set.', this ); - } - - this._setCustomProperty( documentSymbol, document ); - - this.bind( 'isReadOnly' ).to( document ); - - this.bind( 'isFocused' ).to( - document, - 'isFocused', - isFocused => isFocused && document.selection.editableElement == this - ); - - // Update focus state based on selection changes. - this.listenTo( document.selection, 'change', () => { - this.isFocused = document.isFocused && document.selection.editableElement == this; - } ); - } } mix( EditableElement, ObservableMixin ); diff --git a/src/view/element.js b/src/view/element.js index 097886e38..0997dde46 100644 --- a/src/view/element.js +++ b/src/view/element.js @@ -564,7 +564,7 @@ export default class Element extends Node { } // ContainerElement and AttributeElement should be also cloned properly. - const cloned = new this.constructor( this.name, this._attrs, childrenClone ); + const cloned = new this.constructor( this.document, this.name, this._attrs, childrenClone ); // Classes and styles are cloned separately - this solution is faster than adding them back to attributes and // parse once again in constructor. @@ -611,7 +611,7 @@ export default class Element extends Node { this._fireChange( 'children', this ); let count = 0; - const nodes = normalize( items ); + const nodes = normalize( this.document, items ); for ( const node of nodes ) { // If node that is being added to this element is already inside another element, first remove it from the old parent. @@ -887,10 +887,10 @@ function parseClasses( classesSet, classesString ) { // // @param {String|module:engine/view/item~Item|Iterable.} // @returns {Iterable.} -function normalize( nodes ) { +function normalize( document, nodes ) { // Separate condition because string is iterable. if ( typeof nodes == 'string' ) { - return [ new Text( nodes ) ]; + return [ new Text( document, nodes ) ]; } if ( !isIterable( nodes ) ) { @@ -901,11 +901,11 @@ function normalize( nodes ) { return Array.from( nodes ) .map( node => { if ( typeof node == 'string' ) { - return new Text( node ); + return new Text( document, node ); } if ( node instanceof TextProxy ) { - return new Text( node.data ); + return new Text( document, node.data ); } return node; diff --git a/src/view/placeholder.js b/src/view/placeholder.js index bdc0709da..6829ca152 100644 --- a/src/view/placeholder.js +++ b/src/view/placeholder.js @@ -201,6 +201,7 @@ function updateDocumentPlaceholders( doc, writer ) { // @returns {Boolean} True if any changes were made to the view document. function updatePlaceholder( writer, element, config ) { const { text, isDirectHost } = config; + const hostElement = isDirectHost ? element : getChildPlaceholderHostSubstitute( element ); let wasViewModified = false; diff --git a/src/view/rooteditableelement.js b/src/view/rooteditableelement.js index f298446fb..2ca25e7fe 100644 --- a/src/view/rooteditableelement.js +++ b/src/view/rooteditableelement.js @@ -22,10 +22,11 @@ export default class RootEditableElement extends EditableElement { /** * Creates root editable element. * + * @param {module:engine/view/document~Document} document A document where the element belongs to. * @param {String} name Node name. */ - constructor( name ) { - super( name ); + constructor( document, name ) { + super( document, name ); /** * Name of this root inside {@link module:engine/view/document~Document} that is an owner of this root. If no diff --git a/tests/controller/datacontroller.js b/tests/controller/datacontroller.js index f358f051e..9670cc0fd 100644 --- a/tests/controller/datacontroller.js +++ b/tests/controller/datacontroller.js @@ -11,6 +11,7 @@ import HtmlDataProcessor from '../../src/dataprocessor/htmldataprocessor'; import ModelDocumentFragment from '../../src/model/documentfragment'; import ViewDocumentFragment from '../../src/view/documentfragment'; +import ViewDocument from '../../src/view/document'; import { getData, setData, stringify, parse as parseModel } from '../../src/dev-utils/model'; import { parse as parseView, stringify as stringifyView } from '../../src/dev-utils/view'; @@ -22,7 +23,7 @@ import DowncastHelpers from '../../src/conversion/downcasthelpers'; import { expectToThrowCKEditorError } from '@ckeditor/ckeditor5-utils/tests/_utils/utils'; describe( 'DataController', () => { - let model, modelDocument, htmlDataProcessor, data, schema, upcastHelpers, downcastHelpers; + let model, modelDocument, htmlDataProcessor, data, schema, upcastHelpers, downcastHelpers, viewDocument; beforeEach( () => { model = new Model(); @@ -36,6 +37,7 @@ describe( 'DataController', () => { schema.register( '$title', { inheritAllFrom: '$root' } ); htmlDataProcessor = new HtmlDataProcessor(); + viewDocument = new ViewDocument(); data = new DataController( model, htmlDataProcessor ); @@ -139,7 +141,7 @@ describe( 'DataController', () => { schema.register( 'inlineRoot' ); schema.extend( '$text', { allowIn: 'inlineRoot' } ); - const viewFragment = new ViewDocumentFragment( [ parseView( 'foo' ) ] ); + const viewFragment = new ViewDocumentFragment( viewDocument, [ parseView( 'foo' ) ] ); // Model fragment in root. expect( stringify( data.toModel( viewFragment ) ) ).to.equal( '' ); diff --git a/tests/conversion/downcastdispatcher.js b/tests/conversion/downcastdispatcher.js index b8741dfca..07f6fc3dd 100644 --- a/tests/conversion/downcastdispatcher.js +++ b/tests/conversion/downcastdispatcher.js @@ -414,8 +414,8 @@ describe( 'DowncastDispatcher', () => { root._appendChild( [ image ] ); // Create view elements that will be "mapped" to model elements. - const viewCaption = new ViewContainerElement( 'caption' ); - const viewFigure = new ViewContainerElement( 'figure', null, viewCaption ); + const viewCaption = new ViewContainerElement( view.document, 'caption' ); + const viewFigure = new ViewContainerElement( view.document, 'figure', null, viewCaption ); // Create custom highlight handler mock. viewFigure._setCustomProperty( 'addHighlight', () => {} ); diff --git a/tests/conversion/downcasthelpers.js b/tests/conversion/downcasthelpers.js index 91d857c8b..898c1a46d 100644 --- a/tests/conversion/downcasthelpers.js +++ b/tests/conversion/downcasthelpers.js @@ -16,6 +16,7 @@ import ViewAttributeElement from '../../src/view/attributeelement'; import ViewContainerElement from '../../src/view/containerelement'; import ViewUIElement from '../../src/view/uielement'; import ViewText from '../../src/view/text'; +import ViewDocument from '../../src/view/document'; import testUtils from '@ckeditor/ckeditor5-core/tests/_utils/utils'; @@ -1319,13 +1320,15 @@ describe( 'DowncastHelpers', () => { converterPriority: 7 }; - let markerRange; + let markerRange, viewDocument; beforeEach( () => { + viewDocument = new ViewDocument(); + downcastHelpers.elementToElement( { model: 'div', view: () => { - const viewContainer = new ViewContainerElement( 'div' ); + const viewContainer = new ViewContainerElement( viewDocument, 'div' ); viewContainer._setCustomProperty( 'addHighlight', ( element, descriptor, writer ) => { writer.addClass( descriptor.classes, element ); @@ -1499,6 +1502,12 @@ describe( 'downcast converters', () => { // Remove converter is by default already added in `EditingController` instance. describe( 'remove()', () => { + let viewDocument; + + beforeEach( () => { + viewDocument = new ViewDocument(); + } ); + it( 'should remove items from view accordingly to changes in model #1', () => { const modelElement = new ModelElement( 'paragraph', null, new ModelText( 'foobar' ) ); @@ -1552,9 +1561,9 @@ describe( 'downcast converters', () => { it( 'should not remove view ui elements that are placed next to removed content', () => { modelRoot._appendChild( new ModelText( 'fozbar' ) ); viewRoot._appendChild( [ - new ViewText( 'foz' ), - new ViewUIElement( 'span' ), - new ViewText( 'bar' ) + new ViewText( viewDocument, 'foz' ), + new ViewUIElement( viewDocument, 'span' ), + new ViewText( viewDocument, 'bar' ) ] ); // Remove 'b'. @@ -1579,9 +1588,9 @@ describe( 'downcast converters', () => { it( 'should remove correct amount of text when it is split by view ui element', () => { modelRoot._appendChild( new ModelText( 'fozbar' ) ); viewRoot._appendChild( [ - new ViewText( 'foz' ), - new ViewUIElement( 'span' ), - new ViewText( 'bar' ) + new ViewText( viewDocument, 'foz' ), + new ViewUIElement( viewDocument, 'span' ), + new ViewText( viewDocument, 'bar' ) ] ); // Remove 'zb'. @@ -1649,10 +1658,10 @@ describe( 'downcast converters', () => { const modelP1 = new ModelElement( 'paragraph' ); const modelP2 = new ModelElement( 'paragraph' ); - const viewP1 = new ViewContainerElement( 'p' ); - const viewUi1 = new ViewUIElement( 'span' ); - const viewUi2 = new ViewUIElement( 'span' ); - const viewP2 = new ViewContainerElement( 'p' ); + const viewP1 = new ViewContainerElement( viewDocument, 'p' ); + const viewUi1 = new ViewUIElement( viewDocument, 'span' ); + const viewUi2 = new ViewUIElement( viewDocument, 'span' ); + const viewP2 = new ViewContainerElement( viewDocument, 'p' ); modelRoot._appendChild( [ modelP1, modelP2 ] ); viewRoot._appendChild( [ viewP1, viewUi1, viewUi2, viewP2 ] ); @@ -1685,13 +1694,19 @@ describe( 'downcast converters', () => { } ); describe( 'createViewElementFromHighlightDescriptor()', () => { + let viewDocument; + + beforeEach( () => { + viewDocument = new ViewDocument(); + } ); + it( 'should return attribute element from descriptor object', () => { const descriptor = { classes: 'foo-class', attributes: { one: '1', two: '2' }, priority: 7 }; - const element = createViewElementFromHighlightDescriptor( descriptor ); + const element = createViewElementFromHighlightDescriptor( viewDocument, descriptor ); expect( element.is( 'attributeElement' ) ).to.be.true; expect( element.name ).to.equal( 'span' ); @@ -1709,7 +1724,7 @@ describe( 'downcast converters', () => { attributes: { one: '1', two: '2' }, priority: 7 }; - const element = createViewElementFromHighlightDescriptor( descriptor ); + const element = createViewElementFromHighlightDescriptor( viewDocument, descriptor ); expect( element.is( 'attributeElement' ) ).to.be.true; expect( element.name ).to.equal( 'span' ); @@ -1727,7 +1742,7 @@ describe( 'downcast converters', () => { attributes: { one: '1', two: '2' }, priority: 7 }; - const element = createViewElementFromHighlightDescriptor( descriptor ); + const element = createViewElementFromHighlightDescriptor( viewDocument, descriptor ); expect( element.is( 'attributeElement' ) ).to.be.true; expect( element.name ).to.equal( 'span' ); @@ -1743,7 +1758,7 @@ describe( 'downcast converters', () => { classes: 'foo-class', attributes: { one: '1', two: '2' } }; - const element = createViewElementFromHighlightDescriptor( descriptor ); + const element = createViewElementFromHighlightDescriptor( viewDocument, descriptor ); expect( element.is( 'attributeElement' ) ).to.be.true; expect( element.name ).to.equal( 'span' ); @@ -1760,7 +1775,7 @@ describe( 'downcast converters', () => { classes: 'foo-class', priority: 7 }; - const element = createViewElementFromHighlightDescriptor( descriptor ); + const element = createViewElementFromHighlightDescriptor( viewDocument, descriptor ); expect( element.is( 'attributeElement' ) ).to.be.true; expect( element.name ).to.equal( 'span' ); @@ -1908,7 +1923,11 @@ describe( 'downcast selection converters', () => { } ); describe( 'collapsed selection', () => { - let marker; + let marker, viewDocument; + + beforeEach( () => { + viewDocument = new ViewDocument(); + } ); it( 'in container', () => { test( @@ -2040,8 +2059,8 @@ describe( 'downcast selection converters', () => { // Add two ui elements to view. viewRoot._appendChild( [ - new ViewUIElement( 'span' ), - new ViewUIElement( 'span' ) + new ViewUIElement( viewDocument, 'span' ), + new ViewUIElement( viewDocument, 'span' ) ] ); model.change( writer => { @@ -2073,7 +2092,7 @@ describe( 'downcast selection converters', () => { dispatcher.convertInsert( model.createRangeIn( modelRoot ), writer ); // Add ui element to view. - const uiElement = new ViewUIElement( 'span' ); + const uiElement = new ViewUIElement( viewDocument, 'span' ); viewRoot._insertChild( 1, uiElement ); dispatcher.convertSelection( docSelection, model.markers, writer ); @@ -2098,7 +2117,7 @@ describe( 'downcast selection converters', () => { dispatcher.convertInsert( model.createRangeIn( modelRoot ), writer ); // Add ui element to view. - const uiElement = new ViewUIElement( 'span' ); + const uiElement = new ViewUIElement( viewDocument, 'span' ); viewRoot._insertChild( 1, uiElement, writer ); dispatcher.convertSelection( docSelection, model.markers, writer ); } ); diff --git a/tests/conversion/mapper.js b/tests/conversion/mapper.js index 619935780..70c7ca7c7 100644 --- a/tests/conversion/mapper.js +++ b/tests/conversion/mapper.js @@ -11,6 +11,7 @@ import ModelText from '../../src/model/text'; import ModelPosition from '../../src/model/position'; import ModelRange from '../../src/model/range'; +import ViewDocument from '../../src/view/document'; import ViewElement from '../../src/view/element'; import ViewUIElement from '../../src/view/uielement'; import ViewText from '../../src/view/text'; @@ -18,12 +19,18 @@ import ViewPosition from '../../src/view/position'; import ViewRange from '../../src/view/range'; describe( 'Mapper', () => { + let viewDocument; + + beforeEach( () => { + viewDocument = new ViewDocument(); + } ); + describe( 'clearBindings', () => { it( 'should remove all mapping', () => { - const viewA = new ViewElement( 'a' ); - const viewB = new ViewElement( 'b' ); - const viewC = new ViewElement( 'c' ); - const viewD = new ViewElement( 'd' ); + const viewA = new ViewElement( viewDocument, 'a' ); + const viewB = new ViewElement( viewDocument, 'b' ); + const viewC = new ViewElement( viewDocument, 'c' ); + const viewD = new ViewElement( viewDocument, 'd' ); const modelA = new ModelElement( 'a' ); const modelB = new ModelElement( 'b' ); @@ -69,7 +76,7 @@ describe( 'Mapper', () => { describe( 'unbindModelElement', () => { it( 'should remove binding between given model element and view element that it was bound to', () => { - const viewA = new ViewElement( 'a' ); + const viewA = new ViewElement( viewDocument, 'a' ); const modelA = new ModelElement( 'a' ); const mapper = new Mapper(); @@ -85,7 +92,7 @@ describe( 'Mapper', () => { } ); it( 'should not remove binding between view and model element if view element got rebound', () => { - const viewA = new ViewElement( 'a' ); + const viewA = new ViewElement( viewDocument, 'a' ); const modelA = new ModelElement( 'a' ); const modelB = new ModelElement( 'b' ); @@ -105,7 +112,7 @@ describe( 'Mapper', () => { describe( 'unbindViewElement', () => { it( 'should remove binding between given view element and model element that it was bound to', () => { - const viewA = new ViewElement( 'a' ); + const viewA = new ViewElement( viewDocument, 'a' ); const modelA = new ModelElement( 'a' ); const mapper = new Mapper(); @@ -121,8 +128,8 @@ describe( 'Mapper', () => { } ); it( 'should not remove binding between model and view element if model element got rebound', () => { - const viewA = new ViewElement( 'a' ); - const viewB = new ViewElement( 'b' ); + const viewA = new ViewElement( viewDocument, 'a' ); + const viewB = new ViewElement( viewDocument, 'b' ); const modelA = new ModelElement( 'a' ); const mapper = new Mapper(); @@ -201,21 +208,21 @@ describe( 'Mapper', () => { new ModelText( 'zz' ) ] ); - viewTextB = new ViewText( 'b' ); - viewTextO = new ViewText( 'o' ); - viewTextM = new ViewText( 'm' ); - viewTextX = new ViewText( 'x' ); - viewTextY = new ViewText( 'y' ); - viewTextZZ = new ViewText( 'zz' ); - viewTextFOO = new ViewText( 'foo' ); - viewTextBAR = new ViewText( 'bar' ); - viewImg = new ViewElement( 'img' ); - viewSup = new ViewElement( 'sup', {}, [ viewTextO ] ); - viewU = new ViewElement( 'u', {}, [ viewTextB, viewSup, viewTextM ] ); - viewI = new ViewElement( 'i', {}, [ viewTextFOO ] ); - viewB = new ViewElement( 'b', {}, [ viewI ] ); - viewP = new ViewElement( 'p', {}, [ viewTextY, viewB, viewTextBAR, viewImg, viewU ] ); - viewDiv = new ViewElement( 'div', {}, [ viewTextX, viewP, viewTextZZ ] ); + viewTextB = new ViewText( viewDocument, 'b' ); + viewTextO = new ViewText( viewDocument, 'o' ); + viewTextM = new ViewText( viewDocument, 'm' ); + viewTextX = new ViewText( viewDocument, 'x' ); + viewTextY = new ViewText( viewDocument, 'y' ); + viewTextZZ = new ViewText( viewDocument, 'zz' ); + viewTextFOO = new ViewText( viewDocument, 'foo' ); + viewTextBAR = new ViewText( viewDocument, 'bar' ); + viewImg = new ViewElement( viewDocument, 'img' ); + viewSup = new ViewElement( viewDocument, 'sup', {}, [ viewTextO ] ); + viewU = new ViewElement( viewDocument, 'u', {}, [ viewTextB, viewSup, viewTextM ] ); + viewI = new ViewElement( viewDocument, 'i', {}, [ viewTextFOO ] ); + viewB = new ViewElement( viewDocument, 'b', {}, [ viewI ] ); + viewP = new ViewElement( viewDocument, 'p', {}, [ viewTextY, viewB, viewTextBAR, viewImg, viewU ] ); + viewDiv = new ViewElement( viewDocument, 'div', {}, [ viewTextX, viewP, viewTextZZ ] ); mapper = new Mapper(); mapper.bindElements( modelP, viewP ); @@ -467,17 +474,17 @@ describe( 'Mapper', () => { modelDiv = new ModelRootElement(); modelDiv._appendChild( [ new ModelText( 'x' ), modelWidget, new ModelText( 'zz' ) ] ); - viewTextX = new ViewText( 'y' ); - viewTextZZ = new ViewText( 'zz' ); - viewTextFOO = new ViewText( 'foo' ); - viewTextLABEL = new ViewText( 'label' ); + viewTextX = new ViewText( viewDocument, 'y' ); + viewTextZZ = new ViewText( viewDocument, 'zz' ); + viewTextFOO = new ViewText( viewDocument, 'foo' ); + viewTextLABEL = new ViewText( viewDocument, 'label' ); - viewImg = new ViewElement( 'img' ); - viewMask = new ViewElement( 'mask', {}, [ viewTextLABEL ] ); - viewCaption = new ViewElement( 'caption', {}, [ viewTextFOO ] ); - viewWrapper = new ViewElement( 'wrapper', {}, [ viewImg, viewCaption ] ); - viewWidget = new ViewElement( 'widget', [ viewMask, viewWrapper ] ); - viewDiv = new ViewElement( 'div', {}, [ viewTextX, viewWidget, viewTextZZ ] ); + viewImg = new ViewElement( viewDocument, 'img' ); + viewMask = new ViewElement( viewDocument, 'mask', {}, [ viewTextLABEL ] ); + viewCaption = new ViewElement( viewDocument, 'caption', {}, [ viewTextFOO ] ); + viewWrapper = new ViewElement( viewDocument, 'wrapper', {}, [ viewImg, viewCaption ] ); + viewWidget = new ViewElement( viewDocument, 'widget', [ viewMask, viewWrapper ] ); + viewDiv = new ViewElement( viewDocument, 'div', {}, [ viewTextX, viewWidget, viewTextZZ ] ); mapper = new Mapper(); mapper.bindElements( modelDiv, viewDiv ); @@ -574,15 +581,15 @@ describe( 'Mapper', () => { modelRoot = new ModelRootElement( 'root', null, [ modelListItem1, modelListItem11, modelListItem12, modelListItem2 ] ); - viewListItem11 = new ViewElement( 'li', null, new ViewText( 'bbb' ) ); - viewListItem12 = new ViewElement( 'li', null, new ViewText( 'ccc' ) ); - viewListNested = new ViewElement( 'ul', null, [ viewListItem11, viewListItem12 ] ); + viewListItem11 = new ViewElement( viewDocument, 'li', null, new ViewText( viewDocument, 'bbb' ) ); + viewListItem12 = new ViewElement( viewDocument, 'li', null, new ViewText( viewDocument, 'ccc' ) ); + viewListNested = new ViewElement( viewDocument, 'ul', null, [ viewListItem11, viewListItem12 ] ); - viewListItem1 = new ViewElement( 'li', null, [ new ViewText( 'aaa' ), viewListNested ] ); - viewListItem2 = new ViewElement( 'li', null, new ViewText( 'ddd' ) ); - viewList = new ViewElement( 'ul', null, [ viewListItem1, viewListItem2 ] ); + viewListItem1 = new ViewElement( viewDocument, 'li', null, [ new ViewText( viewDocument, 'aaa' ), viewListNested ] ); + viewListItem2 = new ViewElement( viewDocument, 'li', null, new ViewText( viewDocument, 'ddd' ) ); + viewList = new ViewElement( viewDocument, 'ul', null, [ viewListItem1, viewListItem2 ] ); - viewRoot = new ViewElement( 'div', null, viewList ); + viewRoot = new ViewElement( viewDocument, 'div', null, viewList ); mapper = new Mapper(); mapper.bindElements( modelRoot, viewRoot ); @@ -632,7 +639,7 @@ describe( 'Mapper', () => { } ); it( 'should bind element to a marker name', () => { - const view = new ViewElement( 'a' ); + const view = new ViewElement( viewDocument, 'a' ); mapper.bindElementToMarker( view, 'marker' ); @@ -644,9 +651,9 @@ describe( 'Mapper', () => { } ); it( 'should bind multiple elements to a marker name', () => { - const viewA = new ViewElement( 'a' ); - const viewB = new ViewElement( 'b' ); - const viewC = new ViewElement( 'c' ); + const viewA = new ViewElement( viewDocument, 'a' ); + const viewB = new ViewElement( viewDocument, 'b' ); + const viewC = new ViewElement( viewDocument, 'c' ); mapper.bindElementToMarker( viewA, 'marker' ); mapper.bindElementToMarker( viewB, 'marker' ); @@ -658,8 +665,8 @@ describe( 'Mapper', () => { } ); it( 'should unbind element from a marker name', () => { - const viewA = new ViewElement( 'a' ); - const viewB = new ViewElement( 'b' ); + const viewA = new ViewElement( viewDocument, 'a' ); + const viewB = new ViewElement( viewDocument, 'b' ); mapper.bindElementToMarker( viewA, 'marker' ); mapper.bindElementToMarker( viewA, 'markerB' ); @@ -701,7 +708,7 @@ describe( 'Mapper', () => { } ); it( 'should return length according to callback added by registerViewToModelLength', () => { - const viewElement = new ViewElement( 'span' ); + const viewElement = new ViewElement( viewDocument, 'span' ); mapper.registerViewToModelLength( 'span', () => 4 ); @@ -709,7 +716,7 @@ describe( 'Mapper', () => { } ); it( 'should return 1 for mapped elements', () => { - const viewElement = new ViewElement( 'span' ); + const viewElement = new ViewElement( viewDocument, 'span' ); const modelElement = new ModelElement( 'span' ); mapper.bindElements( modelElement, viewElement ); @@ -717,24 +724,24 @@ describe( 'Mapper', () => { } ); it( 'should return 0 for ui elements', () => { - const viewUiElement = new ViewUIElement( 'span' ); + const viewUiElement = new ViewUIElement( viewDocument, 'span' ); expect( mapper.getModelLength( viewUiElement ) ).to.equal( 0 ); } ); it( 'should return length of data for text nodes', () => { - const viewText = new ViewText( 'foo' ); + const viewText = new ViewText( viewDocument, 'foo' ); expect( mapper.getModelLength( viewText ) ).to.equal( 3 ); } ); it( 'should return sum of length of children for unmapped element', () => { const modelP = new ModelElement( 'p' ); - const viewP = new ViewElement( 'p' ); - const viewUi = new ViewUIElement( 'span' ); - const viewFoo = new ViewText( 'foo' ); - const viewCallback = new ViewElement( 'xxx' ); - const viewDiv = new ViewElement( 'div', null, [ viewP, viewUi, viewFoo, viewCallback ] ); + const viewP = new ViewElement( viewDocument, 'p' ); + const viewUi = new ViewUIElement( viewDocument, 'span' ); + const viewFoo = new ViewText( viewDocument, 'foo' ); + const viewCallback = new ViewElement( viewDocument, 'xxx' ); + const viewDiv = new ViewElement( viewDocument, 'div', null, [ viewP, viewUi, viewFoo, viewCallback ] ); mapper.bindElements( modelP, viewP ); mapper.registerViewToModelLength( 'xxx', () => 2 ); @@ -750,10 +757,10 @@ describe( 'Mapper', () => { const modelP = new ModelElement( 'p' ); const modelDiv = new ModelElement( 'div' ); - const viewText = new ViewText( 'foo' ); - const viewSpan = new ViewElement( 'span', null, viewText ); - const viewP = new ViewElement( 'p', null, viewSpan ); - const viewDiv = new ViewElement( 'div', null, viewP ); + const viewText = new ViewText( viewDocument, 'foo' ); + const viewSpan = new ViewElement( viewDocument, 'span', null, viewText ); + const viewP = new ViewElement( viewDocument, 'p', null, viewSpan ); + const viewDiv = new ViewElement( viewDocument, 'div', null, viewP ); mapper.bindElements( modelP, viewP ); mapper.bindElements( modelDiv, viewDiv ); @@ -770,8 +777,8 @@ describe( 'Mapper', () => { describe( 'flushUnboundMarkerNames()', () => { it( 'should return marker names of markers which elements has been unbound and clear that list', () => { - const viewA = new ViewElement( 'a' ); - const viewB = new ViewElement( 'b' ); + const viewA = new ViewElement( viewDocument, 'a' ); + const viewB = new ViewElement( viewDocument, 'b' ); const mapper = new Mapper(); diff --git a/tests/conversion/upcastdispatcher.js b/tests/conversion/upcastdispatcher.js index dc858e71a..b4a0856b6 100644 --- a/tests/conversion/upcastdispatcher.js +++ b/tests/conversion/upcastdispatcher.js @@ -8,6 +8,7 @@ import ViewContainerElement from '../../src/view/containerelement'; import ViewElement from '../../src/view/element'; import ViewDocumentFragment from '../../src/view/documentfragment'; import ViewText from '../../src/view/text'; +import ViewDocument from '../../src/view/document'; import Model from '../../src/model/model'; import ModelText from '../../src/model/text'; @@ -22,10 +23,11 @@ import first from '@ckeditor/ckeditor5-utils/src/first'; import { expectToThrowCKEditorError } from '@ckeditor/ckeditor5-utils/tests/_utils/utils'; describe( 'UpcastDispatcher', () => { - let model; + let model, viewDocument; beforeEach( () => { model = new Model(); + viewDocument = new ViewDocument(); } ); describe( 'constructor()', () => { @@ -56,7 +58,7 @@ describe( 'UpcastDispatcher', () => { } ); it( 'should create api for a conversion process', () => { - const viewElement = new ViewContainerElement( 'p', null, new ViewText( 'foobar' ) ); + const viewElement = new ViewContainerElement( viewDocument, 'p', null, new ViewText( viewDocument, 'foobar' ) ); // To be sure that both converters was called. const spy = sinon.spy(); @@ -108,16 +110,16 @@ describe( 'UpcastDispatcher', () => { it( 'should fire viewCleanup event on converted view part', () => { sinon.spy( dispatcher, 'fire' ); - const viewP = new ViewContainerElement( 'p' ); + const viewP = new ViewContainerElement( viewDocument, 'p' ); model.change( writer => dispatcher.convert( viewP, writer ) ); expect( dispatcher.fire.calledWith( 'viewCleanup', viewP ) ).to.be.true; } ); it( 'should fire proper events', () => { - const viewText = new ViewText( 'foobar' ); - const viewElement = new ViewContainerElement( 'p', null, viewText ); - const viewFragment = new ViewDocumentFragment( viewElement ); + const viewText = new ViewText( viewDocument, 'foobar' ); + const viewElement = new ViewContainerElement( viewDocument, 'p', null, viewText ); + const viewFragment = new ViewDocumentFragment( viewDocument, viewElement ); sinon.spy( dispatcher, 'fire' ); @@ -134,7 +136,7 @@ describe( 'UpcastDispatcher', () => { it( 'should convert ViewText', () => { const spy = sinon.spy(); - const viewText = new ViewText( 'foobar' ); + const viewText = new ViewText( viewDocument, 'foobar' ); dispatcher.on( 'text', ( evt, data, conversionApi ) => { // Check if this method has been fired. @@ -170,7 +172,7 @@ describe( 'UpcastDispatcher', () => { it( 'should convert ViewContainerElement', () => { const spy = sinon.spy(); - const viewElement = new ViewContainerElement( 'p', { attrKey: 'attrValue' } ); + const viewElement = new ViewContainerElement( viewDocument, 'p', { attrKey: 'attrValue' } ); dispatcher.on( 'element', ( evt, data, conversionApi ) => { // Check if this method has been fired. @@ -208,7 +210,7 @@ describe( 'UpcastDispatcher', () => { it( 'should convert ViewDocumentFragment', () => { const spy = sinon.spy(); - const viewFragment = new ViewDocumentFragment(); + const viewFragment = new ViewDocumentFragment( viewDocument ); dispatcher.on( 'documentFragment', ( evt, data, conversionApi ) => { // Check if this method has been fired. @@ -242,9 +244,9 @@ describe( 'UpcastDispatcher', () => { } ); it( 'should remove empty elements that was created as a result of split', () => { - const viewElement = new ViewElement( 'div', null, [ - new ViewElement( 'p', null, [ - new ViewElement( 'img' ) + const viewElement = new ViewElement( viewDocument, 'div', null, [ + new ViewElement( viewDocument, 'p', null, [ + new ViewElement( viewDocument, 'img' ) ] ) ] ); @@ -289,7 +291,7 @@ describe( 'UpcastDispatcher', () => { } ); it( 'should extract temporary markers elements from converter element and create static markers list', () => { - const viewFragment = new ViewDocumentFragment(); + const viewFragment = new ViewDocumentFragment( viewDocument ); dispatcher.on( 'documentFragment', ( evt, data, conversionApi ) => { // Create model fragment. @@ -326,7 +328,7 @@ describe( 'UpcastDispatcher', () => { dispatcher = new UpcastDispatcher( { schema: model.schema } ); const spy = sinon.spy(); - const viewElement = new ViewContainerElement( 'third' ); + const viewElement = new ViewContainerElement( viewDocument, 'third' ); let checkChildResult; model.schema.register( 'first', { @@ -377,8 +379,8 @@ describe( 'UpcastDispatcher', () => { spyP = sinon.spy(); spyText = sinon.spy(); - viewP = new ViewContainerElement( 'p' ); - viewText = new ViewText( 'foobar' ); + viewP = new ViewContainerElement( viewDocument, 'p' ); + viewText = new ViewText( viewDocument, 'foobar' ); modelP = new ModelElement( 'paragraph' ); modelText = new ModelText( 'foobar' ); @@ -404,9 +406,9 @@ describe( 'UpcastDispatcher', () => { spyNull = sinon.spy(); spyArray = sinon.spy(); - viewDiv = new ViewContainerElement( 'div' ); // Will not be recognized and not converted. - viewNull = new ViewContainerElement( 'null' ); // Will return `null` in `data.modelRange` upon conversion. - viewArray = new ViewContainerElement( 'array' ); // Will return an array in `data.modelRange` upon conversion. + viewDiv = new ViewContainerElement( viewDocument, 'div' ); // Will not be recognized and not converted. + viewNull = new ViewContainerElement( viewDocument, 'null' ); // Will return `null` in `data.modelRange` upon conversion. + viewArray = new ViewContainerElement( viewDocument, 'array' ); // Will return an array in `data.modelRange` upon conversion. dispatcher.on( 'element:null', ( evt, data ) => { spyNull(); @@ -444,7 +446,7 @@ describe( 'UpcastDispatcher', () => { expect( textResult.modelCursor.path ).to.deep.equal( [ 7 ] ); } ); - model.change( writer => dispatcher.convert( new ViewDocumentFragment(), writer ) ); + model.change( writer => dispatcher.convert( new ViewDocumentFragment( viewDocument ), writer ) ); expect( spy.calledOnce ).to.be.true; expect( spyP.calledOnce ).to.be.true; @@ -459,7 +461,7 @@ describe( 'UpcastDispatcher', () => { expect( conversionApi.convertItem( viewNull, data.modelCursor ).modelRange ).to.equal( null ); } ); - model.change( writer => dispatcher.convert( new ViewDocumentFragment(), writer ) ); + model.change( writer => dispatcher.convert( new ViewDocumentFragment( viewDocument ), writer ) ); expect( spy.calledOnce ).to.be.true; expect( spyNull.calledOnce ).to.be.true; @@ -473,7 +475,7 @@ describe( 'UpcastDispatcher', () => { } ); expectToThrowCKEditorError( () => { - model.change( writer => dispatcher.convert( new ViewDocumentFragment(), writer ) ); + model.change( writer => dispatcher.convert( new ViewDocumentFragment( viewDocument ), writer ) ); }, /^view-conversion-dispatcher-incorrect-result/, model ); expect( spy.calledOnce ).to.be.true; @@ -501,7 +503,7 @@ describe( 'UpcastDispatcher', () => { expect( result.modelCursor.path ).to.deep.equal( [ 7 ] ); } ); - model.change( writer => dispatcher.convert( new ViewDocumentFragment( [ viewP, viewText ] ), writer ) ); + model.change( writer => dispatcher.convert( new ViewDocumentFragment( viewDocument, [ viewP, viewText ] ), writer ) ); expect( spy.calledOnce ).to.be.true; expect( spyP.calledOnce ).to.be.true; @@ -534,7 +536,7 @@ describe( 'UpcastDispatcher', () => { spy(); } ); - model.change( writer => dispatcher.convert( new ViewDocumentFragment(), writer ) ); + model.change( writer => dispatcher.convert( new ViewDocumentFragment( viewDocument ), writer ) ); sinon.assert.calledOnce( spy ); } ); @@ -571,7 +573,7 @@ describe( 'UpcastDispatcher', () => { spy(); } ); - model.change( writer => dispatcher.convert( new ViewDocumentFragment(), writer ) ); + model.change( writer => dispatcher.convert( new ViewDocumentFragment( viewDocument ), writer ) ); sinon.assert.calledOnce( spy ); } ); @@ -591,7 +593,7 @@ describe( 'UpcastDispatcher', () => { spy(); } ); - model.change( writer => dispatcher.convert( new ViewDocumentFragment(), writer ) ); + model.change( writer => dispatcher.convert( new ViewDocumentFragment( viewDocument ), writer ) ); sinon.assert.calledOnce( spy ); } ); @@ -610,7 +612,7 @@ describe( 'UpcastDispatcher', () => { spy(); } ); - model.change( writer => dispatcher.convert( new ViewDocumentFragment(), writer, [ '$root', 'paragraph' ] ) ); + model.change( writer => dispatcher.convert( new ViewDocumentFragment( viewDocument ), writer, [ '$root', 'paragraph' ] ) ); sinon.assert.calledOnce( spy ); } ); } ); @@ -633,7 +635,7 @@ describe( 'UpcastDispatcher', () => { evt.stop(); }, { priority: 'high' } ); - const viewElement = new ViewElement( 'p' ); + const viewElement = new ViewElement( viewDocument, 'p' ); model.change( writer => dispatcher.convert( viewElement, writer ) ); @@ -695,12 +697,12 @@ describe( 'UpcastDispatcher', () => { evt.stop(); }, { priority: 'high' } ); - const viewElement = new ViewElement( 'p', null, [ - new ViewText( 'foo' ), - new ViewElement( 'image' ), - new ViewText( 'bar' ), - new ViewElement( 'image' ), - new ViewText( 'xyz' ) + const viewElement = new ViewElement( viewDocument, 'p', null, [ + new ViewText( viewDocument, 'foo' ), + new ViewElement( viewDocument, 'image' ), + new ViewText( viewDocument, 'bar' ), + new ViewElement( viewDocument, 'image' ), + new ViewText( viewDocument, 'xyz' ) ] ); model.change( writer => dispatcher.convert( viewElement, writer, [ '$root' ] ) ); diff --git a/tests/conversion/upcasthelpers.js b/tests/conversion/upcasthelpers.js index 7a0289f32..c5784080c 100644 --- a/tests/conversion/upcasthelpers.js +++ b/tests/conversion/upcasthelpers.js @@ -10,6 +10,7 @@ import ViewDocumentFragment from '../../src/view/documentfragment'; import ViewText from '../../src/view/text'; import ViewUIElement from '../../src/view/uielement'; import ViewAttributeElement from '../../src/view/attributeelement'; +import ViewDocument from '../../src/view/document'; import Model from '../../src/model/model'; import ModelDocumentFragment from '../../src/model/documentfragment'; @@ -29,10 +30,11 @@ import ViewSelection from '../../src/view/selection'; import ViewRange from '../../src/view/range'; describe( 'UpcastHelpers', () => { - let upcastDispatcher, model, schema, upcastHelpers; + let upcastDispatcher, model, schema, upcastHelpers, viewDocument; beforeEach( () => { model = new Model(); + viewDocument = new ViewDocument(); schema = model.schema; @@ -61,7 +63,7 @@ describe( 'UpcastHelpers', () => { it( 'config.view is a string', () => { upcastHelpers.elementToElement( { view: 'p', model: 'paragraph' } ); - expectResult( new ViewContainerElement( 'p' ), '' ); + expectResult( new ViewContainerElement( viewDocument, 'p' ), '' ); } ); it( 'can be overwritten using converterPriority', () => { @@ -72,7 +74,7 @@ describe( 'UpcastHelpers', () => { upcastHelpers.elementToElement( { view: 'p', model: 'p' } ); upcastHelpers.elementToElement( { view: 'p', model: 'paragraph', converterPriority: 'high' } ); - expectResult( new ViewContainerElement( 'p' ), '' ); + expectResult( new ViewContainerElement( viewDocument, 'p' ), '' ); } ); it( 'config.view is an object', () => { @@ -88,8 +90,8 @@ describe( 'UpcastHelpers', () => { model: 'fancyParagraph' } ); - expectResult( new ViewContainerElement( 'p', { class: 'fancy' } ), '' ); - expectResult( new ViewContainerElement( 'p' ), '' ); + expectResult( new ViewContainerElement( viewDocument, 'p', { class: 'fancy' } ), '' ); + expectResult( new ViewContainerElement( viewDocument, 'p' ), '' ); } ); it( 'config.model is a function', () => { @@ -108,8 +110,11 @@ describe( 'UpcastHelpers', () => { } } ); - expectResult( new ViewContainerElement( 'p', { class: 'heading', 'data-level': 2 } ), '' ); - expectResult( new ViewContainerElement( 'p', { 'data-level': 2 } ), '' ); + expectResult( + new ViewContainerElement( viewDocument, 'p', { class: 'heading', 'data-level': 2 } ), + '' + ); + expectResult( new ViewContainerElement( viewDocument, 'p', { 'data-level': 2 } ), '' ); } ); it( 'config.view is not set - should fire conversion for every element', () => { @@ -117,20 +122,23 @@ describe( 'UpcastHelpers', () => { model: 'paragraph' } ); - expectResult( new ViewContainerElement( 'p' ), '' ); - expectResult( new ViewContainerElement( 'foo' ), '' ); + expectResult( new ViewContainerElement( viewDocument, 'p' ), '' ); + expectResult( new ViewContainerElement( viewDocument, 'foo' ), '' ); } ); it( 'should fire conversion of the element children', () => { upcastHelpers.elementToElement( { view: 'p', model: 'paragraph' } ); - expectResult( new ViewContainerElement( 'p', null, new ViewText( 'foo' ) ), 'foo' ); + expectResult( + new ViewContainerElement( viewDocument, 'p', null, new ViewText( viewDocument, 'foo' ) ), + 'foo' + ); } ); it( 'should not insert a model element if it is not allowed by schema', () => { upcastHelpers.elementToElement( { view: 'h2', model: 'heading' } ); - expectResult( new ViewContainerElement( 'h2' ), '' ); + expectResult( new ViewContainerElement( viewDocument, 'h2' ), '' ); } ); it( 'should auto-break elements', () => { @@ -142,10 +150,10 @@ describe( 'UpcastHelpers', () => { upcastHelpers.elementToElement( { view: 'h2', model: 'heading' } ); expectResult( - new ViewContainerElement( 'p', null, [ - new ViewText( 'Foo' ), - new ViewContainerElement( 'h2', null, new ViewText( 'Xyz' ) ), - new ViewText( 'Bar' ) + new ViewContainerElement( viewDocument, 'p', null, [ + new ViewText( viewDocument, 'Foo' ), + new ViewContainerElement( viewDocument, 'h2', null, new ViewText( viewDocument, 'Xyz' ) ), + new ViewText( viewDocument, 'Bar' ) ] ), 'FooXyzBar' ); @@ -155,7 +163,7 @@ describe( 'UpcastHelpers', () => { upcastHelpers.elementToElement( { view: 'p', model: 'paragraph' } ); upcastHelpers.elementToElement( { view: 'p', model: () => null, converterPriority: 'high' } ); - expectResult( new ViewContainerElement( 'p' ), '' ); + expectResult( new ViewContainerElement( viewDocument, 'p' ), '' ); } ); } ); @@ -168,7 +176,7 @@ describe( 'UpcastHelpers', () => { upcastHelpers.elementToAttribute( { view: 'strong', model: 'bold' } ); expectResult( - new ViewAttributeElement( 'strong', null, new ViewText( 'foo' ) ), + new ViewAttributeElement( viewDocument, 'strong', null, new ViewText( viewDocument, 'foo' ) ), '<$text bold="true">foo' ); } ); @@ -178,7 +186,7 @@ describe( 'UpcastHelpers', () => { upcastHelpers.elementToAttribute( { view: 'strong', model: 'bold', converterPriority: 'high' } ); expectResult( - new ViewAttributeElement( 'strong', null, new ViewText( 'foo' ) ), + new ViewAttributeElement( viewDocument, 'strong', null, new ViewText( viewDocument, 'foo' ) ), '<$text bold="true">foo' ); } ); @@ -193,11 +201,11 @@ describe( 'UpcastHelpers', () => { } ); expectResult( - new ViewAttributeElement( 'span', { class: 'bold' }, new ViewText( 'foo' ) ), + new ViewAttributeElement( viewDocument, 'span', { class: 'bold' }, new ViewText( viewDocument, 'foo' ) ), '<$text bold="true">foo' ); - expectResult( new ViewAttributeElement( 'span', {}, new ViewText( 'foo' ) ), 'foo' ); + expectResult( new ViewAttributeElement( viewDocument, 'span', {}, new ViewText( viewDocument, 'foo' ) ), 'foo' ); } ); it( 'model attribute value is given', () => { @@ -217,11 +225,11 @@ describe( 'UpcastHelpers', () => { } ); expectResult( - new ViewAttributeElement( 'span', { class: 'styled styled-dark' }, new ViewText( 'foo' ) ), + new ViewAttributeElement( viewDocument, 'span', { class: 'styled styled-dark' }, new ViewText( viewDocument, 'foo' ) ), '<$text styled="dark">foo' ); - expectResult( new ViewAttributeElement( 'span', {}, new ViewText( 'foo' ) ), 'foo' ); + expectResult( new ViewAttributeElement( viewDocument, 'span', {}, new ViewText( viewDocument, 'foo' ) ), 'foo' ); } ); it( 'model attribute value is a function', () => { @@ -254,17 +262,17 @@ describe( 'UpcastHelpers', () => { } ); expectResult( - new ViewAttributeElement( 'span', { style: 'font-size:9px' }, new ViewText( 'foo' ) ), + new ViewAttributeElement( viewDocument, 'span', { style: 'font-size:9px' }, new ViewText( viewDocument, 'foo' ) ), '<$text fontSize="small">foo' ); expectResult( - new ViewAttributeElement( 'span', { style: 'font-size:12px' }, new ViewText( 'foo' ) ), + new ViewAttributeElement( viewDocument, 'span', { style: 'font-size:12px' }, new ViewText( viewDocument, 'foo' ) ), 'foo' ); expectResult( - new ViewAttributeElement( 'span', { style: 'font-size:14px' }, new ViewText( 'foo' ) ), + new ViewAttributeElement( viewDocument, 'span', { style: 'font-size:14px' }, new ViewText( viewDocument, 'foo' ) ), '<$text fontSize="big">foo' ); } ); @@ -273,7 +281,7 @@ describe( 'UpcastHelpers', () => { upcastHelpers.elementToAttribute( { view: 'em', model: 'italic' } ); expectResult( - new ViewAttributeElement( 'em', null, new ViewText( 'foo' ) ), + new ViewAttributeElement( viewDocument, 'em', null, new ViewText( viewDocument, 'foo' ) ), 'foo' ); } ); @@ -290,7 +298,7 @@ describe( 'UpcastHelpers', () => { } ); expectResult( - new ViewAttributeElement( 'strong', null, new ViewText( 'foo' ) ), + new ViewAttributeElement( viewDocument, 'strong', null, new ViewText( viewDocument, 'foo' ) ), '<$text bold="true">foo' ); } ); @@ -307,7 +315,12 @@ describe( 'UpcastHelpers', () => { } ); expectResult( - new ViewAttributeElement( 'span', { class: 'attrib-a', style: 'color:attrib-b;' }, new ViewText( 'foo' ) ), + new ViewAttributeElement( + viewDocument, + 'span', + { class: 'attrib-a', style: 'color:attrib-b;' }, + new ViewText( viewDocument, 'foo' ) + ), '<$text attribA="true" attribB="true">foo' ); } ); @@ -329,7 +342,7 @@ describe( 'UpcastHelpers', () => { } ); expectResult( - new ViewAttributeElement( 'strong', { class: 'foo' }, new ViewText( 'foo' ) ), + new ViewAttributeElement( viewDocument, 'strong', { class: 'foo' }, new ViewText( viewDocument, 'foo' ) ), '<$text attribB="true" bold="true">foo' ); } ); @@ -345,9 +358,10 @@ describe( 'UpcastHelpers', () => { expectResult( new ViewAttributeElement( + viewDocument, 'strong', null, - new ViewContainerElement( 'p', null, new ViewText( 'Foo' ) ) + new ViewContainerElement( viewDocument, 'p', null, new ViewText( viewDocument, 'Foo' ) ) ), '<$text bold="true">Foo' ); @@ -375,7 +389,7 @@ describe( 'UpcastHelpers', () => { upcastHelpers.attributeToAttribute( { view: 'src', model: 'source' } ); expectResult( - new ViewAttributeElement( 'img', { src: 'foo.jpg' } ), + new ViewAttributeElement( viewDocument, 'img', { src: 'foo.jpg' } ), '' ); } ); @@ -388,7 +402,7 @@ describe( 'UpcastHelpers', () => { upcastHelpers.attributeToAttribute( { view: { key: 'src' }, model: 'source' } ); expectResult( - new ViewAttributeElement( 'img', { src: 'foo.jpg' } ), + new ViewAttributeElement( viewDocument, 'img', { src: 'foo.jpg' } ), '' ); } ); @@ -401,7 +415,7 @@ describe( 'UpcastHelpers', () => { upcastHelpers.attributeToAttribute( { view: { name: 'img', key: 'src' }, model: { name: 'image', key: 'source' } } ); expectResult( - new ViewAttributeElement( 'img', { src: 'foo.jpg' } ), + new ViewAttributeElement( viewDocument, 'img', { src: 'foo.jpg' } ), '' ); } ); @@ -415,7 +429,7 @@ describe( 'UpcastHelpers', () => { upcastHelpers.attributeToAttribute( { view: { key: 'src' }, model: 'source', converterPriority: 'normal' } ); expectResult( - new ViewAttributeElement( 'img', { src: 'foo.jpg' } ), + new ViewAttributeElement( viewDocument, 'img', { src: 'foo.jpg' } ), '' ); } ); @@ -434,7 +448,7 @@ describe( 'UpcastHelpers', () => { } ); expectResult( - new ViewAttributeElement( 'img', { 'data-style': 'dark' } ), + new ViewAttributeElement( viewDocument, 'img', { 'data-style': 'dark' } ), '' ); } ); @@ -459,17 +473,17 @@ describe( 'UpcastHelpers', () => { upcastHelpers.elementToElement( { view: 'p', model: 'paragraph' } ); expectResult( - new ViewContainerElement( 'img', { class: 'styled-dark' } ), + new ViewContainerElement( viewDocument, 'img', { class: 'styled-dark' } ), '' ); expectResult( - new ViewContainerElement( 'img', { class: 'styled-xxx' } ), + new ViewContainerElement( viewDocument, 'img', { class: 'styled-xxx' } ), '' ); expectResult( - new ViewContainerElement( 'p', { class: 'styled-dark' } ), + new ViewContainerElement( viewDocument, 'p', { class: 'styled-dark' } ), '' ); } ); @@ -496,7 +510,7 @@ describe( 'UpcastHelpers', () => { } ); expectResult( - new ViewAttributeElement( 'img', { 'class': 'styled-dark' } ), + new ViewAttributeElement( viewDocument, 'img', { 'class': 'styled-dark' } ), '' ); } ); @@ -505,7 +519,7 @@ describe( 'UpcastHelpers', () => { upcastHelpers.attributeToAttribute( { view: 'src', model: 'source' } ); expectResult( - new ViewAttributeElement( 'img', { src: 'foo.jpg' } ), + new ViewAttributeElement( viewDocument, 'img', { src: 'foo.jpg' } ), '' ); } ); @@ -538,7 +552,7 @@ describe( 'UpcastHelpers', () => { } ); expectResult( - new ViewAttributeElement( 'img', { class: 'styled' } ), + new ViewAttributeElement( viewDocument, 'img', { class: 'styled' } ), '' ); } ); @@ -559,9 +573,10 @@ describe( 'UpcastHelpers', () => { expectResult( new ViewContainerElement( + viewDocument, 'div', { class: 'border' }, - new ViewContainerElement( 'div', { class: 'shade' } ) + new ViewContainerElement( viewDocument, 'div', { class: 'shade' } ) ), '
' ); @@ -576,12 +591,12 @@ describe( 'UpcastHelpers', () => { it( 'config.view is a string', () => { upcastHelpers.elementToMarker( { view: 'marker-search', model: 'search' } ); - const frag = new ViewDocumentFragment( [ - new ViewText( 'fo' ), - new ViewUIElement( 'marker-search' ), - new ViewText( 'oba' ), - new ViewUIElement( 'marker-search' ), - new ViewText( 'r' ) + const frag = new ViewDocumentFragment( viewDocument, [ + new ViewText( viewDocument, 'fo' ), + new ViewUIElement( viewDocument, 'marker-search' ), + new ViewText( viewDocument, 'oba' ), + new ViewUIElement( viewDocument, 'marker-search' ), + new ViewText( viewDocument, 'r' ) ] ); const marker = { name: 'search', start: [ 2 ], end: [ 5 ] }; @@ -593,12 +608,12 @@ describe( 'UpcastHelpers', () => { upcastHelpers.elementToMarker( { view: 'marker-search', model: 'search-result' } ); upcastHelpers.elementToMarker( { view: 'marker-search', model: 'search', converterPriority: 'high' } ); - const frag = new ViewDocumentFragment( [ - new ViewText( 'fo' ), - new ViewUIElement( 'marker-search' ), - new ViewText( 'oba' ), - new ViewUIElement( 'marker-search' ), - new ViewText( 'r' ) + const frag = new ViewDocumentFragment( viewDocument, [ + new ViewText( viewDocument, 'fo' ), + new ViewUIElement( viewDocument, 'marker-search' ), + new ViewText( viewDocument, 'oba' ), + new ViewUIElement( viewDocument, 'marker-search' ), + new ViewText( viewDocument, 'r' ) ] ); const marker = { name: 'search', start: [ 2 ], end: [ 5 ] }; @@ -615,12 +630,12 @@ describe( 'UpcastHelpers', () => { model: 'search' } ); - const frag = new ViewDocumentFragment( [ - new ViewText( 'f' ), - new ViewUIElement( 'span', { 'data-marker': 'search' } ), - new ViewText( 'oob' ), - new ViewUIElement( 'span', { 'data-marker': 'search' } ), - new ViewText( 'ar' ) + const frag = new ViewDocumentFragment( viewDocument, [ + new ViewText( viewDocument, 'f' ), + new ViewUIElement( viewDocument, 'span', { 'data-marker': 'search' } ), + new ViewText( viewDocument, 'oob' ), + new ViewUIElement( viewDocument, 'span', { 'data-marker': 'search' } ), + new ViewText( viewDocument, 'ar' ) ] ); const marker = { name: 'search', start: [ 1 ], end: [ 4 ] }; @@ -634,12 +649,12 @@ describe( 'UpcastHelpers', () => { model: viewElement => 'comment:' + viewElement.getAttribute( 'data-comment-id' ) } ); - const frag = new ViewDocumentFragment( [ - new ViewText( 'foo' ), - new ViewUIElement( 'comment', { 'data-comment-id': 4 } ), - new ViewText( 'b' ), - new ViewUIElement( 'comment', { 'data-comment-id': 4 } ), - new ViewText( 'ar' ) + const frag = new ViewDocumentFragment( viewDocument, [ + new ViewText( viewDocument, 'foo' ), + new ViewUIElement( viewDocument, 'comment', { 'data-comment-id': 4 } ), + new ViewText( viewDocument, 'b' ), + new ViewUIElement( viewDocument, 'comment', { 'data-comment-id': 4 } ), + new ViewText( viewDocument, 'ar' ) ] ); const marker = { name: 'comment:4', start: [ 3 ], end: [ 4 ] }; @@ -652,12 +667,12 @@ describe( 'UpcastHelpers', () => { upcastHelpers.elementToMarker( { view: 'marker-search', model: 'search' } ); - const element = new ViewContainerElement( 'p', null, [ - new ViewText( 'fo' ), - new ViewUIElement( 'marker-search' ), - new ViewText( 'oba' ), - new ViewUIElement( 'marker-search' ), - new ViewText( 'r' ) + const element = new ViewContainerElement( viewDocument, 'p', null, [ + new ViewText( viewDocument, 'fo' ), + new ViewUIElement( viewDocument, 'marker-search' ), + new ViewText( viewDocument, 'oba' ), + new ViewUIElement( viewDocument, 'marker-search' ), + new ViewText( viewDocument, 'r' ) ] ); const marker = { name: 'search', start: [ 0, 2 ], end: [ 0, 5 ] }; @@ -683,10 +698,11 @@ describe( 'UpcastHelpers', () => { } ); describe( 'upcast-converters', () => { - let dispatcher, schema, context, model; + let dispatcher, schema, context, model, viewDocument; beforeEach( () => { model = new Model(); + viewDocument = new ViewDocument(); schema = model.schema; schema.register( 'paragraph', { inheritAllFrom: '$block' } ); @@ -699,7 +715,7 @@ describe( 'upcast-converters', () => { describe( 'convertText()', () => { it( 'should return converter converting ViewText to ModelText', () => { - const viewText = new ViewText( 'foobar' ); + const viewText = new ViewText( viewDocument, 'foobar' ); dispatcher.on( 'text', convertText() ); @@ -711,7 +727,7 @@ describe( 'upcast-converters', () => { } ); it( 'should not convert already consumed texts', () => { - const viewText = new ViewText( 'foofuckbafuckr' ); + const viewText = new ViewText( viewDocument, 'foofuckbafuckr' ); // Default converter for elements. Returns just converted children. Added with lowest priority. dispatcher.on( 'text', convertText(), { priority: 'lowest' } ); @@ -739,7 +755,7 @@ describe( 'upcast-converters', () => { } } ); - const viewText = new ViewText( 'foobar' ); + const viewText = new ViewText( viewDocument, 'foobar' ); dispatcher.on( 'text', convertText() ); let conversionResult = model.change( writer => dispatcher.convert( viewText, writer, context ) ); @@ -755,7 +771,7 @@ describe( 'upcast-converters', () => { } ); it( 'should support unicode', () => { - const viewText = new ViewText( 'நிலைக்கு' ); + const viewText = new ViewText( viewDocument, 'நிலைக்கு' ); dispatcher.on( 'text', convertText() ); @@ -769,9 +785,9 @@ describe( 'upcast-converters', () => { describe( 'convertToModelFragment()', () => { it( 'should return converter converting whole ViewDocumentFragment to ModelDocumentFragment', () => { - const viewFragment = new ViewDocumentFragment( [ - new ViewContainerElement( 'p', null, new ViewText( 'foo' ) ), - new ViewText( 'bar' ) + const viewFragment = new ViewDocumentFragment( viewDocument, [ + new ViewContainerElement( viewDocument, 'p', null, new ViewText( viewDocument, 'foo' ) ), + new ViewText( viewDocument, 'bar' ) ] ); // To get any meaningful results we have to actually convert something. @@ -788,7 +804,7 @@ describe( 'upcast-converters', () => { } ); it( 'should not convert already consumed (converted) changes', () => { - const viewP = new ViewContainerElement( 'p', null, new ViewText( 'foo' ) ); + const viewP = new ViewContainerElement( viewDocument, 'p', null, new ViewText( viewDocument, 'foo' ) ); // To get any meaningful results we have to actually convert something. dispatcher.on( 'text', convertText() ); @@ -818,9 +834,12 @@ describe( 'upcast-converters', () => { it( 'should forward correct modelCursor', () => { const spy = sinon.spy(); - const view = new ViewDocumentFragment( [ - new ViewContainerElement( 'div', null, [ new ViewText( 'abc' ), new ViewContainerElement( 'foo' ) ] ), - new ViewContainerElement( 'bar' ) + const view = new ViewDocumentFragment( viewDocument, [ + new ViewContainerElement( viewDocument, 'div', null, [ + new ViewText( viewDocument, 'abc' ), + new ViewContainerElement( viewDocument, 'foo' ) + ] ), + new ViewContainerElement( viewDocument, 'bar' ) ] ); const position = ModelPosition._createAt( new ModelElement( 'element' ), 0 ); diff --git a/tests/conversion/viewconsumable.js b/tests/conversion/viewconsumable.js index a450f65a5..79f04bd80 100644 --- a/tests/conversion/viewconsumable.js +++ b/tests/conversion/viewconsumable.js @@ -3,6 +3,7 @@ * For licensing, see LICENSE.md or https://ckeditor.com/legal/ckeditor-oss-license */ +import ViewDocument from '../../src/view/document'; import ViewElement from '../../src/view/element'; import ViewText from '../../src/view/text'; import ViewDocumentFragment from '../../src/view/documentfragment'; @@ -13,11 +14,12 @@ import { addMarginRules } from '../../src/view/styles/margin'; import { addPaddingRules } from '../../src/view/styles/padding'; describe( 'ViewConsumable', () => { - let viewConsumable, el; + let viewConsumable, el, viewDocument; beforeEach( () => { + viewDocument = new ViewDocument(); viewConsumable = new ViewConsumable(); - el = new ViewElement( 'p' ); + el = new ViewElement( viewDocument, 'p' ); } ); describe( 'add', () => { @@ -28,14 +30,14 @@ describe( 'ViewConsumable', () => { } ); it( 'should allow to add text node', () => { - const text = new ViewText( 'foobar' ); + const text = new ViewText( viewDocument, 'foobar' ); viewConsumable.add( text ); expect( viewConsumable.test( text ) ).to.be.true; } ); it( 'should allow to add document fragment', () => { - const fragment = new ViewDocumentFragment(); + const fragment = new ViewDocumentFragment( viewDocument ); viewConsumable.add( fragment ); expect( viewConsumable.test( fragment ) ).to.be.true; } ); @@ -102,7 +104,7 @@ describe( 'ViewConsumable', () => { describe( 'test', () => { it( 'should test element name', () => { - const el2 = new ViewElement( 'p' ); + const el2 = new ViewElement( viewDocument, 'p' ); viewConsumable.add( el, { name: true } ); @@ -111,8 +113,8 @@ describe( 'ViewConsumable', () => { } ); it( 'should test text nodes', () => { - const text1 = new ViewText(); - const text2 = new ViewText(); + const text1 = new ViewText( viewDocument ); + const text2 = new ViewText( viewDocument ); viewConsumable.add( text1 ); @@ -121,8 +123,8 @@ describe( 'ViewConsumable', () => { } ); it( 'should test document fragments', () => { - const fragment1 = new ViewDocumentFragment(); - const fragment2 = new ViewDocumentFragment(); + const fragment1 = new ViewDocumentFragment( viewDocument ); + const fragment2 = new ViewDocumentFragment( viewDocument ); viewConsumable.add( fragment1 ); @@ -131,7 +133,7 @@ describe( 'ViewConsumable', () => { } ); it( 'should test attribute, classes and styles', () => { - const el = new ViewElement( 'p' ); + const el = new ViewElement( viewDocument, 'p' ); viewConsumable.add( el, { attributes: 'href', classes: 'foobar', styles: 'color' } ); @@ -241,7 +243,7 @@ describe( 'ViewConsumable', () => { } ); it( 'should consume text node', () => { - const text = new ViewText(); + const text = new ViewText( viewDocument ); viewConsumable.add( text ); const consumed = viewConsumable.consume( text ); expect( consumed ).to.be.true; @@ -250,7 +252,7 @@ describe( 'ViewConsumable', () => { } ); it( 'should consume document fragment', () => { - const fragment = new ViewDocumentFragment(); + const fragment = new ViewDocumentFragment( viewDocument ); viewConsumable.add( fragment ); const consumed = viewConsumable.consume( fragment ); expect( consumed ).to.be.true; @@ -357,8 +359,8 @@ describe( 'ViewConsumable', () => { } ); it( 'should revert text node', () => { - const text1 = new ViewText(); - const text2 = new ViewText(); + const text1 = new ViewText( viewDocument ); + const text2 = new ViewText( viewDocument ); viewConsumable.add( text1 ); viewConsumable.consume( text1 ); @@ -371,8 +373,8 @@ describe( 'ViewConsumable', () => { } ); it( 'should revert document fragment', () => { - const fragment1 = new ViewDocumentFragment(); - const fragment2 = new ViewDocumentFragment(); + const fragment1 = new ViewDocumentFragment( viewDocument ); + const fragment2 = new ViewDocumentFragment( viewDocument ); viewConsumable.add( fragment1 ); viewConsumable.consume( fragment1 ); @@ -528,7 +530,7 @@ describe( 'ViewConsumable', () => { } ); it( 'should return new ViewConsumable instance from document fragment', () => { - const fragment = new ViewDocumentFragment(); + const fragment = new ViewDocumentFragment( viewDocument ); const newConsumable = ViewConsumable.createFrom( fragment ); expect( newConsumable ).to.be.instanceof( ViewConsumable ); @@ -536,11 +538,11 @@ describe( 'ViewConsumable', () => { } ); it( 'should add all child elements', () => { - const text1 = new ViewText( 'foo' ); - const text2 = new ViewText( 'bar' ); - const child1 = new ViewElement( 'p', { 'title': 'baz' }, [ text1 ] ); - const child2 = new ViewElement( 'p' ); - const child3 = new ViewElement( 'p', { 'style': 'top:10px;', 'class': 'qux bar' }, [ text2, child2 ] ); + const text1 = new ViewText( viewDocument, 'foo' ); + const text2 = new ViewText( viewDocument, 'bar' ); + const child1 = new ViewElement( viewDocument, 'p', { 'title': 'baz' }, [ text1 ] ); + const child2 = new ViewElement( viewDocument, 'p' ); + const child3 = new ViewElement( viewDocument, 'p', { 'style': 'top:10px;', 'class': 'qux bar' }, [ text2, child2 ] ); el._appendChild( [ child1, child3 ] ); const newConsumable = ViewConsumable.createFrom( el ); diff --git a/tests/dev-utils/view.js b/tests/dev-utils/view.js index 87d2b665f..0086de817 100644 --- a/tests/dev-utils/view.js +++ b/tests/dev-utils/view.js @@ -6,6 +6,7 @@ /* globals document */ import { parse, stringify, getData, setData } from '../../src/dev-utils/view'; +import ViewDocument from '../../src/view/document'; import DocumentFragment from '../../src/view/documentfragment'; import Position from '../../src/view/position'; import Element from '../../src/view/element'; @@ -39,7 +40,7 @@ describe( 'view test utils', () => { renderUIElements: false }; const root = createAttachedRoot( viewDocument, element ); - root._appendChild( new Element( 'p' ) ); + root._appendChild( new Element( viewDocument, 'p' ) ); expect( getData( view, options ) ).to.equal( '

' ); sinon.assert.calledOnce( stringifySpy ); @@ -61,7 +62,7 @@ describe( 'view test utils', () => { const viewDocument = view.document; const options = { showType: false, showPriority: false }; const root = createAttachedRoot( viewDocument, element ); - root._appendChild( new Element( 'p' ) ); + root._appendChild( new Element( viewDocument, 'p' ) ); view.change( writer => { writer.setSelection( Range._createFromParentsAndOffsets( root, 0, root, 1 ) ); @@ -133,25 +134,31 @@ describe( 'view test utils', () => { } ); describe( 'stringify', () => { + let viewDocument; + + beforeEach( () => { + viewDocument = new ViewDocument(); + } ); + it( 'should write text', () => { - const text = new Text( 'foobar' ); + const text = new Text( viewDocument, 'foobar' ); expect( stringify( text ) ).to.equal( 'foobar' ); } ); it( 'should write elements and texts', () => { - const text = new Text( 'foobar' ); - const b = new Element( 'b', null, text ); - const p = new Element( 'p', null, b ); + const text = new Text( viewDocument, 'foobar' ); + const b = new Element( viewDocument, 'b', null, text ); + const p = new Element( viewDocument, 'p', null, b ); expect( stringify( p ) ).to.equal( '

foobar

' ); } ); it( 'should write elements with attributes (attributes in alphabetical order)', () => { - const text = new Text( 'foobar' ); - const b = new Element( 'b', { + const text = new Text( viewDocument, 'foobar' ); + const b = new Element( viewDocument, 'b', { foo: 'bar' }, text ); - const p = new Element( 'p', { + const p = new Element( viewDocument, 'p', { baz: 'qux', bar: 'taz', class: 'short wide' @@ -161,20 +168,20 @@ describe( 'view test utils', () => { } ); it( 'should write selection ranges inside elements', () => { - const text1 = new Text( 'foobar' ); - const text2 = new Text( 'bazqux' ); - const b1 = new Element( 'b', null, text1 ); - const b2 = new Element( 'b', null, text2 ); - const p = new Element( 'p', null, [ b1, b2 ] ); + const text1 = new Text( viewDocument, 'foobar' ); + const text2 = new Text( viewDocument, 'bazqux' ); + const b1 = new Element( viewDocument, 'b', null, text1 ); + const b2 = new Element( viewDocument, 'b', null, text2 ); + const p = new Element( viewDocument, 'p', null, [ b1, b2 ] ); const range = Range._createFromParentsAndOffsets( p, 1, p, 2 ); const selection = new DocumentSelection( [ range ] ); expect( stringify( p, selection ) ).to.equal( '

foobar[bazqux]

' ); } ); it( 'should support unicode', () => { - const text = new Text( 'நிலைக்கு' ); - const b = new Element( 'b', null, text ); - const p = new Element( 'p', null, b ); + const text = new Text( viewDocument, 'நிலைக்கு' ); + const b = new Element( viewDocument, 'b', null, text ); + const p = new Element( viewDocument, 'p', null, b ); const range = Range._createFromParentsAndOffsets( p, 0, text, 4 ); const selection = new DocumentSelection( [ range ] ); @@ -182,30 +189,30 @@ describe( 'view test utils', () => { } ); it( 'should write collapsed selection ranges inside elements', () => { - const text = new Text( 'foobar' ); - const p = new Element( 'p', null, text ); + const text = new Text( viewDocument, 'foobar' ); + const p = new Element( viewDocument, 'p', null, text ); const range = Range._createFromParentsAndOffsets( p, 0, p, 0 ); const selection = new DocumentSelection( [ range ] ); expect( stringify( p, selection ) ).to.equal( '

[]foobar

' ); } ); it( 'should write selection ranges inside text', () => { - const text1 = new Text( 'foobar' ); - const text2 = new Text( 'bazqux' ); - const b1 = new Element( 'b', null, text1 ); - const b2 = new Element( 'b', null, text2 ); - const p = new Element( 'p', null, [ b1, b2 ] ); + const text1 = new Text( viewDocument, 'foobar' ); + const text2 = new Text( viewDocument, 'bazqux' ); + const b1 = new Element( viewDocument, 'b', null, text1 ); + const b2 = new Element( viewDocument, 'b', null, text2 ); + const p = new Element( viewDocument, 'p', null, [ b1, b2 ] ); const range = Range._createFromParentsAndOffsets( text1, 1, text1, 5 ); const selection = new DocumentSelection( [ range ] ); expect( stringify( p, selection ) ).to.equal( '

f{ooba}rbazqux

' ); } ); it( 'should write selection ranges inside text represented by `[` and `]` characters', () => { - const text1 = new Text( 'foobar' ); - const text2 = new Text( 'bazqux' ); - const b1 = new Element( 'b', null, text1 ); - const b2 = new Element( 'b', null, text2 ); - const p = new Element( 'p', null, [ b1, b2 ] ); + const text1 = new Text( viewDocument, 'foobar' ); + const text2 = new Text( viewDocument, 'bazqux' ); + const b1 = new Element( viewDocument, 'b', null, text1 ); + const b2 = new Element( viewDocument, 'b', null, text2 ); + const p = new Element( viewDocument, 'p', null, [ b1, b2 ] ); const range = Range._createFromParentsAndOffsets( text1, 1, text1, 5 ); const selection = new DocumentSelection( [ range ] ); expect( stringify( p, selection, { sameSelectionCharacters: true } ) ) @@ -213,108 +220,108 @@ describe( 'view test utils', () => { } ); it( 'should write collapsed selection ranges inside texts', () => { - const text = new Text( 'foobar' ); - const p = new Element( 'p', null, text ); + const text = new Text( viewDocument, 'foobar' ); + const p = new Element( viewDocument, 'p', null, text ); const range = Range._createFromParentsAndOffsets( text, 0, text, 0 ); const selection = new DocumentSelection( [ range ] ); expect( stringify( p, selection ) ).to.equal( '

{}foobar

' ); } ); it( 'should write ranges that start inside text end ends between elements', () => { - const text1 = new Text( 'foobar' ); - const text2 = new Text( 'bazqux' ); - const b1 = new Element( 'b', null, text1 ); - const b2 = new Element( 'b', null, text2 ); - const p = new Element( 'p', null, [ b1, b2 ] ); + const text1 = new Text( viewDocument, 'foobar' ); + const text2 = new Text( viewDocument, 'bazqux' ); + const b1 = new Element( viewDocument, 'b', null, text1 ); + const b2 = new Element( viewDocument, 'b', null, text2 ); + const p = new Element( viewDocument, 'p', null, [ b1, b2 ] ); const range = Range._createFromParentsAndOffsets( p, 0, text2, 5 ); const selection = new DocumentSelection( [ range ] ); expect( stringify( p, selection ) ).to.equal( '

[foobarbazqu}x

' ); } ); it( 'should write elements types as namespaces when needed', () => { - const text = new Text( 'foobar' ); - const b = new AttributeElement( 'b', null, text ); - const p = new ContainerElement( 'p', null, b ); + const text = new Text( viewDocument, 'foobar' ); + const b = new AttributeElement( viewDocument, 'b', null, text ); + const p = new ContainerElement( viewDocument, 'p', null, b ); expect( stringify( p, null, { showType: true } ) ) .to.equal( 'foobar' ); } ); it( 'should not write element type when type is not specified', () => { - const p = new Element( 'p' ); + const p = new Element( viewDocument, 'p' ); expect( stringify( p, null, { showType: true } ) ).to.equal( '

' ); } ); it( 'should write elements priorities when needed', () => { - const text = new Text( 'foobar' ); - const b = new AttributeElement( 'b', null, text ); - const p = new ContainerElement( 'p', null, b ); + const text = new Text( viewDocument, 'foobar' ); + const b = new AttributeElement( viewDocument, 'b', null, text ); + const p = new ContainerElement( viewDocument, 'p', null, b ); expect( stringify( p, null, { showPriority: true } ) ) .to.equal( '

foobar

' ); } ); it( 'should write elements id when needed', () => { - const text = new Text( 'foobar' ); - const span = new AttributeElement( 'span', null, text ); + const text = new Text( viewDocument, 'foobar' ); + const span = new AttributeElement( viewDocument, 'span', null, text ); span._id = 'foo'; - const p = new ContainerElement( 'p', null, span ); + const p = new ContainerElement( viewDocument, 'p', null, span ); expect( stringify( p, null, { showAttributeElementId: true } ) ) .to.equal( '

foobar

' ); } ); it( 'should parse DocumentFragment as root', () => { - const text1 = new Text( 'foobar' ); - const text2 = new Text( 'bazqux' ); - const b1 = new Element( 'b', null, text1 ); - const b2 = new Element( 'b', null, text2 ); - const fragment = new DocumentFragment( [ b1, b2 ] ); + const text1 = new Text( viewDocument, 'foobar' ); + const text2 = new Text( viewDocument, 'bazqux' ); + const b1 = new Element( viewDocument, 'b', null, text1 ); + const b2 = new Element( viewDocument, 'b', null, text2 ); + const fragment = new DocumentFragment( viewDocument, [ b1, b2 ] ); expect( stringify( fragment, null ) ).to.equal( 'foobarbazqux' ); } ); it( 'should not write ranges outside elements - end position outside element', () => { - const text = new Text( 'foobar' ); - const b = new Element( 'b', null, text ); - const p = new Element( 'p', null, b ); + const text = new Text( viewDocument, 'foobar' ); + const b = new Element( viewDocument, 'b', null, text ); + const p = new Element( viewDocument, 'p', null, b ); const range = Range._createFromParentsAndOffsets( p, 0, p, 5 ); expect( stringify( p, range ) ).to.equal( '

[foobar

' ); } ); it( 'should not write ranges outside elements - start position outside element', () => { - const text = new Text( 'foobar' ); - const b = new Element( 'b', null, text ); - const p = new Element( 'p', null, b ); + const text = new Text( viewDocument, 'foobar' ); + const b = new Element( viewDocument, 'b', null, text ); + const p = new Element( viewDocument, 'p', null, b ); const range = Range._createFromParentsAndOffsets( p, -1, p, 1 ); expect( stringify( p, range ) ).to.equal( '

foobar]

' ); } ); it( 'should not write ranges outside elements - end position outside text', () => { - const text = new Text( 'foobar' ); - const b = new Element( 'b', null, text ); - const p = new Element( 'p', null, b ); + const text = new Text( viewDocument, 'foobar' ); + const b = new Element( viewDocument, 'b', null, text ); + const p = new Element( viewDocument, 'p', null, b ); const range = Range._createFromParentsAndOffsets( text, 0, text, 7 ); expect( stringify( p, range ) ).to.equal( '

{foobar

' ); } ); it( 'should not write ranges outside elements - start position outside text', () => { - const text = new Text( 'foobar' ); - const b = new Element( 'b', null, text ); - const p = new Element( 'p', null, b ); + const text = new Text( viewDocument, 'foobar' ); + const b = new Element( viewDocument, 'b', null, text ); + const p = new Element( viewDocument, 'p', null, b ); const range = Range._createFromParentsAndOffsets( text, -1, text, 2 ); expect( stringify( p, range ) ).to.equal( '

fo}obar

' ); } ); it( 'should write multiple ranges from selection #1', () => { - const text1 = new Text( 'foobar' ); - const text2 = new Text( 'bazqux' ); - const b1 = new Element( 'b', null, text1 ); - const b2 = new Element( 'b', null, text2 ); - const p = new Element( 'p', null, [ b1, b2 ] ); + const text1 = new Text( viewDocument, 'foobar' ); + const text2 = new Text( viewDocument, 'bazqux' ); + const b1 = new Element( viewDocument, 'b', null, text1 ); + const b2 = new Element( viewDocument, 'b', null, text2 ); + const p = new Element( viewDocument, 'p', null, [ b1, b2 ] ); const range1 = Range._createFromParentsAndOffsets( p, 0, p, 1 ); const range2 = Range._createFromParentsAndOffsets( p, 1, p, 1 ); const selection = new DocumentSelection( [ range2, range1 ] ); @@ -323,10 +330,10 @@ describe( 'view test utils', () => { } ); it( 'should write multiple ranges from selection #2', () => { - const text1 = new Text( 'foobar' ); - const text2 = new Text( 'bazqux' ); - const b = new Element( 'b', null, text1 ); - const p = new Element( 'p', null, [ b, text2 ] ); + const text1 = new Text( viewDocument, 'foobar' ); + const text2 = new Text( viewDocument, 'bazqux' ); + const b = new Element( viewDocument, 'b', null, text1 ); + const p = new Element( viewDocument, 'p', null, [ b, text2 ] ); const range1 = Range._createFromParentsAndOffsets( p, 0, p, 1 ); const range2 = Range._createFromParentsAndOffsets( text2, 0, text2, 3 ); const range3 = Range._createFromParentsAndOffsets( text2, 3, text2, 4 ); @@ -337,35 +344,35 @@ describe( 'view test utils', () => { } ); it( 'should use Position instance instead of Selection', () => { - const text = new Text( 'foobar' ); + const text = new Text( viewDocument, 'foobar' ); const position = new Position( text, 3 ); const string = stringify( text, position ); expect( string ).to.equal( 'foo{}bar' ); } ); it( 'should use Range instance instead of Selection', () => { - const text = new Text( 'foobar' ); + const text = new Text( viewDocument, 'foobar' ); const range = Range._createFromParentsAndOffsets( text, 3, text, 4 ); const string = stringify( text, range ); expect( string ).to.equal( 'foo{b}ar' ); } ); it( 'should stringify EmptyElement', () => { - const img = new EmptyElement( 'img' ); - const p = new ContainerElement( 'p', null, img ); + const img = new EmptyElement( viewDocument, 'img' ); + const p = new ContainerElement( viewDocument, 'p', null, img ); expect( stringify( p, null, { showType: true } ) ) .to.equal( '' ); } ); it( 'should stringify UIElement', () => { - const span = new UIElement( 'span' ); - const p = new ContainerElement( 'p', null, span ); + const span = new UIElement( viewDocument, 'span' ); + const p = new ContainerElement( viewDocument, 'p', null, span ); expect( stringify( p, null, { showType: true } ) ) .to.equal( '' ); } ); it( 'should not stringify inner UIElement content (renderUIElements=false)', () => { - const span = new UIElement( 'span' ); + const span = new UIElement( viewDocument, 'span' ); span.render = function( domDocument ) { const domElement = this.toDomElement( domDocument ); @@ -375,13 +382,13 @@ describe( 'view test utils', () => { return domElement; }; - const p = new ContainerElement( 'p', null, span ); + const p = new ContainerElement( viewDocument, 'p', null, span ); expect( stringify( p, null, { showType: true } ) ) .to.equal( '' ); } ); it( 'should stringify UIElement, (renderUIElements=true)', () => { - const span = new UIElement( 'span' ); + const span = new UIElement( viewDocument, 'span' ); span.render = function( domDocument ) { const domElement = this.toDomElement( domDocument ); @@ -391,14 +398,14 @@ describe( 'view test utils', () => { return domElement; }; - const p = new ContainerElement( 'p', null, span ); + const p = new ContainerElement( viewDocument, 'p', null, span ); expect( stringify( p, null, { showType: true, renderUIElements: true } ) ) .to.equal( 'foo' ); } ); it( 'should sort classes in specified element', () => { - const text = new Text( 'foobar' ); - const b = new Element( 'b', { + const text = new Text( viewDocument, 'foobar' ); + const b = new Element( viewDocument, 'b', { class: 'zz xx aa' }, text ); @@ -406,8 +413,8 @@ describe( 'view test utils', () => { } ); it( 'should sort styles in specified element', () => { - const text = new Text( 'foobar' ); - const i = new Element( 'i', { + const text = new Text( viewDocument, 'foobar' ); + const i = new Element( viewDocument, 'i', { style: 'text-decoration: underline; font-weight: bold' }, text ); @@ -416,6 +423,12 @@ describe( 'view test utils', () => { } ); describe( 'parse', () => { + let viewDocument; + + beforeEach( () => { + viewDocument = new ViewDocument(); + } ); + it( 'should return empty DocumentFragment for empty string', () => { const fragment = parse( '' ); @@ -445,8 +458,8 @@ describe( 'view test utils', () => { const view = parse( '' ); expect( view ).to.be.instanceOf( DocumentFragment ); expect( view.childCount ).to.equal( 2 ); - expect( view.getChild( 0 ).isSimilar( new Element( 'b' ) ) ).to.be.true; - expect( view.getChild( 1 ).isSimilar( new Element( 'i' ) ) ).to.be.true; + expect( view.getChild( 0 ).isSimilar( new Element( viewDocument, 'b' ) ) ).to.be.true; + expect( view.getChild( 1 ).isSimilar( new Element( viewDocument, 'i' ) ) ).to.be.true; } ); it( 'should parse text', () => { @@ -463,7 +476,7 @@ describe( 'view test utils', () => { it( 'should parse elements and texts', () => { const view = parse( 'foobar' ); - const element = new Element( 'b' ); + const element = new Element( viewDocument, 'b' ); expect( view ).to.be.instanceof( Element ); expect( view.isSimilar( element ) ).to.be.true; @@ -475,7 +488,7 @@ describe( 'view test utils', () => { it( 'should parse element attributes', () => { const view = parse( '' ); - const element = new Element( 'b', { name: 'foo', title: 'bar', class: 'foo bar', style: 'color:red;' } ); + const element = new Element( viewDocument, 'b', { name: 'foo', title: 'bar', class: 'foo bar', style: 'color:red;' } ); expect( view ).to.be.instanceof( Element ); expect( view.isSimilar( element ) ).to.be.true; @@ -484,9 +497,9 @@ describe( 'view test utils', () => { it( 'should parse element type', () => { const view1 = parse( '' ); - const attribute = new AttributeElement( 'b' ); + const attribute = new AttributeElement( viewDocument, 'b' ); const view2 = parse( '' ); - const container = new ContainerElement( 'p' ); + const container = new ContainerElement( viewDocument, 'p' ); expect( view1 ).to.be.instanceof( AttributeElement ); expect( view1.isSimilar( attribute ) ).to.be.true; @@ -496,10 +509,10 @@ describe( 'view test utils', () => { it( 'should parse element priority', () => { const parsed1 = parse( '' ); - const attribute1 = new AttributeElement( 'b' ); + const attribute1 = new AttributeElement( viewDocument, 'b' ); attribute1._priority = 12; const parsed2 = parse( '' ); - const attribute2 = new AttributeElement( 'b' ); + const attribute2 = new AttributeElement( viewDocument, 'b' ); attribute2._priority = 44; parsed1.isSimilar( attribute1 ); @@ -517,7 +530,7 @@ describe( 'view test utils', () => { it( 'should paste nested elements and texts', () => { const parsed = parse( 'foobarqux' ); - expect( parsed.isSimilar( new ContainerElement( 'p' ) ) ).to.be.true; + expect( parsed.isSimilar( new ContainerElement( viewDocument, 'p' ) ) ).to.be.true; expect( parsed.childCount ).to.equal( 2 ); expect( parsed.getChild( 0 ) ).to.be.instanceof( Text ).and.have.property( 'data' ).that.equal( 'foo' ); const b = parsed.getChild( 1 ); @@ -584,7 +597,7 @@ describe( 'view test utils', () => { it( 'should parse ranges #1', () => { const { view, selection } = parse( 'foo{bar]' ); - expect( view.isSimilar( new ContainerElement( 'p' ) ) ).to.be.true; + expect( view.isSimilar( new ContainerElement( viewDocument, 'p' ) ) ).to.be.true; expect( view.childCount ).to.equal( 1 ); const text = view.getChild( 0 ); expect( text ).to.be.instanceof( Text ); @@ -595,13 +608,13 @@ describe( 'view test utils', () => { it( 'should parse ranges #2', () => { const { view, selection } = parse( '[foob}ar{baz]' ); - expect( view.isSimilar( new AttributeElement( 'b' ) ) ).to.be.true; + expect( view.isSimilar( new AttributeElement( viewDocument, 'b' ) ) ).to.be.true; expect( view.childCount ).to.equal( 2 ); const text1 = view.getChild( 0 ); expect( text1 ).to.be.instanceof( Text ); expect( text1.data ).to.equal( 'foobar' ); const i = view.getChild( 1 ); - expect( i.isSimilar( new Element( 'i' ) ) ).to.be.true; + expect( i.isSimilar( new Element( viewDocument, 'i' ) ) ).to.be.true; expect( i.childCount ).to.equal( 1 ); const text2 = i.getChild( 0 ); expect( text2 ).to.be.instanceof( Text ); @@ -677,7 +690,7 @@ describe( 'view test utils', () => { } ); it( 'should throw when wrong type is provided', () => { - sinon.stub( XmlDataProcessor.prototype, 'toView' ).returns( new ContainerElement( 'invalidType:b' ) ); + sinon.stub( XmlDataProcessor.prototype, 'toView' ).returns( new ContainerElement( viewDocument, 'invalidType:b' ) ); expect( () => { parse( 'sth' ); @@ -687,14 +700,14 @@ describe( 'view test utils', () => { } ); it( 'should use provided root element #1', () => { - const root = new Element( 'p' ); + const root = new Element( viewDocument, 'p' ); const data = parse( 'text', { rootElement: root } ); expect( stringify( data ) ).to.equal( '

text

' ); } ); it( 'should use provided root element #2', () => { - const root = new Element( 'p' ); + const root = new Element( viewDocument, 'p' ); const data = parse( 'texttest', { rootElement: root } ); expect( stringify( data ) ).to.equal( '

texttest

' ); diff --git a/tests/view/_utils/createroot.js b/tests/view/_utils/createroot.js index a470bdbb7..fc7c98b0b 100644 --- a/tests/view/_utils/createroot.js +++ b/tests/view/_utils/createroot.js @@ -14,9 +14,8 @@ import RootEditableElement from '../../../src/view/rooteditableelement'; * @returns {module:engine/view/rooteditableelement~RootEditableElement} Root element. */ export default function createRoot( doc, name = 'div', rootName = 'main' ) { - const root = new RootEditableElement( name ); + const root = new RootEditableElement( doc, name ); - root._document = doc; root.rootName = rootName; doc.roots.add( root ); diff --git a/tests/view/attributeelement.js b/tests/view/attributeelement.js index e26dbc8de..472f7e25a 100644 --- a/tests/view/attributeelement.js +++ b/tests/view/attributeelement.js @@ -5,14 +5,20 @@ import AttributeElement from '../../src/view/attributeelement'; import Element from '../../src/view/element'; +import Document from '../../src/view/document'; import { parse } from '../../src/dev-utils/view'; - import { expectToThrowCKEditorError } from '@ckeditor/ckeditor5-utils/tests/_utils/utils'; describe( 'AttributeElement', () => { + let document; + + beforeEach( () => { + document = new Document(); + } ); + describe( 'constructor()', () => { it( 'should create element with default priority', () => { - const el = new AttributeElement( 'strong' ); + const el = new AttributeElement( document, 'strong' ); expect( el ).to.be.an.instanceof( AttributeElement ); expect( el ).to.be.an.instanceof( Element ); @@ -25,7 +31,7 @@ describe( 'AttributeElement', () => { let el; before( () => { - el = new AttributeElement( 'span' ); + el = new AttributeElement( document, 'span' ); } ); it( 'should return true for attributeElement/element, also with correct name and element name', () => { @@ -60,7 +66,7 @@ describe( 'AttributeElement', () => { describe( '_clone()', () => { it( 'should clone element with priority', () => { - const el = new AttributeElement( 'b' ); + const el = new AttributeElement( document, 'b' ); el._priority = 7; const clone = el._clone(); @@ -73,32 +79,32 @@ describe( 'AttributeElement', () => { describe( 'isSimilar', () => { it( 'should return true if priorities are the same', () => { - const b1 = new AttributeElement( 'b' ); + const b1 = new AttributeElement( document, 'b' ); b1._priority = 7; - const b2 = new AttributeElement( 'b' ); + const b2 = new AttributeElement( document, 'b' ); b2._priority = 7; expect( b1.isSimilar( b2 ) ).to.be.true; } ); it( 'should return false if priorities are different', () => { - const b1 = new AttributeElement( 'b' ); + const b1 = new AttributeElement( document, 'b' ); b1._priority = 7; - const b2 = new AttributeElement( 'b' ); // default priority + const b2 = new AttributeElement( document, 'b' ); // default priority expect( b1.isSimilar( b2 ) ).to.be.false; } ); it( 'should return true if ids are the same even if other properties are different', () => { - const element1 = new AttributeElement( 'b' ); + const element1 = new AttributeElement( document, 'b' ); element1._id = 'xyz'; - const element2 = new AttributeElement( 'b', { foo: 'bar' } ); + const element2 = new AttributeElement( document, 'b', { foo: 'bar' } ); element2._id = 'xyz'; - const element3 = new AttributeElement( 'span' ); + const element3 = new AttributeElement( document, 'span' ); element3._id = 'xyz'; expect( element1.isSimilar( element2 ) ).to.be.true; @@ -106,11 +112,11 @@ describe( 'AttributeElement', () => { } ); it( 'should return false if ids are different even if other properties are same', () => { - const element1 = new AttributeElement( 'span', { foo: 'bar' } ); + const element1 = new AttributeElement( document, 'span', { foo: 'bar' } ); element1._priority = 3; element1._id = 'foo'; - const element2 = new AttributeElement( 'span', { foo: 'bar' } ); + const element2 = new AttributeElement( document, 'span', { foo: 'bar' } ); element2._priority = 3; element2._id = 'bar'; @@ -121,8 +127,8 @@ describe( 'AttributeElement', () => { // More tests are available in DowncastWriter tests. describe( 'getElementsWithSameId', () => { it( 'should return a copy of _clonesGroup set', () => { - const attributeA = new AttributeElement( 'b' ); - const attributeB = new AttributeElement( 'b' ); + const attributeA = new AttributeElement( document, 'b' ); + const attributeB = new AttributeElement( document, 'b' ); attributeA._id = 'foo'; attributeB._id = 'foo'; @@ -135,7 +141,7 @@ describe( 'AttributeElement', () => { } ); it( 'should throw if attribute element has no id', () => { - const attribute = new AttributeElement( 'b' ); + const attribute = new AttributeElement( document, 'b' ); expectToThrowCKEditorError( () => { attribute.getElementsWithSameId(); @@ -194,7 +200,7 @@ describe( 'AttributeElement', () => { } ); it( 'should return null if there is no parent', () => { - const attribute = new AttributeElement( 'b' ); + const attribute = new AttributeElement( document, 'b' ); expect( attribute.getFillerOffset() ).to.be.null; } ); diff --git a/tests/view/containerelement.js b/tests/view/containerelement.js index ce70808d3..e088158b3 100644 --- a/tests/view/containerelement.js +++ b/tests/view/containerelement.js @@ -5,12 +5,19 @@ import { default as ContainerElement, getFillerOffset } from '../../src/view/containerelement'; import Element from '../../src/view/element'; +import Document from '../../src/view/document'; import { parse } from '../../src/dev-utils/view'; describe( 'ContainerElement', () => { + let document; + + beforeEach( () => { + document = new Document(); + } ); + describe( 'constructor()', () => { it( 'should create element with default priority', () => { - const el = new ContainerElement( 'p' ); + const el = new ContainerElement( document, 'p' ); expect( el ).to.be.an.instanceof( ContainerElement ); expect( el ).to.be.an.instanceof( Element ); @@ -22,7 +29,7 @@ describe( 'ContainerElement', () => { let el; before( () => { - el = new ContainerElement( 'p' ); + el = new ContainerElement( document, 'p' ); } ); it( 'should return true for containerElement/element, also with correct name and element name', () => { diff --git a/tests/view/documentfragment.js b/tests/view/documentfragment.js index f85a0bb19..d1a925d4e 100644 --- a/tests/view/documentfragment.js +++ b/tests/view/documentfragment.js @@ -8,27 +8,34 @@ import Element from '../../src/view/element'; import Node from '../../src/view/node'; import Text from '../../src/view/text'; import TextProxy from '../../src/view/textproxy'; +import Document from '../../src/view/document'; describe( 'DocumentFragment', () => { + let document; + + beforeEach( () => { + document = new Document(); + } ); + describe( 'constructor()', () => { it( 'should create DocumentFragment without children', () => { - const fragment = new DocumentFragment(); + const fragment = new DocumentFragment( document ); expect( fragment ).to.be.an.instanceof( DocumentFragment ); expect( fragment.childCount ).to.equal( 0 ); } ); - it( 'should create DocumentFragment with child node', () => { - const child = new Element( 'p' ); - const fragment = new DocumentFragment( child ); + it( 'should create DocumentFragment document,with child node', () => { + const child = new Element( document, 'p' ); + const fragment = new DocumentFragment( document, child ); expect( fragment.childCount ).to.equal( 1 ); expect( fragment.getChild( 0 ) ).to.have.property( 'name' ).that.equals( 'p' ); } ); - it( 'should create DocumentFragment with multiple nodes', () => { - const children = [ new Element( 'p' ), new Element( 'div' ) ]; - const fragment = new DocumentFragment( children ); + it( 'should create DocumentFragment document,with multiple nodes', () => { + const children = [ new Element( document, 'p' ), new Element( document, 'div' ) ]; + const fragment = new DocumentFragment( document, children ); expect( fragment.childCount ).to.equal( 2 ); expect( fragment.getChild( 0 ) ).to.have.property( 'name' ).that.equals( 'p' ); @@ -38,8 +45,8 @@ describe( 'DocumentFragment', () => { describe( 'iterator', () => { it( 'should iterate over all nodes added to document fragment', () => { - const children = [ new Element( 'p' ), new Element( 'div' ) ]; - const fragment = new DocumentFragment( children ); + const children = [ new Element( document, 'p' ), new Element( document, 'div' ) ]; + const fragment = new DocumentFragment( document, children ); const arr = Array.from( fragment ); @@ -51,7 +58,7 @@ describe( 'DocumentFragment', () => { describe( 'getRoot', () => { it( 'should return document fragment', () => { - const fragment = new DocumentFragment(); + const fragment = new DocumentFragment( document ); expect( fragment.root ).to.equal( fragment ); } ); @@ -59,13 +66,13 @@ describe( 'DocumentFragment', () => { describe( 'isEmpty', () => { it( 'should return true if there are no children in document fragment', () => { - const fragment = new DocumentFragment(); + const fragment = new DocumentFragment( document ); expect( fragment.isEmpty ).to.be.true; } ); it( 'should return false if there are children in document fragment', () => { - const fragment = new DocumentFragment( [ new Element( 'p' ) ] ); + const fragment = new DocumentFragment( document, [ new Element( document, 'p' ) ] ); expect( fragment.isEmpty ).to.be.false; } ); @@ -75,7 +82,7 @@ describe( 'DocumentFragment', () => { let frag; before( () => { - frag = new DocumentFragment(); + frag = new DocumentFragment( document ); } ); it( 'should return true for documentFragment', () => { @@ -102,11 +109,11 @@ describe( 'DocumentFragment', () => { let fragment, el1, el2, el3, el4; beforeEach( () => { - fragment = new DocumentFragment(); - el1 = new Element( 'el1' ); - el2 = new Element( 'el2' ); - el3 = new Element( 'el3' ); - el4 = new Element( 'el4' ); + fragment = new DocumentFragment( document ); + el1 = new Element( document, 'el1' ); + el2 = new Element( document, 'el2' ); + el3 = new Element( document, 'el3' ); + el4 = new Element( document, 'el4' ); } ); describe( 'insertion', () => { @@ -129,7 +136,7 @@ describe( 'DocumentFragment', () => { expect( fragment.getChild( 0 ) ).to.have.property( 'data' ).that.equals( 'abc' ); fragment._removeChildren( 0, 1 ); - fragment._insertChild( 0, [ new Element( 'p' ), 'abc' ] ); + fragment._insertChild( 0, [ new Element( document, 'p' ), 'abc' ] ); expect( fragment.childCount ).to.equal( 2 ); expect( fragment.getChild( 1 ) ).to.have.property( 'data' ).that.equals( 'abc' ); @@ -168,8 +175,8 @@ describe( 'DocumentFragment', () => { } ); it( 'should accept and correctly handle text proxies', () => { - const frag = new DocumentFragment(); - const text = new Text( 'abcxyz' ); + const frag = new DocumentFragment( document ); + const text = new Text( document, 'abcxyz' ); const textProxy = new TextProxy( text, 2, 3 ); frag._insertChild( 0, textProxy ); @@ -260,10 +267,10 @@ describe( 'DocumentFragment', () => { describe( 'node methods when inserted to fragment', () => { it( 'index should return proper value', () => { - const node1 = new Node(); - const node2 = new Node(); - const node3 = new Node(); - const fragment = new DocumentFragment( [ node1, node2, node3 ] ); + const node1 = new Node( document ); + const node2 = new Node( document ); + const node3 = new Node( document ); + const fragment = new DocumentFragment( document, [ node1, node2, node3 ] ); expect( node1.index ).to.equal( 0 ); expect( node2.index ).to.equal( 1 ); @@ -274,10 +281,10 @@ describe( 'DocumentFragment', () => { } ); it( 'nextSibling should return proper node', () => { - const node1 = new Node(); - const node2 = new Node(); - const node3 = new Node(); - new DocumentFragment( [ node1, node2, node3 ] ); // eslint-disable-line no-new + const node1 = new Node( document ); + const node2 = new Node( document ); + const node3 = new Node( document ); + new DocumentFragment( document, [ node1, node2, node3 ] ); // eslint-disable-line no-new expect( node1.nextSibling ).to.equal( node2 ); expect( node2.nextSibling ).to.equal( node3 ); @@ -285,10 +292,10 @@ describe( 'DocumentFragment', () => { } ); it( 'previousSibling should return proper node', () => { - const node1 = new Node(); - const node2 = new Node(); - const node3 = new Node(); - new DocumentFragment( [ node1, node2, node3 ] ); // eslint-disable-line no-new + const node1 = new Node( document ); + const node2 = new Node( document ); + const node3 = new Node( document ); + new DocumentFragment( document, [ node1, node2, node3 ] ); // eslint-disable-line no-new expect( node1.previousSibling ).to.be.null; expect( node2.previousSibling ).to.equal( node1 ); @@ -296,10 +303,10 @@ describe( 'DocumentFragment', () => { } ); it( '_remove() should remove node from fragment', () => { - const node1 = new Node(); - const node2 = new Node(); - const node3 = new Node(); - const fragment = new DocumentFragment( [ node1, node2, node3 ] ); + const node1 = new Node( document ); + const node2 = new Node( document ); + const node3 = new Node( document ); + const fragment = new DocumentFragment( document, [ node1, node2, node3 ] ); node1._remove(); node3._remove(); diff --git a/tests/view/documentselection.js b/tests/view/documentselection.js index aa86b81e9..4636f5bdf 100644 --- a/tests/view/documentselection.js +++ b/tests/view/documentselection.js @@ -17,13 +17,14 @@ import testUtils from '@ckeditor/ckeditor5-core/tests/_utils/utils'; import { expectToThrowCKEditorError } from '@ckeditor/ckeditor5-utils/tests/_utils/utils'; describe( 'DocumentSelection', () => { - let documentSelection, el, range1, range2, range3; + let documentSelection, el, range1, range2, range3, document; testUtils.createSinonSandbox(); beforeEach( () => { - const text = new Text( 'xxxxxxxxxxxxxxxxxxxx' ); - el = new Element( 'p', null, text ); + document = new Document(); + const text = new Text( document, 'xxxxxxxxxxxxxxxxxxxx' ); + el = new Element( document, 'p', null, text ); documentSelection = new DocumentSelection(); @@ -845,8 +846,8 @@ describe( 'DocumentSelection', () => { } ); it( 'should collapse selection at node and offset', () => { - const foo = new Text( 'foo' ); - const p = new Element( 'p', null, foo ); + const foo = new Text( document, 'foo' ); + const p = new Element( document, 'p', null, foo ); documentSelection._setTo( foo, 0 ); let range = documentSelection.getFirstRange(); @@ -864,7 +865,7 @@ describe( 'DocumentSelection', () => { } ); it( 'should throw an error when the second parameter is not passed and first is an item', () => { - const foo = new Text( 'foo' ); + const foo = new Text( document, 'foo' ); expectToThrowCKEditorError( () => { documentSelection._setTo( foo ); @@ -872,8 +873,8 @@ describe( 'DocumentSelection', () => { } ); it( 'should collapse selection at node and flag', () => { - const foo = new Text( 'foo' ); - const p = new Element( 'p', null, foo ); + const foo = new Text( document, 'foo' ); + const p = new Element( document, 'p', null, foo ); documentSelection._setTo( foo, 'end' ); let range = documentSelection.getFirstRange(); @@ -1029,10 +1030,10 @@ describe( 'DocumentSelection', () => { } ); it( 'should allow setting selection on an item', () => { - const textNode1 = new Text( 'foo' ); - const textNode2 = new Text( 'bar' ); - const textNode3 = new Text( 'baz' ); - const element = new Element( 'p', null, [ textNode1, textNode2, textNode3 ] ); + const textNode1 = new Text( document, 'foo' ); + const textNode2 = new Text( document, 'bar' ); + const textNode3 = new Text( document, 'baz' ); + const element = new Element( document, 'p', null, [ textNode1, textNode2, textNode3 ] ); documentSelection._setTo( textNode2, 'on' ); @@ -1045,7 +1046,7 @@ describe( 'DocumentSelection', () => { } ); it( 'should allow setting selection inside an element', () => { - const element = new Element( 'p', null, [ new Text( 'foo' ), new Text( 'bar' ) ] ); + const element = new Element( document, 'p', null, [ new Text( document, 'foo' ), new Text( document, 'bar' ) ] ); documentSelection._setTo( element, 'in' ); @@ -1058,7 +1059,7 @@ describe( 'DocumentSelection', () => { } ); it( 'should allow setting backward selection inside an element', () => { - const element = new Element( 'p', null, [ new Text( 'foo' ), new Text( 'bar' ) ] ); + const element = new Element( document, 'p', null, [ new Text( document, 'foo' ), new Text( document, 'bar' ) ] ); documentSelection._setTo( element, 'in', { backward: true } ); @@ -1087,7 +1088,7 @@ describe( 'DocumentSelection', () => { const viewDocument = new Document(); documentSelection._setTo( viewDocument.selection ); const root = createViewRoot( viewDocument, 'div', 'main' ); - const element = new Element( 'p' ); + const element = new Element( document, 'p' ); root._appendChild( element ); documentSelection._setTo( Range._createFromParentsAndOffsets( element, 0, element, 0 ) ); diff --git a/tests/view/domconverter/binding.js b/tests/view/domconverter/binding.js index c1160d908..0107baadd 100644 --- a/tests/view/domconverter/binding.js +++ b/tests/view/domconverter/binding.js @@ -9,6 +9,7 @@ import ViewElement from '../../../src/view/element'; import ViewDocumentSelection from '../../../src/view/documentselection'; import DomConverter from '../../../src/view/domconverter'; import ViewDocumentFragment from '../../../src/view/documentfragment'; +import ViewDocument from '../../../src/view/document'; import { INLINE_FILLER } from '../../../src/view/filler'; import { parse } from '../../../src/dev-utils/view'; @@ -16,16 +17,17 @@ import { parse } from '../../../src/dev-utils/view'; import createElement from '@ckeditor/ckeditor5-utils/src/dom/createelement'; describe( 'DomConverter', () => { - let converter; + let converter, viewDocument; before( () => { converter = new DomConverter(); + viewDocument = new ViewDocument(); } ); describe( 'bindElements()', () => { it( 'should bind elements', () => { const domElement = document.createElement( 'p' ); - const viewElement = new ViewElement( 'p' ); + const viewElement = new ViewElement( viewDocument, 'p' ); converter.bindElements( domElement, viewElement ); @@ -37,7 +39,7 @@ describe( 'DomConverter', () => { describe( 'bindDocumentFragments()', () => { it( 'should bind document fragments', () => { const domFragment = document.createDocumentFragment(); - const viewFragment = new ViewDocumentFragment(); + const viewFragment = new ViewDocumentFragment( viewDocument ); converter.bindDocumentFragments( domFragment, viewFragment ); @@ -49,7 +51,7 @@ describe( 'DomConverter', () => { describe( 'mapDomToView()', () => { it( 'should return corresponding view element if element is passed', () => { const domElement = document.createElement( 'p' ); - const viewElement = new ViewElement( 'p' ); + const viewElement = new ViewElement( viewDocument, 'p' ); converter.bindElements( domElement, viewElement ); @@ -77,7 +79,7 @@ describe( 'DomConverter', () => { const domText = document.createTextNode( 'foo' ); const domP = createElement( document, 'p', null, [ domImg, domText ] ); - const viewImg = new ViewElement( 'img' ); + const viewImg = new ViewElement( viewDocument, 'img' ); converter.bindElements( domImg, viewImg ); @@ -173,7 +175,7 @@ describe( 'DomConverter', () => { describe( 'mapViewToDom()', () => { it( 'should return corresponding DOM element if element was passed', () => { const domElement = document.createElement( 'p' ); - const viewElement = new ViewElement( 'p' ); + const viewElement = new ViewElement( viewDocument, 'p' ); converter.bindElements( domElement, viewElement ); @@ -182,7 +184,7 @@ describe( 'DomConverter', () => { it( 'should return corresponding DOM document fragment', () => { const domFragment = document.createDocumentFragment(); - const viewFragment = new ViewDocumentFragment(); + const viewFragment = new ViewDocumentFragment( viewDocument ); converter.bindElements( domFragment, viewFragment ); @@ -203,7 +205,7 @@ describe( 'DomConverter', () => { domP.appendChild( domImg ); domP.appendChild( domText ); - const viewImg = new ViewElement( 'img' ); + const viewImg = new ViewElement( viewDocument, 'img' ); converter.bindElements( domImg, viewImg ); @@ -267,7 +269,7 @@ describe( 'DomConverter', () => { let domEl, selection, viewElement; beforeEach( () => { - viewElement = new ViewElement(); + viewElement = new ViewElement( viewDocument ); domEl = document.createElement( 'div' ); selection = new ViewDocumentSelection( viewElement, 'in' ); converter.bindFakeSelection( domEl, selection ); @@ -282,7 +284,7 @@ describe( 'DomConverter', () => { it( 'should keep a copy of selection', () => { const selectionCopy = new ViewDocumentSelection( selection ); - selection._setTo( new ViewElement(), 'in', { backward: true } ); + selection._setTo( new ViewElement( viewDocument ), 'in', { backward: true } ); const bindSelection = converter.fakeSelectionToView( domEl ); expect( bindSelection ).to.not.equal( selection ); @@ -294,7 +296,7 @@ describe( 'DomConverter', () => { describe( 'unbindDomElement', () => { it( 'should unbind elements', () => { const domElement = document.createElement( 'p' ); - const viewElement = new ViewElement( 'p' ); + const viewElement = new ViewElement( viewDocument, 'p' ); converter.bindElements( domElement, viewElement ); @@ -312,8 +314,8 @@ describe( 'DomConverter', () => { const domChild = document.createElement( 'span' ); domElement.appendChild( domChild ); - const viewElement = new ViewElement( 'p' ); - const viewChild = new ViewElement( 'span' ); + const viewElement = new ViewElement( viewDocument, 'p' ); + const viewChild = new ViewElement( viewDocument, 'span' ); converter.bindElements( domElement, viewElement ); converter.bindElements( domChild, viewChild ); @@ -329,7 +331,7 @@ describe( 'DomConverter', () => { it( 'should do nothing if there are no elements bind', () => { const domElement = document.createElement( 'p' ); - const viewElement = new ViewElement( 'p' ); + const viewElement = new ViewElement( viewDocument, 'p' ); expect( converter.mapDomToView( domElement ) ).to.be.undefined; expect( converter.mapViewToDom( viewElement ) ).to.be.undefined; diff --git a/tests/view/domconverter/dom-to-view.js b/tests/view/domconverter/dom-to-view.js index 069eafaea..6bb9a68b2 100644 --- a/tests/view/domconverter/dom-to-view.js +++ b/tests/view/domconverter/dom-to-view.js @@ -6,6 +6,7 @@ /* globals document */ import ViewElement from '../../../src/view/element'; +import ViewDocument from '../../../src/view/document'; import ViewDocumentSelection from '../../../src/view/documentselection'; import DomConverter from '../../../src/view/domconverter'; import ViewDocumentFragment from '../../../src/view/documentfragment'; @@ -17,10 +18,11 @@ import count from '@ckeditor/ckeditor5-utils/src/count'; import createElement from '@ckeditor/ckeditor5-utils/src/dom/createelement'; describe( 'DomConverter', () => { - let converter; + let converter, viewDocument; before( () => { converter = new DomConverter(); + viewDocument = new ViewDocument(); } ); describe( 'domToView()', () => { @@ -29,7 +31,7 @@ describe( 'DomConverter', () => { const domText = document.createTextNode( 'foo' ); const domP = createElement( document, 'p', { 'class': 'foo' }, [ domImg, domText ] ); - const viewImg = new ViewElement( 'img' ); + const viewImg = new ViewElement( viewDocument, 'img' ); converter.bindElements( domImg, viewImg ); @@ -90,7 +92,7 @@ describe( 'DomConverter', () => { const domText = document.createTextNode( 'foo' ); const domP = createElement( document, 'p', { 'class': 'foo' }, [ domImg, domText ] ); - const viewImg = new ViewElement( 'img' ); + const viewImg = new ViewElement( viewDocument, 'img' ); converter.bindElements( domImg, viewImg ); @@ -133,7 +135,7 @@ describe( 'DomConverter', () => { domFragment.appendChild( domImg ); domFragment.appendChild( domText ); - const viewImg = new ViewElement( 'img' ); + const viewImg = new ViewElement( viewDocument, 'img' ); converter.bindElements( domImg, viewImg ); @@ -1001,7 +1003,7 @@ describe( 'DomConverter', () => { domContainer.innerHTML = 'fake selection container'; document.body.appendChild( domContainer ); - const viewSelection = new ViewDocumentSelection( new ViewElement(), 'in' ); + const viewSelection = new ViewDocumentSelection( new ViewElement( viewDocument ), 'in' ); converter.bindFakeSelection( domContainer, viewSelection ); const domRange = document.createRange(); @@ -1022,7 +1024,7 @@ describe( 'DomConverter', () => { domContainer.innerHTML = 'fake selection container'; document.body.appendChild( domContainer ); - const viewSelection = new ViewDocumentSelection( new ViewElement(), 'in' ); + const viewSelection = new ViewDocumentSelection( new ViewElement( viewDocument ), 'in' ); converter.bindFakeSelection( domContainer, viewSelection ); const domRange = document.createRange(); diff --git a/tests/view/domconverter/domconverter.js b/tests/view/domconverter/domconverter.js index a77701cc4..b9514654e 100644 --- a/tests/view/domconverter/domconverter.js +++ b/tests/view/domconverter/domconverter.js @@ -39,7 +39,7 @@ describe( 'DomConverter', () => { beforeEach( () => { viewDocument = new ViewDocument(); - viewEditable = new ViewEditable( 'div' ); + viewEditable = new ViewEditable( viewDocument, 'div' ); viewEditable._document = viewDocument; domEditable = document.createElement( 'div' ); @@ -192,7 +192,7 @@ describe( 'DomConverter', () => { return sel; } - let domP, domFillerTextNode, domUiSpan, domUiDeepSpan; + let domP, domFillerTextNode, domUiSpan, domUiDeepSpan, viewDocument; beforeEach( () => { //

INLINE_FILLERfoo

. @@ -203,8 +203,10 @@ describe( 'DomConverter', () => { domUiDeepSpan = document.createElement( 'span' ); domUiSpan.appendChild( domUiDeepSpan ); - const viewUiSpan = new ViewUIElement( 'span' ); - const viewElementSpan = new ViewContainerElement( 'span' ); + viewDocument = new ViewDocument(); + + const viewUiSpan = new ViewUIElement( viewDocument, 'span' ); + const viewElementSpan = new ViewContainerElement( viewDocument, 'span' ); domP.appendChild( domFillerTextNode ); domP.appendChild( domUiSpan ); diff --git a/tests/view/domconverter/uielement.js b/tests/view/domconverter/uielement.js index 88b6680ec..0faa4c230 100644 --- a/tests/view/domconverter/uielement.js +++ b/tests/view/domconverter/uielement.js @@ -8,12 +8,13 @@ import ViewUIElement from '../../../src/view/uielement'; import ViewContainer from '../../../src/view/containerelement'; import DomConverter from '../../../src/view/domconverter'; +import ViewDocument from '../../../src/view/document'; describe( 'DOMConverter UIElement integration', () => { - let converter; + let converter, viewDocument; function createUIElement( name ) { - const element = new ViewUIElement( name ); + const element = new ViewUIElement( viewDocument, name ); element.render = function( domDocument ) { const root = this.toDomElement( domDocument ); @@ -27,11 +28,12 @@ describe( 'DOMConverter UIElement integration', () => { beforeEach( () => { converter = new DomConverter(); + viewDocument = new ViewDocument(); } ); describe( 'viewToDom()', () => { it( 'should create DOM element from UIElement', () => { - const uiElement = new ViewUIElement( 'div' ); + const uiElement = new ViewUIElement( viewDocument, 'div' ); const domElement = converter.viewToDom( uiElement, document ); expect( domElement ).to.be.instanceOf( HTMLElement ); @@ -81,7 +83,7 @@ describe( 'DOMConverter UIElement integration', () => { describe( 'domPositionToView()', () => { it( 'should convert position inside UIElement to position before it', () => { const uiElement = createUIElement( 'h1' ); - const container = new ViewContainer( 'div', null, [ new ViewContainer( 'div' ), uiElement ] ); + const container = new ViewContainer( viewDocument, 'div', null, [ new ViewContainer( viewDocument, 'div' ), uiElement ] ); const domContainer = converter.viewToDom( container, document, { bind: true } ); const viewPosition = converter.domPositionToView( domContainer.childNodes[ 1 ], 0 ); @@ -92,7 +94,7 @@ describe( 'DOMConverter UIElement integration', () => { it( 'should convert position inside UIElement children to position before UIElement', () => { const uiElement = createUIElement( 'h1' ); - const container = new ViewContainer( 'div', null, [ new ViewContainer( 'div' ), uiElement ] ); + const container = new ViewContainer( viewDocument, 'div', null, [ new ViewContainer( viewDocument, 'div' ), uiElement ] ); const domContainer = converter.viewToDom( container, document, { bind: true } ); const viewPosition = converter.domPositionToView( domContainer.childNodes[ 1 ].childNodes[ 0 ], 1 ); diff --git a/tests/view/domconverter/view-to-dom.js b/tests/view/domconverter/view-to-dom.js index eae4f79d8..a08c5525d 100644 --- a/tests/view/domconverter/view-to-dom.js +++ b/tests/view/domconverter/view-to-dom.js @@ -13,6 +13,7 @@ import ViewAttributeElement from '../../../src/view/attributeelement'; import ViewEmptyElement from '../../../src/view/emptyelement'; import DomConverter from '../../../src/view/domconverter'; import ViewDocumentFragment from '../../../src/view/documentfragment'; +import ViewDocument from '../../../src/view/document'; import { INLINE_FILLER, INLINE_FILLER_LENGTH } from '../../../src/view/filler'; import { parse } from '../../../src/dev-utils/view'; @@ -20,17 +21,18 @@ import { parse } from '../../../src/dev-utils/view'; import createElement from '@ckeditor/ckeditor5-utils/src/dom/createelement'; describe( 'DomConverter', () => { - let converter; + let converter, viewDocument; before( () => { converter = new DomConverter(); + viewDocument = new ViewDocument(); } ); describe( 'viewToDom()', () => { it( 'should create tree of DOM elements from view elements', () => { - const viewImg = new ViewElement( 'img' ); - const viewText = new ViewText( 'foo' ); - const viewP = new ViewElement( 'p', { class: 'foo' } ); + const viewImg = new ViewElement( viewDocument, 'img' ); + const viewText = new ViewText( viewDocument, 'foo' ); + const viewP = new ViewElement( viewDocument, 'p', { class: 'foo' } ); viewP._appendChild( viewImg ); viewP._appendChild( viewText ); @@ -56,9 +58,9 @@ describe( 'DomConverter', () => { } ); it( 'should create tree of DOM elements from view elements and bind elements', () => { - const viewImg = new ViewElement( 'img' ); - const viewText = new ViewText( 'foo' ); - const viewP = new ViewElement( 'p', { class: 'foo' } ); + const viewImg = new ViewElement( viewDocument, 'img' ); + const viewText = new ViewText( viewDocument, 'foo' ); + const viewP = new ViewElement( viewDocument, 'p', { class: 'foo' } ); viewP._appendChild( viewImg ); viewP._appendChild( viewText ); @@ -80,8 +82,8 @@ describe( 'DomConverter', () => { } ); it( 'should support unicode', () => { - const viewText = new ViewText( 'நிலைக்கு' ); - const viewP = new ViewElement( 'p', null, viewText ); + const viewText = new ViewText( viewDocument, 'நிலைக்கு' ); + const viewP = new ViewElement( viewDocument, 'p', null, viewText ); const domP = converter.viewToDom( viewP, document, { bind: true } ); @@ -93,9 +95,9 @@ describe( 'DomConverter', () => { } ); it( 'should create tree of DOM elements from view element without children', () => { - const viewImg = new ViewElement( 'img' ); - const viewText = new ViewText( 'foo' ); - const viewP = new ViewElement( 'p', { class: 'foo' } ); + const viewImg = new ViewElement( viewDocument, 'img' ); + const viewText = new ViewText( viewDocument, 'foo' ); + const viewP = new ViewElement( viewDocument, 'p', { class: 'foo' } ); viewP._appendChild( viewImg ); viewP._appendChild( viewText ); @@ -117,9 +119,9 @@ describe( 'DomConverter', () => { } ); it( 'should create DOM document fragment from view document fragment and bind elements', () => { - const viewImg = new ViewElement( 'img' ); - const viewText = new ViewText( 'foo' ); - const viewFragment = new ViewDocumentFragment(); + const viewImg = new ViewElement( viewDocument, 'img' ); + const viewText = new ViewText( viewDocument, 'foo' ); + const viewFragment = new ViewDocumentFragment( viewDocument ); viewFragment._appendChild( viewImg ); viewFragment._appendChild( viewText ); @@ -136,9 +138,9 @@ describe( 'DomConverter', () => { } ); it( 'should create DOM document fragment from view document without children', () => { - const viewImg = new ViewElement( 'img' ); - const viewText = new ViewText( 'foo' ); - const viewFragment = new ViewDocumentFragment(); + const viewImg = new ViewElement( viewDocument, 'img' ); + const viewText = new ViewText( viewDocument, 'foo' ); + const viewFragment = new ViewDocumentFragment( viewDocument ); viewFragment._appendChild( viewImg ); viewFragment._appendChild( viewText ); @@ -157,7 +159,7 @@ describe( 'DomConverter', () => { it( 'should return already bind document fragment', () => { const domFragment = document.createDocumentFragment(); - const viewFragment = new ViewDocumentFragment(); + const viewFragment = new ViewDocumentFragment( viewDocument ); converter.bindDocumentFragments( domFragment, viewFragment ); @@ -167,7 +169,7 @@ describe( 'DomConverter', () => { } ); it( 'should create DOM text node from view text node', () => { - const viewTextNode = new ViewText( 'foo' ); + const viewTextNode = new ViewText( viewDocument, 'foo' ); const domTextNode = converter.viewToDom( viewTextNode, document ); expect( domTextNode ).to.be.instanceof( Text ); @@ -176,7 +178,7 @@ describe( 'DomConverter', () => { it( 'should create namespaced elements', () => { const namespace = 'http://www.w3.org/2000/svg'; - const viewSvg = new ViewElement( 'svg', { xmlns: namespace } ); + const viewSvg = new ViewElement( viewDocument, 'svg', { xmlns: namespace } ); const domSvg = converter.viewToDom( viewSvg, document ); @@ -185,10 +187,10 @@ describe( 'DomConverter', () => { describe( 'it should convert spaces to  ', () => { it( 'at the beginning of each container element', () => { - const viewDiv = new ViewContainerElement( 'div', null, [ - new ViewContainerElement( 'p', null, new ViewText( ' foo' ) ), - new ViewContainerElement( 'p', null, new ViewText( 'bar' ) ), - new ViewContainerElement( 'p', null, new ViewText( ' xxx' ) ) + const viewDiv = new ViewContainerElement( viewDocument, 'div', null, [ + new ViewContainerElement( viewDocument, 'p', null, new ViewText( viewDocument, ' foo' ) ), + new ViewContainerElement( viewDocument, 'p', null, new ViewText( viewDocument, 'bar' ) ), + new ViewContainerElement( viewDocument, 'p', null, new ViewText( viewDocument, ' xxx' ) ) ] ); const domDiv = converter.viewToDom( viewDiv, document ); @@ -197,10 +199,10 @@ describe( 'DomConverter', () => { } ); it( 'at the end of each container element', () => { - const viewDiv = new ViewContainerElement( 'div', null, [ - new ViewContainerElement( 'p', null, new ViewText( 'foo ' ) ), - new ViewContainerElement( 'p', null, new ViewText( 'bar' ) ), - new ViewContainerElement( 'p', null, new ViewText( 'xxx ' ) ) + const viewDiv = new ViewContainerElement( viewDocument, 'div', null, [ + new ViewContainerElement( viewDocument, 'p', null, new ViewText( viewDocument, 'foo ' ) ), + new ViewContainerElement( viewDocument, 'p', null, new ViewText( viewDocument, 'bar' ) ), + new ViewContainerElement( viewDocument, 'p', null, new ViewText( viewDocument, 'xxx ' ) ) ] ); const domDiv = converter.viewToDom( viewDiv, document ); @@ -209,12 +211,12 @@ describe( 'DomConverter', () => { } ); it( 'when there are multiple spaces next to each other or between attribute elements', () => { - const viewDiv = new ViewContainerElement( 'div', null, [ - new ViewText( 'x x x x ' ), - new ViewAttributeElement( 'b', null, new ViewText( ' x ' ) ), - new ViewAttributeElement( 'i', null, - new ViewAttributeElement( 'b', null, - new ViewAttributeElement( 'u', null, new ViewText( ' x' ) ) + const viewDiv = new ViewContainerElement( viewDocument, 'div', null, [ + new ViewText( viewDocument, 'x x x x ' ), + new ViewAttributeElement( viewDocument, 'b', null, new ViewText( viewDocument, ' x ' ) ), + new ViewAttributeElement( viewDocument, 'i', null, + new ViewAttributeElement( viewDocument, 'b', null, + new ViewAttributeElement( viewDocument, 'u', null, new ViewText( viewDocument, ' x' ) ) ) ) ] ); @@ -225,17 +227,17 @@ describe( 'DomConverter', () => { } ); it( 'all together', () => { - const viewDiv = new ViewContainerElement( 'div', null, [ - new ViewContainerElement( 'p', null, [ - new ViewText( ' x x x x ' ), - new ViewAttributeElement( 'b', null, new ViewText( ' x ' ) ), - new ViewAttributeElement( 'i', null, - new ViewAttributeElement( 'b', null, - new ViewAttributeElement( 'u', null, new ViewText( ' x ' ) ) + const viewDiv = new ViewContainerElement( viewDocument, 'div', null, [ + new ViewContainerElement( viewDocument, 'p', null, [ + new ViewText( viewDocument, ' x x x x ' ), + new ViewAttributeElement( viewDocument, 'b', null, new ViewText( viewDocument, ' x ' ) ), + new ViewAttributeElement( viewDocument, 'i', null, + new ViewAttributeElement( viewDocument, 'b', null, + new ViewAttributeElement( viewDocument, 'u', null, new ViewText( viewDocument, ' x ' ) ) ) ) ] ), - new ViewContainerElement( 'p', null, new ViewText( ' x ' ) ) + new ViewContainerElement( viewDocument, 'p', null, new ViewText( viewDocument, ' x ' ) ) ] ); const domDiv = converter.viewToDom( viewDiv, document ); @@ -251,10 +253,10 @@ describe( 'DomConverter', () => { } it( 'spaces in a text node: ' + inputTexts.join( '|' ) + ' -> ' + output, () => { - const viewElement = new ViewContainerElement( 'p' ); + const viewElement = new ViewContainerElement( viewDocument, 'p' ); for ( const text of inputTexts ) { - viewElement._appendChild( new ViewText( text.replace( /_/g, '\u00A0' ) ) ); + viewElement._appendChild( new ViewText( viewDocument, text.replace( /_/g, '\u00A0' ) ) ); } const domElement = converter.viewToDom( viewElement, document ); @@ -415,15 +417,18 @@ describe( 'DomConverter', () => { test( [ ' ', ' ' ], '_ _ __' ); it( 'not in preformatted blocks', () => { - const viewPre = new ViewContainerElement( 'pre', null, [ new ViewText( ' foo ' ), new ViewText( ' bar ' ) ] ); + const viewPre = new ViewContainerElement( viewDocument, 'pre', null, [ + new ViewText( viewDocument, ' foo ' ), + new ViewText( viewDocument, ' bar ' ) + ] ); const domPre = converter.viewToDom( viewPre, document ); expect( domPre.innerHTML ).to.equal( ' foo bar ' ); } ); it( 'not in a preformatted block followed by a text', () => { - const viewPre = new ViewAttributeElement( 'pre', null, new ViewText( 'foo ' ) ); - const viewDiv = new ViewContainerElement( 'div', null, [ viewPre, new ViewText( ' bar' ) ] ); + const viewPre = new ViewAttributeElement( viewDocument, 'pre', null, new ViewText( viewDocument, 'foo ' ) ); + const viewDiv = new ViewContainerElement( viewDocument, 'div', null, [ viewPre, new ViewText( viewDocument, ' bar' ) ] ); const domDiv = converter.viewToDom( viewDiv, document ); expect( domDiv.innerHTML ).to.equal( '
foo   
bar' ); @@ -431,10 +436,10 @@ describe( 'DomConverter', () => { describe( 'around
s', () => { it( 'before
– a single space', () => { - const viewDiv = new ViewContainerElement( 'div', null, [ - new ViewText( 'foo ' ), - new ViewEmptyElement( 'br' ), - new ViewText( 'bar' ) + const viewDiv = new ViewContainerElement( viewDocument, 'div', null, [ + new ViewText( viewDocument, 'foo ' ), + new ViewEmptyElement( viewDocument, 'br' ), + new ViewText( viewDocument, 'bar' ) ] ); const domDiv = converter.viewToDom( viewDiv, document ); @@ -442,10 +447,10 @@ describe( 'DomConverter', () => { } ); it( 'before
– two spaces', () => { - const viewDiv = new ViewContainerElement( 'div', null, [ - new ViewText( 'foo ' ), - new ViewEmptyElement( 'br' ), - new ViewText( 'bar' ) + const viewDiv = new ViewContainerElement( viewDocument, 'div', null, [ + new ViewText( viewDocument, 'foo ' ), + new ViewEmptyElement( viewDocument, 'br' ), + new ViewText( viewDocument, 'bar' ) ] ); const domDiv = converter.viewToDom( viewDiv, document ); @@ -453,10 +458,10 @@ describe( 'DomConverter', () => { } ); it( 'before
– three spaces', () => { - const viewDiv = new ViewContainerElement( 'div', null, [ - new ViewText( 'foo ' ), - new ViewEmptyElement( 'br' ), - new ViewText( 'bar' ) + const viewDiv = new ViewContainerElement( viewDocument, 'div', null, [ + new ViewText( viewDocument, 'foo ' ), + new ViewEmptyElement( viewDocument, 'br' ), + new ViewText( viewDocument, 'bar' ) ] ); const domDiv = converter.viewToDom( viewDiv, document ); @@ -464,10 +469,10 @@ describe( 'DomConverter', () => { } ); it( 'before
– only a space', () => { - const viewDiv = new ViewContainerElement( 'div', null, [ - new ViewText( ' ' ), - new ViewEmptyElement( 'br' ), - new ViewText( 'bar' ) + const viewDiv = new ViewContainerElement( viewDocument, 'div', null, [ + new ViewText( viewDocument, ' ' ), + new ViewEmptyElement( viewDocument, 'br' ), + new ViewText( viewDocument, 'bar' ) ] ); const domDiv = converter.viewToDom( viewDiv, document ); @@ -475,10 +480,10 @@ describe( 'DomConverter', () => { } ); it( 'before
– only two spaces', () => { - const viewDiv = new ViewContainerElement( 'div', null, [ - new ViewText( ' ' ), - new ViewEmptyElement( 'br' ), - new ViewText( 'bar' ) + const viewDiv = new ViewContainerElement( viewDocument, 'div', null, [ + new ViewText( viewDocument, ' ' ), + new ViewEmptyElement( viewDocument, 'br' ), + new ViewText( viewDocument, 'bar' ) ] ); const domDiv = converter.viewToDom( viewDiv, document ); @@ -486,10 +491,10 @@ describe( 'DomConverter', () => { } ); it( 'before
– only three spaces', () => { - const viewDiv = new ViewContainerElement( 'div', null, [ - new ViewText( ' ' ), - new ViewEmptyElement( 'br' ), - new ViewText( 'bar' ) + const viewDiv = new ViewContainerElement( viewDocument, 'div', null, [ + new ViewText( viewDocument, ' ' ), + new ViewEmptyElement( viewDocument, 'br' ), + new ViewText( viewDocument, 'bar' ) ] ); const domDiv = converter.viewToDom( viewDiv, document ); @@ -497,10 +502,10 @@ describe( 'DomConverter', () => { } ); it( 'after
– a single space', () => { - const viewDiv = new ViewContainerElement( 'div', null, [ - new ViewText( 'foo' ), - new ViewEmptyElement( 'br' ), - new ViewText( ' bar' ) + const viewDiv = new ViewContainerElement( viewDocument, 'div', null, [ + new ViewText( viewDocument, 'foo' ), + new ViewEmptyElement( viewDocument, 'br' ), + new ViewText( viewDocument, ' bar' ) ] ); const domDiv = converter.viewToDom( viewDiv, document ); @@ -508,10 +513,10 @@ describe( 'DomConverter', () => { } ); it( 'after
– two spaces', () => { - const viewDiv = new ViewContainerElement( 'div', null, [ - new ViewText( 'foo' ), - new ViewEmptyElement( 'br' ), - new ViewText( ' bar' ) + const viewDiv = new ViewContainerElement( viewDocument, 'div', null, [ + new ViewText( viewDocument, 'foo' ), + new ViewEmptyElement( viewDocument, 'br' ), + new ViewText( viewDocument, ' bar' ) ] ); const domDiv = converter.viewToDom( viewDiv, document ); @@ -519,10 +524,10 @@ describe( 'DomConverter', () => { } ); it( 'after
– three spaces', () => { - const viewDiv = new ViewContainerElement( 'div', null, [ - new ViewText( 'foo' ), - new ViewEmptyElement( 'br' ), - new ViewText( ' bar' ) + const viewDiv = new ViewContainerElement( viewDocument, 'div', null, [ + new ViewText( viewDocument, 'foo' ), + new ViewEmptyElement( viewDocument, 'br' ), + new ViewText( viewDocument, ' bar' ) ] ); const domDiv = converter.viewToDom( viewDiv, document ); @@ -530,10 +535,10 @@ describe( 'DomConverter', () => { } ); it( 'after
– only a space', () => { - const viewDiv = new ViewContainerElement( 'div', null, [ - new ViewText( 'foo' ), - new ViewEmptyElement( 'br' ), - new ViewText( ' ' ) + const viewDiv = new ViewContainerElement( viewDocument, 'div', null, [ + new ViewText( viewDocument, 'foo' ), + new ViewEmptyElement( viewDocument, 'br' ), + new ViewText( viewDocument, ' ' ) ] ); const domDiv = converter.viewToDom( viewDiv, document ); @@ -541,10 +546,10 @@ describe( 'DomConverter', () => { } ); it( 'after
– only two spaces', () => { - const viewDiv = new ViewContainerElement( 'div', null, [ - new ViewText( 'foo' ), - new ViewEmptyElement( 'br' ), - new ViewText( ' ' ) + const viewDiv = new ViewContainerElement( viewDocument, 'div', null, [ + new ViewText( viewDocument, 'foo' ), + new ViewEmptyElement( viewDocument, 'br' ), + new ViewText( viewDocument, ' ' ) ] ); const domDiv = converter.viewToDom( viewDiv, document ); @@ -552,10 +557,10 @@ describe( 'DomConverter', () => { } ); it( 'after
– only three spaces', () => { - const viewDiv = new ViewContainerElement( 'div', null, [ - new ViewText( 'foo' ), - new ViewEmptyElement( 'br' ), - new ViewText( ' ' ) + const viewDiv = new ViewContainerElement( viewDocument, 'div', null, [ + new ViewText( viewDocument, 'foo' ), + new ViewEmptyElement( viewDocument, 'br' ), + new ViewText( viewDocument, ' ' ) ] ); const domDiv = converter.viewToDom( viewDiv, document ); @@ -563,11 +568,11 @@ describe( 'DomConverter', () => { } ); it( 'between
s – a single space', () => { - const viewDiv = new ViewContainerElement( 'div', null, [ - new ViewEmptyElement( 'br' ), - new ViewText( ' ' ), - new ViewEmptyElement( 'br' ), - new ViewText( 'foo' ) + const viewDiv = new ViewContainerElement( viewDocument, 'div', null, [ + new ViewEmptyElement( viewDocument, 'br' ), + new ViewText( viewDocument, ' ' ), + new ViewEmptyElement( viewDocument, 'br' ), + new ViewText( viewDocument, 'foo' ) ] ); const domDiv = converter.viewToDom( viewDiv, document ); @@ -575,11 +580,11 @@ describe( 'DomConverter', () => { } ); it( 'between
s – only two spaces', () => { - const viewDiv = new ViewContainerElement( 'div', null, [ - new ViewEmptyElement( 'br' ), - new ViewText( ' ' ), - new ViewEmptyElement( 'br' ), - new ViewText( 'foo' ) + const viewDiv = new ViewContainerElement( viewDocument, 'div', null, [ + new ViewEmptyElement( viewDocument, 'br' ), + new ViewText( viewDocument, ' ' ), + new ViewEmptyElement( viewDocument, 'br' ), + new ViewText( viewDocument, 'foo' ) ] ); const domDiv = converter.viewToDom( viewDiv, document ); @@ -587,11 +592,11 @@ describe( 'DomConverter', () => { } ); it( 'between
s – only three spaces', () => { - const viewDiv = new ViewContainerElement( 'div', null, [ - new ViewEmptyElement( 'br' ), - new ViewText( ' ' ), - new ViewEmptyElement( 'br' ), - new ViewText( 'foo' ) + const viewDiv = new ViewContainerElement( viewDocument, 'div', null, [ + new ViewEmptyElement( viewDocument, 'br' ), + new ViewText( viewDocument, ' ' ), + new ViewEmptyElement( viewDocument, 'br' ), + new ViewText( viewDocument, 'foo' ) ] ); const domDiv = converter.viewToDom( viewDiv, document ); @@ -599,11 +604,11 @@ describe( 'DomConverter', () => { } ); it( 'between
s – space and text', () => { - const viewDiv = new ViewContainerElement( 'div', null, [ - new ViewEmptyElement( 'br' ), - new ViewText( ' foo' ), - new ViewEmptyElement( 'br' ), - new ViewText( 'foo' ) + const viewDiv = new ViewContainerElement( viewDocument, 'div', null, [ + new ViewEmptyElement( viewDocument, 'br' ), + new ViewText( viewDocument, ' foo' ), + new ViewEmptyElement( viewDocument, 'br' ), + new ViewText( viewDocument, 'foo' ) ] ); const domDiv = converter.viewToDom( viewDiv, document ); @@ -611,11 +616,11 @@ describe( 'DomConverter', () => { } ); it( 'between
s – text and space', () => { - const viewDiv = new ViewContainerElement( 'div', null, [ - new ViewEmptyElement( 'br' ), - new ViewText( 'foo ' ), - new ViewEmptyElement( 'br' ), - new ViewText( 'foo' ) + const viewDiv = new ViewContainerElement( viewDocument, 'div', null, [ + new ViewEmptyElement( viewDocument, 'br' ), + new ViewText( viewDocument, 'foo ' ), + new ViewEmptyElement( viewDocument, 'br' ), + new ViewText( viewDocument, 'foo' ) ] ); const domDiv = converter.viewToDom( viewDiv, document ); @@ -793,7 +798,7 @@ describe( 'DomConverter', () => { } ); it( 'should return null if view position is in a view text node that has not been rendered to DOM', () => { - const viewText = new ViewText( 'foo' ); + const viewText = new ViewText( viewDocument, 'foo' ); const viewPosition = new ViewPosition( viewText, 1 ); const domPosition = converter.viewPositionToDom( viewPosition ); @@ -801,7 +806,7 @@ describe( 'DomConverter', () => { } ); it( 'should return null if view position is in a view element that has not been rendered to DOM', () => { - const viewElement = new ViewContainerElement( 'div' ); + const viewElement = new ViewContainerElement( viewDocument, 'div' ); const viewPosition = new ViewPosition( viewElement, 0 ); const domPosition = converter.viewPositionToDom( viewPosition ); diff --git a/tests/view/editableelement.js b/tests/view/editableelement.js index ea66e7726..4b297ddf1 100644 --- a/tests/view/editableelement.js +++ b/tests/view/editableelement.js @@ -7,14 +7,14 @@ import createDocumentMock from '../../tests/view/_utils/createdocumentmock'; import EditableElement from '../../src/view/editableelement'; import Range from '../../src/view/range'; -import { expectToThrowCKEditorError } from '@ckeditor/ckeditor5-utils/tests/_utils/utils'; +import Document from '../../src/view/document'; describe( 'EditableElement', () => { describe( 'is', () => { let el; before( () => { - el = new EditableElement( 'div' ); + el = new EditableElement( new Document(), 'div' ); } ); it( 'should return true for containerElement/editable/element, also with correct name and element name', () => { @@ -52,58 +52,20 @@ describe( 'EditableElement', () => { } ); } ); - describe( 'document', () => { - let element, docMock; - - beforeEach( () => { - element = new EditableElement( 'div' ); - docMock = createDocumentMock(); - } ); - - it( 'should allow to set document', () => { - element._document = docMock; - - expect( element.document ).to.equal( docMock ); - } ); - - it( 'should return undefined if document is not set', () => { - expect( element.document ).to.be.undefined; - } ); - - it( 'should throw if trying to set document again', () => { - element._document = docMock; - const newDoc = createDocumentMock(); - - expectToThrowCKEditorError( () => { - element._document = newDoc; - }, 'view-editableelement-document-already-set: View document is already set.', docMock ); - } ); - - it( 'should be cloned properly', () => { - element._document = docMock; - const newElement = element._clone(); - - expect( newElement.document ).to.equal( docMock ); - } ); - } ); - describe( 'isFocused', () => { let docMock, viewMain, viewHeader; beforeEach( () => { docMock = createDocumentMock(); - viewMain = new EditableElement( 'div' ); - viewMain._document = docMock; + viewMain = new EditableElement( docMock, 'div' ); - viewHeader = new EditableElement( 'h1' ); - viewHeader._document = docMock; + viewHeader = new EditableElement( docMock, 'h1' ); viewHeader.rootName = 'header'; } ); it( 'should be observable', () => { - const root = new EditableElement( 'div' ); - root._document = createDocumentMock(); + const root = new EditableElement( docMock, 'div' ); expect( root.isFocused ).to.be.false; @@ -155,9 +117,14 @@ describe( 'EditableElement', () => { } ); describe( 'isReadOnly', () => { + let docMock; + + beforeEach( () => { + docMock = createDocumentMock(); + } ); + it( 'should be observable', () => { - const root = new EditableElement( 'div' ); - root._document = createDocumentMock(); + const root = new EditableElement( docMock, 'div' ); expect( root.isReadOnly ).to.be.false; @@ -173,8 +140,7 @@ describe( 'EditableElement', () => { } ); it( 'should be bound to the document#isReadOnly', () => { - const root = new EditableElement( 'div' ); - root._document = createDocumentMock(); + const root = new EditableElement( docMock, 'div' ); root.document.isReadOnly = false; @@ -186,13 +152,18 @@ describe( 'EditableElement', () => { } ); } ); - describe( 'getDocument', () => { - it( 'should return document', () => { - const docMock = createDocumentMock(); - const root = new EditableElement( 'div' ); - root._document = docMock; + describe( 'document', () => { + let element, docMock; + + beforeEach( () => { + docMock = createDocumentMock(); + element = new EditableElement( docMock, 'div' ); + } ); - expect( root.document ).to.equal( docMock ); + it( 'should be cloned properly', () => { + const newElement = element._clone(); + + expect( newElement.document ).to.equal( docMock ); } ); } ); } ); diff --git a/tests/view/element.js b/tests/view/element.js index da77ac34f..d221095c3 100644 --- a/tests/view/element.js +++ b/tests/view/element.js @@ -8,11 +8,18 @@ import Node from '../../src/view/node'; import Element from '../../src/view/element'; import Text from '../../src/view/text'; import TextProxy from '../../src/view/textproxy'; +import Document from '../../src/view/document'; describe( 'Element', () => { + let document; + + beforeEach( () => { + document = new Document(); + } ); + describe( 'constructor()', () => { it( 'should create element without attributes', () => { - const el = new Element( 'p' ); + const el = new Element( document, 'p' ); expect( el ).to.be.an.instanceof( Node ); expect( el ).to.have.property( 'name' ).that.equals( 'p' ); @@ -21,7 +28,7 @@ describe( 'Element', () => { } ); it( 'should create element with attributes as plain object', () => { - const el = new Element( 'p', { foo: 'bar' } ); + const el = new Element( document, 'p', { foo: 'bar' } ); expect( el ).to.have.property( 'name' ).that.equals( 'p' ); expect( count( el.getAttributeKeys() ) ).to.equal( 1 ); @@ -32,7 +39,7 @@ describe( 'Element', () => { const attrs = new Map(); attrs.set( 'foo', 'bar' ); - const el = new Element( 'p', attrs ); + const el = new Element( document, 'p', attrs ); expect( el ).to.have.property( 'name' ).that.equals( 'p' ); expect( count( el.getAttributeKeys() ) ).to.equal( 1 ); @@ -40,7 +47,7 @@ describe( 'Element', () => { } ); it( 'should stringify attributes', () => { - const el = new Element( 'p', { foo: true, bar: null, object: {} } ); + const el = new Element( document, 'p', { foo: true, bar: null, object: {} } ); expect( el.getAttribute( 'foo' ) ).to.equal( 'true' ); expect( el.getAttribute( 'bar' ) ).to.be.undefined; @@ -48,8 +55,8 @@ describe( 'Element', () => { } ); it( 'should create element with children', () => { - const child = new Element( 'p', { foo: 'bar' } ); - const parent = new Element( 'div', [], [ child ] ); + const child = new Element( document, 'p', { foo: 'bar' } ); + const parent = new Element( document, 'div', [], [ child ] ); expect( parent ).to.have.property( 'name' ).that.equals( 'div' ); expect( parent.childCount ).to.equal( 1 ); @@ -57,7 +64,7 @@ describe( 'Element', () => { } ); it( 'should move class attribute to class set ', () => { - const el = new Element( 'p', { id: 'test', class: 'one two three' } ); + const el = new Element( document, 'p', { id: 'test', class: 'one two three' } ); expect( el._attrs.has( 'class' ) ).to.be.false; expect( el._attrs.has( 'id' ) ).to.be.true; @@ -67,7 +74,7 @@ describe( 'Element', () => { } ); it( 'should move style attribute to style proxy', () => { - const el = new Element( 'p', { id: 'test', style: 'one: style1; two:style2 ; three : url(http://ckeditor.com)' } ); + const el = new Element( document, 'p', { id: 'test', style: 'one: style1; two:style2 ; three : url(http://ckeditor.com)' } ); expect( el._attrs.has( 'style' ) ).to.be.false; expect( el._attrs.has( 'id' ) ).to.be.true; @@ -85,7 +92,7 @@ describe( 'Element', () => { let el; before( () => { - el = new Element( 'p' ); + el = new Element( document, 'p' ); } ); it( 'should return true for node, element, element with correct name and element name', () => { @@ -120,13 +127,13 @@ describe( 'Element', () => { describe( 'isEmpty', () => { it( 'should return true if there are no children in element', () => { - const element = new Element( 'p' ); + const element = new Element( document, 'p' ); expect( element.isEmpty ).to.be.true; } ); it( 'should return false if there are children in element', () => { - const fragment = new Element( 'p', null, new Element( 'img' ) ); + const fragment = new Element( document, 'p', null, new Element( document, 'img' ) ); expect( fragment.isEmpty ).to.be.false; } ); @@ -134,7 +141,7 @@ describe( 'Element', () => { describe( '_clone()', () => { it( 'should clone element', () => { - const el = new Element( 'p', { attr1: 'foo', attr2: 'bar' } ); + const el = new Element( document, 'p', { attr1: 'foo', attr2: 'bar' } ); const clone = el._clone(); expect( clone ).to.not.equal( el ); @@ -144,9 +151,9 @@ describe( 'Element', () => { } ); it( 'should deeply clone element', () => { - const el = new Element( 'p', { attr1: 'foo', attr2: 'bar' }, [ - new Element( 'b', { attr: 'baz' } ), - new Element( 'span', { attr: 'qux' } ) + const el = new Element( document, 'p', { attr1: 'foo', attr2: 'bar' }, [ + new Element( document, 'b', { attr: 'baz' } ), + new Element( document, 'span', { attr: 'qux' } ) ] ); const count = el.childCount; const clone = el._clone( true ); @@ -168,9 +175,9 @@ describe( 'Element', () => { } ); it( 'shouldn\'t clone any children when deep copy is not performed', () => { - const el = new Element( 'p', { attr1: 'foo', attr2: 'bar' }, [ - new Element( 'b', { attr: 'baz' } ), - new Element( 'span', { attr: 'qux' } ) + const el = new Element( document, 'p', { attr1: 'foo', attr2: 'bar' }, [ + new Element( document, 'b', { attr: 'baz' } ), + new Element( document, 'span', { attr: 'qux' } ) ] ); const clone = el._clone( false ); @@ -182,7 +189,7 @@ describe( 'Element', () => { } ); it( 'should clone class attribute', () => { - const el = new Element( 'p', { foo: 'bar' } ); + const el = new Element( document, 'p', { foo: 'bar' } ); el._addClass( [ 'baz', 'qux' ] ); const clone = el._clone( false ); @@ -193,7 +200,7 @@ describe( 'Element', () => { } ); it( 'should clone style attribute', () => { - const el = new Element( 'p', { style: 'color: red; font-size: 12px;' } ); + const el = new Element( document, 'p', { style: 'color: red; font-size: 12px;' } ); const clone = el._clone( false ); expect( clone ).to.not.equal( el ); @@ -205,7 +212,7 @@ describe( 'Element', () => { } ); it( 'should clone custom properties', () => { - const el = new Element( 'p' ); + const el = new Element( document, 'p' ); const symbol = Symbol( 'custom' ); el._setCustomProperty( 'foo', 'bar' ); el._setCustomProperty( symbol, 'baz' ); @@ -217,7 +224,7 @@ describe( 'Element', () => { } ); it( 'should clone getFillerOffset', () => { - const el = new Element( 'p' ); + const el = new Element( document, 'p' ); const fm = () => 'foo bar'; expect( el.getFillerOffset ).to.be.undefined; @@ -230,7 +237,7 @@ describe( 'Element', () => { } ); describe( 'isSimilar()', () => { - const el = new Element( 'p', { foo: 'bar' } ); + const el = new Element( document, 'p', { foo: 'bar' } ); it( 'should return false when comparing to non-element', () => { expect( el.isSimilar( null ) ).to.be.false; expect( el.isSimilar( {} ) ).to.be.false; @@ -241,7 +248,7 @@ describe( 'Element', () => { } ); it( 'should return true for element with same attributes and name', () => { - const other = new Element( 'p', { foo: 'bar' } ); + const other = new Element( document, 'p', { foo: 'bar' } ); expect( el.isSimilar( other ) ).to.be.true; } ); @@ -265,10 +272,10 @@ describe( 'Element', () => { } ); it( 'should compare class attribute', () => { - const el1 = new Element( 'p' ); - const el2 = new Element( 'p' ); - const el3 = new Element( 'p' ); - const el4 = new Element( 'p' ); + const el1 = new Element( document, 'p' ); + const el2 = new Element( document, 'p' ); + const el3 = new Element( document, 'p' ); + const el4 = new Element( document, 'p' ); el1._addClass( [ 'foo', 'bar' ] ); el2._addClass( [ 'bar', 'foo' ] ); @@ -284,8 +291,8 @@ describe( 'Element', () => { let element, other; beforeEach( () => { - element = new Element( 'p' ); - other = new Element( 'p' ); + element = new Element( document, 'p' ); + other = new Element( document, 'p' ); element._setStyle( 'color', 'red' ); element._setStyle( 'top', '10px' ); @@ -338,11 +345,11 @@ describe( 'Element', () => { let parent, el1, el2, el3, el4; beforeEach( () => { - parent = new Element( 'p' ); - el1 = new Element( 'el1' ); - el2 = new Element( 'el2' ); - el3 = new Element( 'el3' ); - el4 = new Element( 'el4' ); + parent = new Element( document, 'p' ); + el1 = new Element( document, 'el1' ); + el2 = new Element( document, 'el2' ); + el3 = new Element( document, 'el3' ); + el4 = new Element( document, 'el4' ); } ); describe( 'insertion', () => { @@ -365,7 +372,7 @@ describe( 'Element', () => { expect( parent.getChild( 0 ) ).to.have.property( 'data' ).that.equals( 'abc' ); parent._removeChildren( 0, 1 ); - parent._insertChild( 0, [ new Element( 'p' ), 'abc' ] ); + parent._insertChild( 0, [ new Element( document, 'p' ), 'abc' ] ); expect( parent.childCount ).to.equal( 2 ); expect( parent.getChild( 1 ) ).to.have.property( 'data' ).that.equals( 'abc' ); @@ -386,8 +393,8 @@ describe( 'Element', () => { } ); it( 'should accept and correctly handle text proxies', () => { - const element = new Element( 'div' ); - const text = new Text( 'abcxyz' ); + const element = new Element( document, 'div' ); + const text = new Text( document, 'abcxyz' ); const textProxy = new TextProxy( text, 2, 3 ); element._insertChild( 0, textProxy ); @@ -469,7 +476,7 @@ describe( 'Element', () => { let el; beforeEach( () => { - el = new Element( 'p' ); + el = new Element( document, 'p' ); } ); describe( '_setAttribute', () => { @@ -662,7 +669,7 @@ describe( 'Element', () => { it( 'should remove class attribute', () => { el._addClass( [ 'foo', 'bar' ] ); - const el2 = new Element( 'p' ); + const el2 = new Element( document, 'p' ); const removed1 = el._removeAttribute( 'class' ); const removed2 = el2._removeAttribute( 'class' ); @@ -676,7 +683,7 @@ describe( 'Element', () => { it( 'should remove style attribute', () => { el._setStyle( 'color', 'red' ); el._setStyle( 'position', 'fixed' ); - const el2 = new Element( 'p' ); + const el2 = new Element( document, 'p' ); const removed1 = el._removeAttribute( 'style' ); const removed2 = el2._removeAttribute( 'style' ); @@ -693,7 +700,7 @@ describe( 'Element', () => { let el; beforeEach( () => { - el = new Element( 'p' ); + el = new Element( document, 'p' ); } ); describe( '_addClass()', () => { @@ -791,7 +798,7 @@ describe( 'Element', () => { let el; beforeEach( () => { - el = new Element( 'p' ); + el = new Element( document, 'p' ); } ); describe( '_setStyle()', () => { @@ -919,29 +926,29 @@ describe( 'Element', () => { describe( 'findAncestor', () => { it( 'should return null if element have no ancestor', () => { - const el = new Element( 'p' ); + const el = new Element( document, 'p' ); expect( el.findAncestor( 'div' ) ).to.be.null; } ); it( 'should return ancestor if matching', () => { - const el1 = new Element( 'p' ); - const el2 = new Element( 'div', null, el1 ); + const el1 = new Element( document, 'p' ); + const el2 = new Element( document, 'div', null, el1 ); expect( el1.findAncestor( 'div' ) ).to.equal( el2 ); } ); it( 'should return parent\'s ancestor if matching', () => { - const el1 = new Element( 'p' ); - const el2 = new Element( 'div', null, el1 ); - const el3 = new Element( 'div', { class: 'foo bar' }, el2 ); + const el1 = new Element( document, 'p' ); + const el2 = new Element( document, 'div', null, el1 ); + const el3 = new Element( document, 'div', { class: 'foo bar' }, el2 ); expect( el1.findAncestor( { classes: 'foo' } ) ).to.equal( el3 ); } ); it( 'should return null if no matches found', () => { - const el1 = new Element( 'p' ); - new Element( 'div', null, el1 ); // eslint-disable-line no-new + const el1 = new Element( document, 'p' ); + new Element( document, 'div', null, el1 ); // eslint-disable-line no-new expect( el1.findAncestor( { name: 'div', @@ -952,14 +959,14 @@ describe( 'Element', () => { describe( 'custom properties', () => { it( 'should allow to set and get custom properties', () => { - const el = new Element( 'p' ); + const el = new Element( document, 'p' ); el._setCustomProperty( 'foo', 'bar' ); expect( el.getCustomProperty( 'foo' ) ).to.equal( 'bar' ); } ); it( 'should allow to add symbol property', () => { - const el = new Element( 'p' ); + const el = new Element( document, 'p' ); const symbol = Symbol( 'custom' ); el._setCustomProperty( symbol, 'bar' ); @@ -967,7 +974,7 @@ describe( 'Element', () => { } ); it( 'should allow to remove custom property', () => { - const el = new Element( 'foo' ); + const el = new Element( document, 'foo' ); const symbol = Symbol( 'quix' ); el._setCustomProperty( 'bar', 'baz' ); el._setCustomProperty( symbol, 'test' ); @@ -983,7 +990,7 @@ describe( 'Element', () => { } ); it( 'should allow to iterate over custom properties', () => { - const el = new Element( 'p' ); + const el = new Element( document, 'p' ); el._setCustomProperty( 'foo', 1 ); el._setCustomProperty( 'bar', 2 ); el._setCustomProperty( 'baz', 3 ); @@ -1001,20 +1008,20 @@ describe( 'Element', () => { describe( 'getIdentity()', () => { it( 'should return only name if no other attributes are present', () => { - const el = new Element( 'foo' ); + const el = new Element( document, 'foo' ); expect( el.getIdentity() ).to.equal( 'foo' ); } ); it( 'should return classes in sorted order', () => { - const el = new Element( 'fruit' ); + const el = new Element( document, 'fruit' ); el._addClass( [ 'banana', 'lemon', 'apple' ] ); expect( el.getIdentity() ).to.equal( 'fruit class="apple,banana,lemon"' ); } ); it( 'should return styles in sorted order', () => { - const el = new Element( 'foo', { + const el = new Element( document, 'foo', { style: 'margin-top: 2em; background-color: red' } ); @@ -1022,7 +1029,7 @@ describe( 'Element', () => { } ); it( 'should return attributes in sorted order', () => { - const el = new Element( 'foo', { + const el = new Element( document, 'foo', { a: 1, d: 4, b: 3 @@ -1032,7 +1039,7 @@ describe( 'Element', () => { } ); it( 'should return classes, styles and attributes', () => { - const el = new Element( 'baz', { + const el = new Element( document, 'baz', { foo: 'one', bar: 'two', style: 'text-align:center;border-radius:10px' diff --git a/tests/view/emptyelement.js b/tests/view/emptyelement.js index 577d6f6d7..50c7e4456 100644 --- a/tests/view/emptyelement.js +++ b/tests/view/emptyelement.js @@ -5,15 +5,17 @@ import EmptyElement from '../../src/view/emptyelement'; import Element from '../../src/view/element'; +import Document from '../../src/view/document'; import { expectToThrowCKEditorError } from '@ckeditor/ckeditor5-utils/tests/_utils/utils'; describe( 'EmptyElement', () => { - let element, emptyElement; + let element, emptyElement, document; beforeEach( () => { - element = new Element( 'b' ); - emptyElement = new EmptyElement( 'img', { + document = new Document(); + element = new Element( document, 'b' ); + emptyElement = new EmptyElement( document, 'img', { alt: 'alternative text', style: 'margin-top: 2em;color: white;', class: 'image big' @@ -24,7 +26,7 @@ describe( 'EmptyElement', () => { let el; before( () => { - el = new EmptyElement( 'p' ); + el = new EmptyElement( document, 'p' ); } ); it( 'should return true for emptyElement/element, also with correct name and element name', () => { @@ -59,10 +61,10 @@ describe( 'EmptyElement', () => { } ); it( 'should throw if child elements are passed to constructor', () => { - const el = new Element( 'i' ); + const el = new Element( document, 'i' ); expectToThrowCKEditorError( () => { - new EmptyElement( 'img', null, [ el ] ); // eslint-disable-line no-new + new EmptyElement( document, 'img', null, [ el ] ); // eslint-disable-line no-new }, 'view-emptyelement-cannot-add: Cannot add child nodes to EmptyElement instance.', el ); } ); diff --git a/tests/view/matcher.js b/tests/view/matcher.js index 42d2171df..e5ff5c4cd 100644 --- a/tests/view/matcher.js +++ b/tests/view/matcher.js @@ -5,12 +5,19 @@ import Matcher from '../../src/view/matcher'; import Element from '../../src/view/element'; +import Document from '../../src/view/document'; describe( 'Matcher', () => { + let document; + + beforeEach( () => { + document = new Document(); + } ); + describe( 'add', () => { it( 'should allow to add pattern to matcher', () => { const matcher = new Matcher( 'div' ); - const el = new Element( 'p', { title: 'foobar' } ); + const el = new Element( document, 'p', { title: 'foobar' } ); expect( matcher.match( el ) ).to.be.null; const pattern = { name: 'p', attributes: { title: 'foobar' } }; @@ -26,8 +33,8 @@ describe( 'Matcher', () => { it( 'should allow to add more than one pattern', () => { const matcher = new Matcher(); - const el1 = new Element( 'p' ); - const el2 = new Element( 'div' ); + const el1 = new Element( document, 'p' ); + const el2 = new Element( document, 'div' ); matcher.add( 'p', 'div' ); @@ -46,8 +53,8 @@ describe( 'Matcher', () => { describe( 'match', () => { it( 'should match element name', () => { const matcher = new Matcher( 'p' ); - const el = new Element( 'p' ); - const el2 = new Element( 'div' ); + const el = new Element( document, 'p' ); + const el2 = new Element( document, 'div' ); const result = matcher.match( el ); @@ -63,8 +70,8 @@ describe( 'Matcher', () => { it( 'should match element name with RegExp', () => { const pattern = /^text...a$/; const matcher = new Matcher( pattern ); - const el1 = new Element( 'textarea' ); - const el2 = new Element( 'div' ); + const el1 = new Element( document, 'textarea' ); + const el2 = new Element( document, 'div' ); const result = matcher.match( el1 ); @@ -82,9 +89,9 @@ describe( 'Matcher', () => { } }; const matcher = new Matcher( pattern ); - const el1 = new Element( 'p', { title: 'foobar' } ); - const el2 = new Element( 'p', { title: 'foobaz' } ); - const el3 = new Element( 'p', { name: 'foobar' } ); + const el1 = new Element( document, 'p', { title: 'foobar' } ); + const el2 = new Element( document, 'p', { title: 'foobaz' } ); + const el3 = new Element( document, 'p', { name: 'foobar' } ); const result = matcher.match( el1 ); @@ -106,9 +113,9 @@ describe( 'Matcher', () => { } }; const matcher = new Matcher( pattern ); - const el1 = new Element( 'p', { title: 'foobar' } ); - const el2 = new Element( 'p', { title: 'foobaz' } ); - const el3 = new Element( 'p', { title: 'qux' } ); + const el1 = new Element( document, 'p', { title: 'foobar' } ); + const el2 = new Element( document, 'p', { title: 'foobaz' } ); + const el3 = new Element( document, 'p', { title: 'qux' } ); let result = matcher.match( el1 ); expect( result ).to.be.an( 'object' ); @@ -133,9 +140,9 @@ describe( 'Matcher', () => { } }; const matcher = new Matcher( pattern ); - const el1 = new Element( 'p', { title: 'foobar' } ); - const el2 = new Element( 'p', { title: '' } ); - const el3 = new Element( 'p' ); + const el1 = new Element( document, 'p', { title: 'foobar' } ); + const el2 = new Element( document, 'p', { title: '' } ); + const el3 = new Element( document, 'p' ); let result = matcher.match( el1 ); expect( result ).to.be.an( 'object' ); @@ -157,7 +164,7 @@ describe( 'Matcher', () => { it( 'should match element class names', () => { const pattern = { classes: 'foobar' }; const matcher = new Matcher( pattern ); - const el1 = new Element( 'p', { class: 'foobar' } ); + const el1 = new Element( document, 'p', { class: 'foobar' } ); const result = matcher.match( el1 ); expect( result ).to.be.an( 'object' ); @@ -171,9 +178,9 @@ describe( 'Matcher', () => { it( 'should match element class names using RegExp', () => { const pattern = { classes: /fooba./ }; const matcher = new Matcher( pattern ); - const el1 = new Element( 'p', { class: 'foobar' } ); - const el2 = new Element( 'p', { class: 'foobaz' } ); - const el3 = new Element( 'p', { class: 'qux' } ); + const el1 = new Element( document, 'p', { class: 'foobar' } ); + const el2 = new Element( document, 'p', { class: 'foobaz' } ); + const el3 = new Element( document, 'p', { class: 'qux' } ); let result = matcher.match( el1 ); expect( result ).to.be.an( 'object' ); @@ -198,8 +205,8 @@ describe( 'Matcher', () => { } }; const matcher = new Matcher( pattern ); - const el1 = new Element( 'p', { style: 'color: red' } ); - const el2 = new Element( 'p', { style: 'position: absolute' } ); + const el1 = new Element( document, 'p', { style: 'color: red' } ); + const el2 = new Element( document, 'p', { style: 'position: absolute' } ); const result = matcher.match( el1 ); expect( result ).to.be.an( 'object' ); @@ -218,9 +225,9 @@ describe( 'Matcher', () => { } }; const matcher = new Matcher( pattern ); - const el1 = new Element( 'p', { style: 'color: blue' } ); - const el2 = new Element( 'p', { style: 'color: darkblue' } ); - const el3 = new Element( 'p', { style: 'color: red' } ); + const el1 = new Element( document, 'p', { style: 'color: blue' } ); + const el2 = new Element( document, 'p', { style: 'color: darkblue' } ); + const el3 = new Element( document, 'p', { style: 'color: red' } ); let result = matcher.match( el1 ); expect( result ).to.be.an( 'object' ); @@ -248,8 +255,8 @@ describe( 'Matcher', () => { return null; }; const matcher = new Matcher( pattern ); - const el1 = new Element( 'p' ); - const el2 = new Element( 'div', null, [ el1 ] ); + const el1 = new Element( document, 'p' ); + const el2 = new Element( document, 'div', null, [ el1 ] ); expect( matcher.match( el1 ) ).to.be.null; const result = matcher.match( el2 ); @@ -262,9 +269,9 @@ describe( 'Matcher', () => { const pattern = { name: 'p' }; - const el1 = new Element( 'div' ); - const el2 = new Element( 'p' ); - const el3 = new Element( 'span' ); + const el1 = new Element( document, 'div' ); + const el2 = new Element( document, 'p' ); + const el3 = new Element( document, 'span' ); const matcher = new Matcher( pattern ); const result = matcher.match( el1, el2, el3 ); @@ -284,7 +291,7 @@ describe( 'Matcher', () => { } }; const matcher = new Matcher( pattern ); - const el = new Element( 'a', { + const el = new Element( document, 'a', { name: 'foo', title: 'bar' } ); @@ -305,7 +312,7 @@ describe( 'Matcher', () => { classes: [ 'foo', 'bar' ] }; const matcher = new Matcher( pattern ); - const el = new Element( 'a' ); + const el = new Element( document, 'a' ); el._addClass( [ 'foo', 'bar', 'baz' ] ); const result = matcher.match( el ); @@ -327,7 +334,7 @@ describe( 'Matcher', () => { } }; const matcher = new Matcher( pattern ); - const el = new Element( 'a' ); + const el = new Element( document, 'a' ); el._setStyle( { color: 'red', position: 'relative' @@ -347,9 +354,9 @@ describe( 'Matcher', () => { describe( 'matchAll', () => { it( 'should return all matched elements with correct patterns', () => { const matcher = new Matcher( 'p', 'div' ); - const el1 = new Element( 'p' ); - const el2 = new Element( 'div' ); - const el3 = new Element( 'span' ); + const el1 = new Element( document, 'p' ); + const el2 = new Element( document, 'div' ); + const el3 = new Element( document, 'span' ); const result = matcher.matchAll( el1, el2, el3 ); expect( result ).to.be.an( 'array' ); @@ -372,9 +379,9 @@ describe( 'Matcher', () => { it( 'should return all matched elements when using RegExp pattern', () => { const pattern = { classes: /^red-.*/ }; const matcher = new Matcher( pattern ); - const el1 = new Element( 'p' ); - const el2 = new Element( 'p' ); - const el3 = new Element( 'p' ); + const el1 = new Element( document, 'p' ); + const el2 = new Element( document, 'p' ); + const el3 = new Element( document, 'p' ); el1._addClass( 'red-foreground' ); el2._addClass( 'red-background' ); diff --git a/tests/view/node.js b/tests/view/node.js index 59aa43b41..906ae1cd0 100644 --- a/tests/view/node.js +++ b/tests/view/node.js @@ -11,23 +11,26 @@ import RootEditableElement from '../../src/view/rooteditableelement'; import createDocumentMock from '../../tests/view/_utils/createdocumentmock'; import { expectToThrowCKEditorError } from '@ckeditor/ckeditor5-utils/tests/_utils/utils'; +import Document from '../../src/view/document'; describe( 'Node', () => { - let root, + let root, document, one, two, three, charB, charA, charR, img; before( () => { - charB = new Text( 'b' ); - charA = new Text( 'a' ); - img = new Element( 'img' ); - charR = new Text( 'r' ); + document = new Document(); - one = new Element( 'one' ); - two = new Element( 'two', null, [ charB, charA, img, charR ] ); - three = new Element( 'three' ); + charB = new Text( document, 'b' ); + charA = new Text( document, 'a' ); + img = new Element( document, 'img' ); + charR = new Text( document, 'r' ); - root = new Element( null, null, [ one, two, three ] ); + one = new Element( document, 'one' ); + two = new Element( document, 'two', null, [ charB, charA, img, charR ] ); + three = new Element( document, 'three' ); + + root = new Element( document, null, null, [ one, two, three ] ); } ); describe( 'is()', () => { @@ -125,7 +128,7 @@ describe( 'Node', () => { } ); it( 'should return ancestors including DocumentFragment', () => { - const fragment = new DocumentFragment( root ); + const fragment = new DocumentFragment( document, root ); const result = img.getAncestors(); root._remove(); @@ -146,7 +149,7 @@ describe( 'Node', () => { } ); it( 'should return null for detached subtrees', () => { - const detached = new Element( 'foo' ); + const detached = new Element( document, 'foo' ); expect( img.getCommonAncestor( detached ) ).to.be.null; expect( detached.getCommonAncestor( img ) ).to.be.null; @@ -179,11 +182,11 @@ describe( 'Node', () => { const foo = new Text( 'foo' ); const bar = new Text( 'bar' ); const bom = new Text( 'bom' ); - const d = new Element( 'd', null, [ bar ] ); - const c = new Element( 'c', null, [ foo, d ] ); - const b = new Element( 'b', null, [ c ] ); - const e = new Element( 'e', null, [ bom ] ); - const a = new Element( 'a', null, [ b, e ] ); + const d = new Element( document, 'd', null, [ bar ] ); + const c = new Element( document, 'c', null, [ foo, d ] ); + const b = new Element( document, 'b', null, [ c ] ); + const e = new Element( document, 'e', null, [ bom ] ); + const a = new Element( document, 'a', null, [ b, e ] ); // foobarbom @@ -205,7 +208,7 @@ describe( 'Node', () => { it( 'should return document fragment', () => { const foo = new Text( 'foo' ); const bar = new Text( 'bar' ); - const df = new DocumentFragment( [ foo, bar ] ); + const df = new DocumentFragment( document, [ foo, bar ] ); expect( foo.getCommonAncestor( bar ) ).to.equal( df ); } ); @@ -229,7 +232,7 @@ describe( 'Node', () => { it( 'should throw an error if parent does not contain element', () => { const f = new Text( 'f' ); - const bar = new Element( 'bar', [], [] ); + const bar = new Element( document, 'bar', [], [] ); f.parent = bar; @@ -253,42 +256,17 @@ describe( 'Node', () => { } ); } ); - describe( 'getDocument()', () => { - it( 'should return null if any parent has not set Document', () => { - expect( charA.document ).to.be.null; - } ); - - it( 'should return Document attached to the parent element', () => { - const docMock = createDocumentMock(); - const parent = new RootEditableElement( 'div' ); - parent._document = docMock; - const child = new Element( 'p' ); - - child.parent = parent; - - expect( parent.document ).to.equal( docMock ); - expect( child.document ).to.equal( docMock ); - } ); - - it( 'should return null if element is inside DocumentFragment', () => { - const child = new Element( 'p' ); - new DocumentFragment( [ child ] ); // eslint-disable-line no-new - - expect( child.document ).to.be.null; - } ); - } ); - describe( 'getRoot()', () => { it( 'should return this element if it has no parent', () => { - const child = new Element( 'p' ); + const child = new Element( document, 'p' ); expect( child.root ).to.equal( child ); } ); it( 'should return root element', () => { - const parent = new RootEditableElement( 'div' ); + const parent = new RootEditableElement( document, 'div' ); parent._document = createDocumentMock(); - const child = new Element( 'p' ); + const child = new Element( document, 'p' ); child.parent = parent; @@ -326,8 +304,8 @@ describe( 'Node', () => { } ); it( 'should return false if elements are in different roots', () => { - const otherRoot = new Element( 'root' ); - const otherElement = new Element( 'element' ); + const otherRoot = new Element( document, 'root' ); + const otherElement = new Element( document, 'element' ); otherRoot._appendChild( otherElement ); @@ -364,8 +342,8 @@ describe( 'Node', () => { } ); it( 'should return false if elements are in different roots', () => { - const otherRoot = new Element( 'root' ); - const otherElement = new Element( 'element' ); + const otherRoot = new Element( document, 'root' ); + const otherElement = new Element( document, 'element' ); otherRoot._appendChild( otherElement ); @@ -376,7 +354,7 @@ describe( 'Node', () => { describe( '_remove()', () => { it( 'should remove node from its parent', () => { const char = new Text( 'a' ); - const parent = new Element( 'p', null, [ char ] ); + const parent = new Element( document, 'p', null, [ char ] ); char._remove(); expect( parent.getChildIndex( char ) ).to.equal( -1 ); @@ -384,7 +362,7 @@ describe( 'Node', () => { it( 'uses parent._removeChildren method', () => { const char = new Text( 'a' ); - const parent = new Element( 'p', null, [ char ] ); + const parent = new Element( document, 'p', null, [ char ] ); const _removeChildrenSpy = sinon.spy( parent, '_removeChildren' ); const index = char.index; char._remove(); @@ -396,15 +374,18 @@ describe( 'Node', () => { describe( 'toJSON()', () => { it( 'should prevent circular reference when stringifying a node', () => { - const char = new Text( 'a' ); - const parent = new Element( 'p', null ); + const char = new Text( document, 'a' ); + const parent = new Element( document, 'p', null ); parent._appendChild( char ); + sinon.stub( char, 'document' ).value( 'view.Document()' ); + const json = JSON.stringify( char ); const parsed = JSON.parse( json ); expect( parsed ).to.deep.equal( { - _textData: 'a' + _textData: 'a', + document: 'view.Document()' } ); } ); } ); @@ -418,9 +399,9 @@ describe( 'Node', () => { beforeEach( () => { text = new Text( 'foo' ); - img = new Element( 'img', { 'src': 'img.png' } ); + img = new Element( document, 'img', { 'src': 'img.png' } ); - root = new Element( 'p', { renderer: { markToSync: rootChangeSpy } } ); + root = new Element( document, 'p', { renderer: { markToSync: rootChangeSpy } } ); root._appendChild( [ text, img ] ); root.on( 'change:children', ( evt, node ) => rootChangeSpy( 'children', node ) ); @@ -470,7 +451,7 @@ describe( 'Node', () => { describe( '_insertChild()', () => { it( 'should fire change event', () => { - root._insertChild( 1, new Element( 'img' ) ); + root._insertChild( 1, new Element( document, 'img' ) ); sinon.assert.calledOnce( rootChangeSpy ); sinon.assert.calledWith( rootChangeSpy, 'children', root ); @@ -479,7 +460,7 @@ describe( 'Node', () => { describe( '_appendChild()', () => { it( 'should fire change event', () => { - root._appendChild( new Element( 'img' ) ); + root._appendChild( new Element( document, 'img' ) ); sinon.assert.calledOnce( rootChangeSpy ); sinon.assert.calledWith( rootChangeSpy, 'children', root ); diff --git a/tests/view/observer/domeventobserver.js b/tests/view/observer/domeventobserver.js index 946cda0d4..f73f87c88 100644 --- a/tests/view/observer/domeventobserver.js +++ b/tests/view/observer/domeventobserver.js @@ -165,7 +165,7 @@ describe( 'DomEventObserver', () => { let domRoot, domEvent, evtSpy, uiElement; function createUIElement( name ) { - const element = new UIElement( name ); + const element = new UIElement( viewDocument, name ); element.render = function( domDocument ) { const root = this.toDomElement( domDocument ); diff --git a/tests/view/placeholder.js b/tests/view/placeholder.js index 051124e02..6a5774dca 100644 --- a/tests/view/placeholder.js +++ b/tests/view/placeholder.js @@ -83,7 +83,7 @@ describe( 'placeholder', () => { expect( element.hasClass( 'ck-placeholder' ) ).to.be.true; } ); - it( 'if element has selection inside set only data attribute', () => { + it.only( 'if element has selection inside set only data attribute', () => { setData( view, '
[]
another div
' ); const element = viewRoot.getChild( 0 ); diff --git a/tests/view/position.js b/tests/view/position.js index b36e59cdb..b6c6bd289 100644 --- a/tests/view/position.js +++ b/tests/view/position.js @@ -21,6 +21,11 @@ import { expectToThrowCKEditorError } from '@ckeditor/ckeditor5-utils/tests/_uti describe( 'Position', () => { const parentMock = {}; + let document; + + beforeEach( () => { + document = new Document(); + } ); describe( 'constructor()', () => { it( 'should create element without attributes', () => { @@ -60,23 +65,23 @@ describe( 'Position', () => { describe( 'nodeBefore', () => { it( 'should equal to node that is before position', () => { - const b1 = new Element( 'b' ); - const el = new Element( 'p', null, [ b1 ] ); + const b1 = new Element( document, 'b' ); + const el = new Element( document, 'p', null, [ b1 ] ); const position = new Position( el, 1 ); expect( position.nodeBefore ).to.equal( b1 ); } ); it( 'should equal null if there is no node before', () => { - const b1 = new Element( 'b' ); - const el = new Element( 'p', null, [ b1 ] ); + const b1 = new Element( document, 'b' ); + const el = new Element( document, 'p', null, [ b1 ] ); const position = new Position( el, 0 ); expect( position.nodeBefore ).to.be.null; } ); it( 'should equal null if position is located inside text node', () => { - const text = new Text( 'foobar' ); + const text = new Text( document, 'foobar' ); const position = new Position( text, 3 ); expect( position.nodeBefore ).to.be.null; @@ -85,23 +90,23 @@ describe( 'Position', () => { describe( 'nodeAfter', () => { it( 'should equal to node that is after position', () => { - const b1 = new Element( 'b' ); - const el = new Element( 'p', null, [ b1 ] ); + const b1 = new Element( document, 'b' ); + const el = new Element( document, 'p', null, [ b1 ] ); const position = new Position( el, 0 ); expect( position.nodeAfter ).to.equal( b1 ); } ); it( 'should equal null if there is no node before', () => { - const b1 = new Element( 'b' ); - const el = new Element( 'p', null, [ b1 ] ); + const b1 = new Element( document, 'b' ); + const el = new Element( document, 'p', null, [ b1 ] ); const position = new Position( el, 1 ); expect( position.nodeAfter ).to.be.null; } ); it( 'should equal null if position is located inside text node', () => { - const text = new Text( 'foobar' ); + const text = new Text( document, 'foobar' ); const position = new Position( text, 3 ); expect( position.nodeAfter ).to.be.null; @@ -151,13 +156,13 @@ describe( 'Position', () => { describe( 'getRoot', () => { it( 'should return it\'s parent root', () => { - const foo = new Text( 'foo' ); - const docFrag = new DocumentFragment( foo ); + const foo = new Text( document, 'foo' ); + const docFrag = new DocumentFragment( document, foo ); expect( new Position( foo, 1 ).root ).to.equal( docFrag ); - const bar = new Text( 'bar' ); - const p = new Element( 'p', null, bar ); + const bar = new Text( document, 'bar' ); + const p = new Element( document, 'p', null, bar ); expect( new Position( bar, 2 ).root ).to.equal( p ); expect( new Position( p, 0 ).root ).to.equal( p ); @@ -166,16 +171,16 @@ describe( 'Position', () => { describe( 'getAncestors', () => { it( 'should return it\'s parent and all it\'s ancestors', () => { - const foo = new Text( 'foo' ); - const p = new Element( 'p', null, foo ); - const div = new Element( 'div', null, p ); - const docFrag = new DocumentFragment( div ); + const foo = new Text( document, 'foo' ); + const p = new Element( document, 'p', null, foo ); + const div = new Element( document, 'div', null, p ); + const docFrag = new DocumentFragment( document, div ); expect( new Position( foo, 1 ).getAncestors() ).to.deep.equal( [ docFrag, div, p, foo ] ); } ); it( 'should return DocumentFragment if position is directly in document fragment', () => { - const docFrag = new DocumentFragment(); + const docFrag = new DocumentFragment( document ); expect( new Position( docFrag, 0 ).getAncestors() ).to.deep.equal( [ docFrag ] ); } ); @@ -220,10 +225,10 @@ describe( 'Position', () => { } ); it( 'should return false if no common ancestor is found', () => { - const t1 = new Text( 'foo' ); - const t2 = new Text( 'bar' ); - const e1 = new Element( 'p', null, [ t1 ] ); - const e2 = new Element( 'p', null, [ t2 ] ); + const t1 = new Text( document, 'foo' ); + const t2 = new Text( document, 'bar' ); + const e1 = new Element( document, 'p', null, [ t1 ] ); + const e2 = new Element( document, 'p', null, [ t2 ] ); const position1 = new Position( e1, 0 ); const position2 = new Position( e2, 1 ); @@ -241,9 +246,9 @@ describe( 'Position', () => { } ); it( 'should compare positions that have common parent', () => { - const t1 = new Text( 'foo' ); - const t2 = new Text( 'bar' ); - const root = new Element( 'p', null, [ t1, t2 ] ); + const t1 = new Text( document, 'foo' ); + const t2 = new Text( document, 'bar' ); + const root = new Element( document, 'p', null, [ t1, t2 ] ); const position1 = new Position( t1, 2 ); const position2 = new Position( t2, 0 ); const position3 = new Position( root, 0 ); @@ -278,10 +283,10 @@ describe( 'Position', () => { } ); it( 'should return false if no common ancestor is found', () => { - const t1 = new Text( 'foo' ); - const t2 = new Text( 'bar' ); - const e1 = new Element( 'p', null, [ t1 ] ); - const e2 = new Element( 'p', null, [ t2 ] ); + const t1 = new Text( document, 'foo' ); + const t2 = new Text( document, 'bar' ); + const e1 = new Element( document, 'p', null, [ t1 ] ); + const e2 = new Element( document, 'p', null, [ t2 ] ); const position1 = new Position( e1, 0 ); const position2 = new Position( e2, 1 ); @@ -299,9 +304,9 @@ describe( 'Position', () => { } ); it( 'should compare positions that have common parent', () => { - const t1 = new Text( 'foo' ); - const t2 = new Text( 'bar' ); - const root = new Element( 'p', null, [ t1, t2 ] ); + const t1 = new Text( document, 'foo' ); + const t2 = new Text( document, 'bar' ); + const root = new Element( document, 'p', null, [ t1, t2 ] ); const position1 = new Position( t1, 2 ); const position2 = new Position( t2, 0 ); const position3 = new Position( root, 0 ); @@ -325,13 +330,13 @@ describe( 'Position', () => { describe( 'isAtStart', () => { it( 'should return true if it is at the start of it\'s parent', () => { - const foo = new Text( 'foo' ); + const foo = new Text( document, 'foo' ); const position = new Position( foo, 0 ); expect( position.isAtStart ).to.be.true; } ); it( 'should return false if it is not at the start of it\'s parent', () => { - const foo = new Text( 'foo' ); + const foo = new Text( document, 'foo' ); const position = new Position( foo, 1 ); expect( position.isAtStart ).to.be.false; } ); @@ -339,16 +344,16 @@ describe( 'Position', () => { describe( 'isAtEnd', () => { it( 'should return true if it is at the end of it\'s parent', () => { - const foo = new Text( 'foo' ); - const p = new Element( 'p', null, foo ); + const foo = new Text( document, 'foo' ); + const p = new Element( document, 'p', null, foo ); expect( new Position( foo, 3 ).isAtEnd ).to.be.true; expect( new Position( p, 1 ).isAtEnd ).to.be.true; } ); it( 'should return false if it is not at the end of it\'s parent', () => { - const foo = new Text( 'foo' ); - const p = new Element( 'p', null, foo ); + const foo = new Text( document, 'foo' ); + const p = new Element( document, 'p', null, foo ); expect( new Position( foo, 2 ).isAtEnd ).to.be.false; expect( new Position( p, 0 ).isAtEnd ).to.be.false; @@ -357,7 +362,7 @@ describe( 'Position', () => { describe( 'compareWith', () => { it( 'should return same if positions are same', () => { - const root = new Element(); + const root = new Element( document ); const position = new Position( root, 0 ); const compared = new Position( root, 0 ); @@ -365,7 +370,7 @@ describe( 'Position', () => { } ); it( 'should return before if the position is before compared one', () => { - const root = new Element(); + const root = new Element( document ); const position = new Position( root, 0 ); const compared = new Position( root, 1 ); @@ -373,7 +378,7 @@ describe( 'Position', () => { } ); it( 'should return after if the position is after compared one', () => { - const root = new Element(); + const root = new Element( document ); const position = new Position( root, 4 ); const compared = new Position( root, 1 ); @@ -381,8 +386,8 @@ describe( 'Position', () => { } ); it( 'should return different if positions are in different roots', () => { - const root1 = new Element(); - const root2 = new Element(); + const root1 = new Element( document ); + const root2 = new Element( document ); const position = new Position( root1, 4 ); const compared = new Position( root2, 1 ); @@ -390,8 +395,8 @@ describe( 'Position', () => { } ); it( 'should return correct results if position is in document fragment', () => { - const node = new Element( 'name' ); - const docFrag = new DocumentFragment( [ node ] ); + const node = new Element( document, 'name' ); + const docFrag = new DocumentFragment( document, [ node ] ); const position = new Position( docFrag, 0 ); const compared = new Position( docFrag, 1 ); const posInNode = new Position( node, 0 ); @@ -407,7 +412,7 @@ describe( 'Position', () => { describe( 'static creators', () => { describe( '_createAt()', () => { it( 'should throw if no offset is passed', () => { - const element = new Element( 'p' ); + const element = new Element( document, 'p' ); expectToThrowCKEditorError( () => { Position._createAt( element ); @@ -415,7 +420,7 @@ describe( 'Position', () => { } ); it( 'should create positions from positions', () => { - const p = new Element( 'p' ); + const p = new Element( document, 'p' ); const position = new Position( p, 0 ); const created = Position._createAt( position, 0 ); @@ -424,8 +429,8 @@ describe( 'Position', () => { } ); it( 'should create positions from node and offset', () => { - const foo = new Text( 'foo' ); - const p = new Element( 'p', null, foo ); + const foo = new Text( document, 'foo' ); + const p = new Element( document, 'p', null, foo ); expect( Position._createAt( foo, 0 ).parent ).to.equal( foo ); expect( Position._createAt( foo, 0 ).offset ).to.equal( 0 ); @@ -438,8 +443,8 @@ describe( 'Position', () => { } ); it( 'should create positions from node and flag', () => { - const foo = new Text( 'foo' ); - const p = new Element( 'p', null, foo ); + const foo = new Text( document, 'foo' ); + const p = new Element( document, 'p', null, foo ); const fooEnd = Position._createAt( foo, 'end' ); const fooBefore = Position._createAt( foo, 'before' ); @@ -462,8 +467,8 @@ describe( 'Position', () => { } ); it( 'should create positions in document fragment', () => { - const foo = new Text( 'foo' ); - const docFrag = new DocumentFragment( [ foo ] ); + const foo = new Text( document, 'foo' ); + const docFrag = new DocumentFragment( document, [ foo ] ); const pStart = Position._createAt( docFrag, 0 ); const pEnd = Position._createAt( docFrag, 'end' ); @@ -493,7 +498,7 @@ describe( 'Position', () => { } ); it( 'should create positions before `TextProxy`', () => { - const text = new Text( 'abc' ); + const text = new Text( document, 'abc' ); const textProxy = new TextProxy( text, 1, 1 ); const position = new Position( text, 1 ); @@ -520,7 +525,7 @@ describe( 'Position', () => { } ); it( 'should create positions after `TextProxy`', () => { - const text = new Text( 'abcd' ); + const text = new Text( document, 'abcd' ); const textProxy = new TextProxy( text, 1, 2 ); const position = new Position( text, 3 ); @@ -532,15 +537,14 @@ describe( 'Position', () => { describe( 'getEditableElement', () => { it( 'should return null if position is not inside EditableElement', () => { - const position = new Position( new Element( 'p' ), 0 ); + const position = new Position( new Element( document, 'p' ), 0 ); expect( position.editableElement ).to.be.null; } ); it( 'should return EditableElement when position is placed inside', () => { - const document = new Document(); - const p = new Element( 'p' ); - const editable = new EditableElement( 'div', null, p ); + const p = new Element( document, 'p' ); + const editable = new EditableElement( document, 'div', null, p ); editable._document = document; const position = new Position( p, 0 ); @@ -570,28 +574,28 @@ describe( 'Position', () => { beforeEach( () => { texts = { - foz: new Text( 'foz' ), - bar: new Text( 'bar' ), - lorem: new Text( 'Lorem ipsum dolor sit amet.' ), - mauris: new Text( 'Mauris tincidunt tincidunt leo ac rutrum.' ), - maecenas: new Text( 'Maecenas accumsan tellus.' ), - sed: new Text( 'Sed id libero at libero tristique.' ) + foz: new Text( document, 'foz' ), + bar: new Text( document, 'bar' ), + lorem: new Text( document, 'Lorem ipsum dolor sit amet.' ), + mauris: new Text( document, 'Mauris tincidunt tincidunt leo ac rutrum.' ), + maecenas: new Text( document, 'Maecenas accumsan tellus.' ), + sed: new Text( document, 'Sed id libero at libero tristique.' ) }; - liUl1 = new Element( 'li', null, texts.foz ); - liUl2 = new Element( 'li', null, texts.bar ); - ul = new Element( 'ul', null, [ liUl1, liUl2 ] ); + liUl1 = new Element( document, 'li', null, texts.foz ); + liUl2 = new Element( document, 'li', null, texts.bar ); + ul = new Element( document, 'ul', null, [ liUl1, liUl2 ] ); - liOl1 = new Element( 'li', null, texts.lorem ); - liOl2 = new Element( 'li', null, texts.mauris ); - ol = new Element( 'ol', null, [ liOl1, liOl2 ] ); + liOl1 = new Element( document, 'li', null, texts.lorem ); + liOl2 = new Element( document, 'li', null, texts.mauris ); + ol = new Element( document, 'ol', null, [ liOl1, liOl2 ] ); - p = new Element( 'p', null, texts.maecenas ); + p = new Element( document, 'p', null, texts.maecenas ); - article = new Element( 'article', null, [ ol, p ] ); - section = new Element( 'section', null, [ texts.sed, article ] ); + article = new Element( document, 'article', null, [ ol, p ] ); + section = new Element( document, 'section', null, [ texts.sed, article ] ); - div = new Element( 'div', null, [ ul, section ] ); + div = new Element( document, 'div', null, [ ul, section ] ); } ); it( 'for two the same positions returns the parent element', () => { @@ -623,7 +627,7 @@ describe( 'Position', () => { } ); it( 'for two positions in different trees returns null', () => { - const div = new Element( 'div' ); + const div = new Element( document, 'div' ); const posInDiv = new Position( div, 0 ); const firstPosition = new Position( liOl2, 10 ); @@ -644,11 +648,11 @@ describe( 'Position', () => { root = createViewRoot( doc ); - const textAbcd = new Text( 'abcd' ); - const bold = new AttributeElement( 'b', null, [ textAbcd ] ); + const textAbcd = new Text( document, 'abcd' ); + const bold = new AttributeElement( document, 'b', null, [ textAbcd ] ); - const paragraph = new ContainerElement( 'p', null, [ bold ] ); - const img = new ContainerElement( 'img' ); + const paragraph = new ContainerElement( document, 'p', null, [ bold ] ); + const img = new ContainerElement( document, 'img' ); root._insertChild( 0, [ img, paragraph ] ); } ); diff --git a/tests/view/range.js b/tests/view/range.js index 13e6a216d..30e657e6c 100644 --- a/tests/view/range.js +++ b/tests/view/range.js @@ -10,6 +10,7 @@ import DocumentFragment from '../../src/view/documentfragment'; import Text from '../../src/view/text'; import TextProxy from '../../src/view/textproxy'; import TreeWalker from '../../src/view/treewalker'; +import Document from '../../src/view/document'; import { parse, stringify } from '../../src/dev-utils/view'; function getRange( view, options = {} ) { @@ -19,6 +20,12 @@ function getRange( view, options = {} ) { } describe( 'Range', () => { + let document; + + beforeEach( () => { + document = new Document(); + } ); + describe( 'constructor()', () => { it( 'creates range from provided positions', () => { const start = new Position( {}, 1 ); @@ -101,7 +108,7 @@ describe( 'Range', () => { describe( 'getRoot', () => { it( 'should return root element in which range is created', () => { - const viewRoot = new Element( 'div' ); + const viewRoot = new Element( document, 'div' ); const range = getRange( '

f{oo

ba}r

', { rootElement: viewRoot } ); expect( range.root ).to.equal( viewRoot ); @@ -297,7 +304,7 @@ describe( 'Range', () => { let viewRoot, range; beforeEach( () => { - viewRoot = new Element( 'div' ); + viewRoot = new Element( document, 'div' ); range = getRange( '

fo{o

bar

xy}z

', { rootElement: viewRoot } ); } ); @@ -324,7 +331,7 @@ describe( 'Range', () => { let viewRoot, range, beforeF, afterF, beforeB, afterX; beforeEach( () => { - viewRoot = new Element( 'div' ); + viewRoot = new Element( document, 'div' ); range = getRange( '

fo{o

bar

xy}z

', { rootElement: viewRoot } ); beforeF = new Position( viewRoot.getChild( 0 ).getChild( 0 ), 0 ); @@ -395,12 +402,12 @@ describe( 'Range', () => { // t1 t2 t3 beforeEach( () => { - t1 = new Text( 'foo' ); - t2 = new Text( 'bar' ); - t3 = new Text( 'baz' ); - p1 = new Element( 'p', null, [ t1, t2 ] ); - p2 = new Element( 'p', null, t3 ); - root = new Element( 'div', null, [ p1, p2 ] ); + t1 = new Text( document, 'foo' ); + t2 = new Text( document, 'bar' ); + t3 = new Text( document, 'baz' ); + p1 = new Element( document, 'p', null, [ t1, t2 ] ); + p2 = new Element( document, 'p', null, t3 ); + root = new Element( document, 'div', null, [ p1, p2 ] ); } ); describe( 'isIntersecting', () => { @@ -445,7 +452,7 @@ describe( 'Range', () => { it( 'should return false if ranges are in different roots', () => { const range = Range._createFromParentsAndOffsets( t1, 0, t2, 3 ); - const otherRange = Range._createFromParentsAndOffsets( new Element( 'div' ), 1, t3, 0 ); + const otherRange = Range._createFromParentsAndOffsets( new Element( document, 'div' ), 1, t3, 0 ); expect( range.isIntersecting( otherRange ) ).to.be.false; expect( otherRange.isIntersecting( range ) ).to.be.false; @@ -677,9 +684,9 @@ describe( 'Range', () => { let div, p, foz; beforeEach( () => { - foz = new Text( 'foz' ); - p = new Element( 'p', null, foz ); - div = new Element( 'div', null, p ); + foz = new Text( document, 'foz' ); + p = new Element( document, 'p', null, foz ); + div = new Element( document, 'div', null, p ); } ); describe( '_createIn', () => { @@ -704,7 +711,7 @@ describe( 'Range', () => { } ); it( 'should create a proper range on a text proxy', () => { - const text = new Text( 'foobar' ); + const text = new Text( document, 'foobar' ); const textProxy = new TextProxy( text, 2, 3 ); const range = Range._createOn( textProxy ); @@ -751,13 +758,13 @@ describe( 'Range', () => { describe( 'getCommonAncestor()', () => { it( 'should return common ancestor for positions from Range', () => { - const foz = new Text( 'foz' ); - const bar = new Text( 'bar' ); + const foz = new Text( document, 'foz' ); + const bar = new Text( document, 'bar' ); - const li1 = new Element( 'li', null, foz ); - const li2 = new Element( 'li', null, bar ); + const li1 = new Element( document, 'li', null, foz ); + const li2 = new Element( document, 'li', null, bar ); - const ul = new Element( 'ul', null, [ li1, li2 ] ); + const ul = new Element( document, 'ul', null, [ li1, li2 ] ); const range = new Range( new Position( li1, 0 ), new Position( li2, 2 ) ); diff --git a/tests/view/renderer.js b/tests/view/renderer.js index 66996946f..74522a961 100644 --- a/tests/view/renderer.js +++ b/tests/view/renderer.js @@ -13,6 +13,7 @@ import ViewAttributeElement from '../../src/view/attributeelement'; import ViewText from '../../src/view/text'; import ViewRange from '../../src/view/range'; import ViewPosition from '../../src/view/position'; +import ViewDocument from '../../src/view/document'; import UIElement from '../../src/view/uielement'; import DocumentSelection from '../../src/view/documentselection'; import DomConverter from '../../src/view/domconverter'; @@ -30,13 +31,14 @@ import env from '@ckeditor/ckeditor5-utils/src/env'; import { expectToThrowCKEditorError } from '@ckeditor/ckeditor5-utils/tests/_utils/utils'; describe( 'Renderer', () => { - let selection, domConverter, renderer; + let selection, domConverter, renderer, viewDocument; testUtils.createSinonSandbox(); beforeEach( () => { selection = new DocumentSelection(); domConverter = new DomConverter(); + viewDocument = new ViewDocument(); renderer = new Renderer( domConverter, selection ); renderer.domDocuments.add( document ); } ); @@ -45,11 +47,11 @@ describe( 'Renderer', () => { let viewRoot; beforeEach( () => { - viewRoot = new ViewElement( 'p' ); + viewRoot = new ViewElement( viewDocument, 'p' ); const domRoot = document.createElement( 'p' ); domConverter.bindElements( domRoot, viewRoot ); - viewRoot._appendChild( new ViewText( 'foo' ) ); + viewRoot._appendChild( new ViewText( viewDocument, 'foo' ) ); renderer.markedTexts.clear(); renderer.markedAttributes.clear(); @@ -65,7 +67,7 @@ describe( 'Renderer', () => { } ); it( 'should mark children which need update', () => { - viewRoot._appendChild( new ViewText( 'foo' ) ); + viewRoot._appendChild( new ViewText( viewDocument, 'foo' ) ); renderer.markToSync( 'children', viewRoot ); @@ -74,9 +76,9 @@ describe( 'Renderer', () => { it( 'should not mark children if element has no corresponding node', () => { // Overwrite viewRoot with node without coresponding DOM node. - viewRoot = new ViewElement( 'p' ); + viewRoot = new ViewElement( viewDocument, 'p' ); - viewRoot._appendChild( new ViewText( 'foo' ) ); + viewRoot._appendChild( new ViewText( viewDocument, 'foo' ) ); renderer.markToSync( 'children', viewRoot ); @@ -84,7 +86,7 @@ describe( 'Renderer', () => { } ); it( 'should mark text which need update', () => { - const viewText = new ViewText( 'foo' ); + const viewText = new ViewText( viewDocument, 'foo' ); viewRoot._appendChild( viewText ); viewText._data = 'bar'; @@ -94,9 +96,9 @@ describe( 'Renderer', () => { } ); it( 'should not mark text if parent has no corresponding node', () => { - const viewText = new ViewText( 'foo' ); + const viewText = new ViewText( viewDocument, 'foo' ); // Overwrite viewRoot with node without coresponding DOM node. - viewRoot = new ViewElement( 'p' ); + viewRoot = new ViewElement( viewDocument, 'p' ); viewRoot._appendChild( viewText ); viewText._data = 'bar'; @@ -117,7 +119,7 @@ describe( 'Renderer', () => { let viewRoot, domRoot; beforeEach( () => { - viewRoot = new ViewEditableElement( 'div' ); + viewRoot = new ViewEditableElement( viewDocument, 'div' ); viewRoot.getFillerOffset = () => null; domRoot = document.createElement( 'div' ); @@ -164,7 +166,7 @@ describe( 'Renderer', () => { } ); it( 'should add children', () => { - viewRoot._appendChild( new ViewText( 'foo' ) ); + viewRoot._appendChild( new ViewText( viewDocument, 'foo' ) ); renderer.markToSync( 'children', viewRoot ); renderer.render(); @@ -176,7 +178,7 @@ describe( 'Renderer', () => { } ); it( 'should remove children', () => { - viewRoot._appendChild( new ViewText( 'foo' ) ); + viewRoot._appendChild( new ViewText( viewDocument, 'foo' ) ); renderer.markToSync( 'children', viewRoot ); renderer.render(); @@ -195,7 +197,7 @@ describe( 'Renderer', () => { } ); it( 'should update text', () => { - const viewText = new ViewText( 'foo' ); + const viewText = new ViewText( viewDocument, 'foo' ); viewRoot._appendChild( viewText ); renderer.markToSync( 'children', viewRoot ); @@ -216,7 +218,7 @@ describe( 'Renderer', () => { } ); it( 'should not update same text', () => { - const viewText = new ViewText( 'foo' ); + const viewText = new ViewText( viewDocument, 'foo' ); viewRoot._appendChild( viewText ); renderer.markToSync( 'children', viewRoot ); @@ -238,8 +240,8 @@ describe( 'Renderer', () => { } ); it( 'should not update text parent child list changed', () => { - const viewImg = new ViewElement( 'img' ); - const viewText = new ViewText( 'foo' ); + const viewImg = new ViewElement( viewDocument, 'img' ); + const viewText = new ViewText( viewDocument, 'foo' ); viewRoot._appendChild( [ viewImg, viewText ] ); renderer.markToSync( 'children', viewRoot ); @@ -252,7 +254,7 @@ describe( 'Renderer', () => { } ); it( 'should not change text if it is the same during text rendering', () => { - const viewText = new ViewText( 'foo' ); + const viewText = new ViewText( viewDocument, 'foo' ); viewRoot._appendChild( viewText ); renderer.markToSync( 'children', viewRoot ); @@ -269,7 +271,7 @@ describe( 'Renderer', () => { } ); it( 'should not change text if it is the same during children rendering', () => { - const viewText = new ViewText( 'foo' ); + const viewText = new ViewText( viewDocument, 'foo' ); viewRoot._appendChild( viewText ); renderer.markToSync( 'children', viewRoot ); @@ -286,7 +288,7 @@ describe( 'Renderer', () => { } ); it( 'should not change element if it is the same', () => { - const viewImg = new ViewElement( 'img' ); + const viewImg = new ViewElement( viewDocument, 'img' ); viewRoot._appendChild( viewImg ); // This should not be changed during the render. @@ -303,13 +305,13 @@ describe( 'Renderer', () => { } ); it( 'should change element if it is different', () => { - const viewImg = new ViewElement( 'img' ); + const viewImg = new ViewElement( viewDocument, 'img' ); viewRoot._appendChild( viewImg ); renderer.markToSync( 'children', viewRoot ); renderer.render(); - const viewP = new ViewElement( 'p' ); + const viewP = new ViewElement( viewDocument, 'p' ); viewRoot._removeChildren( 0, 1 ); viewRoot._appendChild( viewP ); @@ -321,9 +323,9 @@ describe( 'Renderer', () => { } ); it( 'should update removed item when it is reinserted', () => { - const viewFoo = new ViewText( 'foo' ); - const viewP = new ViewElement( 'p', null, viewFoo ); - const viewDiv = new ViewElement( 'div', null, viewP ); + const viewFoo = new ViewText( viewDocument, 'foo' ); + const viewP = new ViewElement( viewDocument, 'p', null, viewFoo ); + const viewDiv = new ViewElement( viewDocument, 'div', null, viewP ); viewRoot._appendChild( viewDiv ); @@ -355,9 +357,9 @@ describe( 'Renderer', () => { it( 'should update removed item when it is reinserted #2', () => { // Prepare view: root -> div "outer" -> div "inner" -> p. - const viewP = new ViewElement( 'p' ); - const viewDivInner = new ViewElement( 'div', null, viewP ); - const viewDivOuter = new ViewElement( 'div', null, viewDivInner ); + const viewP = new ViewElement( viewDocument, 'p' ); + const viewDivInner = new ViewElement( viewDocument, 'div', null, viewP ); + const viewDivOuter = new ViewElement( viewDocument, 'div', null, viewDivInner ); viewRoot._appendChild( viewDivOuter ); // Render view tree to DOM. @@ -393,9 +395,9 @@ describe( 'Renderer', () => { } ); it( 'should not throw when trying to update children of view element that got removed and lost its binding', () => { - const viewFoo = new ViewText( 'foo' ); - const viewP = new ViewElement( 'p', null, viewFoo ); - const viewDiv = new ViewElement( 'div', null, viewP ); + const viewFoo = new ViewText( viewDocument, 'foo' ); + const viewP = new ViewElement( viewDocument, 'p', null, viewFoo ); + const viewDiv = new ViewElement( viewDocument, 'div', null, viewP ); viewRoot._appendChild( viewDiv ); @@ -420,7 +422,7 @@ describe( 'Renderer', () => { const { view: viewP, selection: newSelection } = parse( 'foo[]bar' ); - const viewRoot = new ViewElement( 'p' ); + const viewRoot = new ViewElement( viewDocument, 'p' ); viewRoot._appendChild( viewP ); selection._setTo( newSelection ); @@ -720,7 +722,7 @@ describe( 'Renderer', () => { expect( domP.childNodes[ 1 ].childNodes[ 0 ].data ).to.equal( INLINE_FILLER ); // Step 2: Add text node. - const viewText = new ViewText( 'x' ); + const viewText = new ViewText( viewDocument, 'x' ); viewB._appendChild( viewText ); selection._setTo( ViewRange._createFromParentsAndOffsets( viewText, 1, viewText, 1 ) ); @@ -903,7 +905,7 @@ describe( 'Renderer', () => { domRange.collapse( true ); domSelection.addRange( domRange ); - const viewText = new ViewText( 'x' ); + const viewText = new ViewText( viewDocument, 'x' ); viewP._appendChild( viewText ); selection._setTo( ViewRange._createFromParentsAndOffsets( viewText, 1, viewText, 1 ) ); @@ -933,7 +935,7 @@ describe( 'Renderer', () => { expect( domSelection.getRangeAt( 0 ).collapsed ).to.be.true; // Add text node only in View

x{}

- const viewText = new ViewText( 'x' ); + const viewText = new ViewText( viewDocument, 'x' ); viewP._appendChild( viewText ); selection._setTo( ViewRange._createFromParentsAndOffsets( viewText, 1, viewText, 1 ) ); @@ -1031,7 +1033,7 @@ describe( 'Renderer', () => { domRange.collapse( true ); domSelection.addRange( domRange ); - const viewText = new ViewText( 'x' ); + const viewText = new ViewText( viewDocument, 'x' ); viewB._appendChild( viewText ); selection._setTo( ViewRange._createFromParentsAndOffsets( viewText, 1, viewText, 1 ) ); @@ -1074,7 +1076,7 @@ describe( 'Renderer', () => { domSelection.removeAllRanges(); // 3. Add text node only to the view:

x{}foo

. - const viewText = new ViewText( 'x' ); + const viewText = new ViewText( viewDocument, 'x' ); viewB._appendChild( viewText ); selection._setTo( ViewRange._createFromParentsAndOffsets( viewText, 1, viewText, 1 ) ); @@ -1137,7 +1139,7 @@ describe( 'Renderer', () => { // 3. Add text node only to the view:

x{}foo

. - const viewText = new ViewText( 'x' ); + const viewText = new ViewText( viewDocument, 'x' ); viewB._appendChild( viewText ); selection._setTo( ViewRange._createFromParentsAndOffsets( viewText, 1, viewText, 1 ) ); @@ -1195,7 +1197,7 @@ describe( 'Renderer', () => { domSelection.removeAllRanges(); domSelection.collapse( domDiv, 0 ); - const viewDiv = new ViewElement( 'div' ); + const viewDiv = new ViewElement( viewDocument, 'div' ); const { view: viewP, selection: newSelection } = parse( 'fo{o}' ); viewDiv._appendChild( viewP ); @@ -1329,7 +1331,7 @@ describe( 'Renderer', () => { // 3. Move the inline filler parent to a newly created element. const viewLi = view.getChild( 0 ); const viewLiIndented = view._removeChildren( 1, 1 ); // Array with one element. - const viewUl = new ViewContainerElement( 'ul', null, viewLiIndented ); + const viewUl = new ViewContainerElement( viewDocument, 'ul', null, viewLiIndented ); viewLi._appendChild( viewUl ); // 4. Mark changed items and render the view. @@ -1391,7 +1393,7 @@ describe( 'Renderer', () => { // Insert space resulting in '

x y

'. const viewB = viewP.getChild( 1 ); viewB._removeChildren( 0 ); - viewB._appendChild( new ViewText( ' y' ) ); + viewB._appendChild( new ViewText( viewDocument, ' y' ) ); renderer.markToSync( 'children', viewP ); renderer.render(); @@ -1469,7 +1471,7 @@ describe( 'Renderer', () => { // Insert space resulting in '

x y

'. viewP._removeChildren( 0 ); - viewP._insertChild( 0, new ViewText( 'x ' ) ); + viewP._insertChild( 0, new ViewText( viewDocument, 'x ' ) ); renderer.markToSync( 'children', viewP ); renderer.render(); @@ -1498,7 +1500,7 @@ describe( 'Renderer', () => { // Insert space resulting in '

x y

'. const viewB = viewP.getChild( 0 ); viewB._removeChildren( 0 ); - viewB._insertChild( 0, new ViewText( 'x ' ) ); + viewB._insertChild( 0, new ViewText( viewDocument, 'x ' ) ); renderer.markToSync( 'children', viewP ); renderer.render(); @@ -1528,7 +1530,7 @@ describe( 'Renderer', () => { // Insert space resulting in '

x y

'. const viewB = viewP.getChild( 0 ); viewB._removeChildren( 0 ); - viewB._insertChild( 0, new ViewText( 'x ' ) ); + viewB._insertChild( 0, new ViewText( viewDocument, 'x ' ) ); renderer.markToSync( 'children', viewP ); renderer.render(); @@ -1580,7 +1582,7 @@ describe( 'Renderer', () => { // '

Heading 1

' -> '

Heading 2

' const viewHeading = viewRoot.getChild( 0 ); viewHeading._removeChildren( 0, viewHeading.childCount ); - viewHeading._insertChild( 0, new ViewText( 'Heading 2' ) ); + viewHeading._insertChild( 0, new ViewText( viewDocument, 'Heading 2' ) ); // Usually whole subtree is marked to sync so we mark root, changed element and all its direct children. renderer.markToSync( 'children', viewRoot ); @@ -1697,7 +1699,7 @@ describe( 'Renderer', () => { const viewLi = view.getChild( 0 ); const viewLiIndented = view._removeChildren( 1, 1 ); // Array with one element. viewLiIndented[ 0 ]._appendChild( parse( 'Baz' ) ); - const viewUl = new ViewContainerElement( 'ul', null, viewLiIndented ); + const viewUl = new ViewContainerElement( viewDocument, 'ul', null, viewLiIndented ); viewLi._appendChild( viewUl ); renderer.markToSync( 'children', view ); @@ -1986,7 +1988,7 @@ describe( 'Renderer', () => { } ); it( 'should move fake selection container between editables', () => { - const viewEditable = new ViewEditableElement( 'div' ); + const viewEditable = new ViewEditableElement( viewDocument, 'div' ); viewEditable._appendChild( parse( 'abc xyz' ) ); const domEditable = document.createElement( 'div' ); @@ -3162,7 +3164,7 @@ describe( 'Renderer', () => { it( 'should handle uiElement rendering', () => { function createUIElement( id, text ) { - const element = new UIElement( 'span' ); + const element = new UIElement( viewDocument, 'span' ); element.render = function( domDocument ) { const domElement = this.toDomElement( domDocument ); domElement.innerText = `${ text }`; @@ -3174,7 +3176,11 @@ describe( 'Renderer', () => { const ui1 = createUIElement( 'id1', 'UI1' ); const ui2 = createUIElement( 'id2', 'UI2' ); - const viewP = new ViewContainerElement( 'p', null, [ new ViewText( 'Foo ' ), ui1, new ViewText( 'Bar' ) ] ); + const viewP = new ViewContainerElement( viewDocument, 'p', null, [ + new ViewText( viewDocument, 'Foo ' ), + ui1, + new ViewText( viewDocument, 'Bar' ) + ] ); viewRoot._appendChild( viewP ); renderer.markToSync( 'children', viewRoot ); @@ -3184,7 +3190,7 @@ describe( 'Renderer', () => { '

Foo UI1Bar

' ) ); viewP._removeChildren( 0, viewP.childCount ); - viewP._insertChild( 0, [ new ViewText( 'Foo' ), ui2, new ViewText( ' Bar' ) ] ); + viewP._insertChild( 0, [ new ViewText( viewDocument, 'Foo' ), ui2, new ViewText( viewDocument, ' Bar' ) ] ); renderer.markToSync( 'children', viewRoot ); renderer.markToSync( 'children', viewP ); @@ -3206,7 +3212,10 @@ describe( 'Renderer', () => { // While linking, the existing DOM children are moved to a new `a` element during binding // inside the `domConverter.viewToDom()` method. It happens because of a modified view structure // where view elements were moved to a newly created link view element. - const viewA = new ViewAttributeElement( 'a', { href: '#href' }, [ new ViewText( 'Foo' ), viewP.getChild( 1 ) ] ); + const viewA = new ViewAttributeElement( viewDocument, 'a', { href: '#href' }, [ + new ViewText( viewDocument, 'Foo' ), + viewP.getChild( 1 ) + ] ); viewP._removeChildren( 0, viewP.childCount ); viewP._insertChild( 0, viewA ); @@ -3743,7 +3752,7 @@ describe( 'Renderer', () => { // Unwrap italic attribute element. view.change( writer => { - writer.unwrap( viewDoc.selection.getFirstRange(), new ViewAttributeElement( 'italic' ) ); + writer.unwrap( viewDoc.selection.getFirstRange(), new ViewAttributeElement( viewDocument, 'italic' ) ); } ); expect( getViewData( view ) ).to.equal( '

[foo]

' ); @@ -3769,7 +3778,7 @@ describe( 'Renderer', () => { // Unwrap italic attribute element and change text inside. view.change( writer => { - writer.unwrap( viewDoc.selection.getFirstRange(), new ViewAttributeElement( 'italic' ) ); + writer.unwrap( viewDoc.selection.getFirstRange(), new ViewAttributeElement( viewDocument, 'italic' ) ); } ); viewRoot.getChild( 0 ).getChild( 0 ).getChild( 0 )._data = 'bar'; @@ -3796,7 +3805,7 @@ describe( 'Renderer', () => { textNode._data = 'foobar'; view.change( writer => { - writer.insert( ViewPosition._createAfter( textNode ), new ViewAttributeElement( 'img' ) ); + writer.insert( ViewPosition._createAfter( textNode ), new ViewAttributeElement( viewDocument, 'img' ) ); } ); expect( getViewData( view ) ).to.equal( '

foobar

' ); @@ -3822,7 +3831,7 @@ describe( 'Renderer', () => { textNode._data = 'foobar'; view.change( writer => { - writer.insert( ViewPosition._createBefore( textNode ), new ViewAttributeElement( 'img' ) ); + writer.insert( ViewPosition._createBefore( textNode ), new ViewAttributeElement( viewDocument, 'img' ) ); } ); expect( getViewData( view ) ).to.equal( '

foobar

' ); @@ -3886,7 +3895,7 @@ describe( 'Renderer', () => { let viewRoot; beforeEach( () => { - viewRoot = new ViewElement( 'div' ); + viewRoot = new ViewElement( viewDocument, 'div' ); renderer.markedTexts.clear(); renderer.markedAttributes.clear(); @@ -3953,7 +3962,7 @@ describe( 'Renderer', () => { let viewRoot, domRoot; beforeEach( () => { - viewRoot = new ViewElement( 'div' ); + viewRoot = new ViewElement( viewDocument, 'div' ); domRoot = document.createElement( 'div' ); document.body.appendChild( domRoot ); @@ -3971,7 +3980,7 @@ describe( 'Renderer', () => { } ); it( 'should update text - change on end', () => { - const viewText = new ViewText( 'foo' ); + const viewText = new ViewText( viewDocument, 'foo' ); viewRoot._appendChild( viewText ); renderer.markToSync( 'children', viewRoot ); @@ -3989,7 +3998,7 @@ describe( 'Renderer', () => { } ); it( 'should update text - change on start', () => { - const viewText = new ViewText( 'foo' ); + const viewText = new ViewText( viewDocument, 'foo' ); viewRoot._appendChild( viewText ); renderer.markToSync( 'children', viewRoot ); @@ -4007,7 +4016,7 @@ describe( 'Renderer', () => { } ); it( 'should update text - change in the middle', () => { - const viewText = new ViewText( 'foobar' ); + const viewText = new ViewText( viewDocument, 'foobar' ); viewRoot._appendChild( viewText ); renderer.markToSync( 'children', viewRoot ); @@ -4025,7 +4034,7 @@ describe( 'Renderer', () => { } ); it( 'should update text - empty expected', () => { - const viewText = new ViewText( 'foo' ); + const viewText = new ViewText( viewDocument, 'foo' ); viewRoot._appendChild( viewText ); renderer.markToSync( 'children', viewRoot ); @@ -4043,7 +4052,7 @@ describe( 'Renderer', () => { } ); it( 'should update text - empty actual', () => { - const viewText = new ViewText( '' ); + const viewText = new ViewText( viewDocument, '' ); viewRoot._appendChild( viewText ); renderer.markToSync( 'children', viewRoot ); @@ -4061,7 +4070,7 @@ describe( 'Renderer', () => { } ); it( 'should handle filler during text modifications', () => { - const viewText = new ViewText( 'foo' ); + const viewText = new ViewText( viewDocument, 'foo' ); viewRoot._appendChild( viewText ); renderer.markToSync( 'children', viewRoot ); @@ -4102,7 +4111,7 @@ describe( 'Renderer', () => { } ); it( 'should handle filler during text modifications - empty text', () => { - const viewText = new ViewText( '' ); + const viewText = new ViewText( viewDocument, '' ); viewRoot._appendChild( viewText ); renderer.markToSync( 'children', viewRoot ); @@ -4145,8 +4154,8 @@ describe( 'Renderer', () => { } ); it( 'should handle filler during text modifications inside inline element', () => { - const viewB = new ViewElement( 'b' ); - const viewText = new ViewText( 'foo' ); + const viewB = new ViewElement( viewDocument, 'b' ); + const viewText = new ViewText( viewDocument, 'foo' ); viewB._appendChild( viewText ); viewRoot._appendChild( viewB ); diff --git a/tests/view/rooteditableelement.js b/tests/view/rooteditableelement.js index ea671c616..c8d849d99 100644 --- a/tests/view/rooteditableelement.js +++ b/tests/view/rooteditableelement.js @@ -10,10 +10,15 @@ import RootEditableElement from '../../src/view/rooteditableelement'; import createDocumentMock from '../../tests/view/_utils/createdocumentmock'; describe( 'RootEditableElement', () => { + let document; + + beforeEach( () => { + document = createDocumentMock(); + } ); + describe( 'constructor()', () => { it( 'should create an element with default root name', () => { - const root = new RootEditableElement( 'div' ); - root._document = createDocumentMock(); + const root = new RootEditableElement( document, 'div' ); expect( root ).to.be.instanceof( EditableElement ); expect( root ).to.be.instanceof( ContainerElement ); @@ -26,8 +31,7 @@ describe( 'RootEditableElement', () => { } ); it( 'should create an element with custom root name', () => { - const root = new RootEditableElement( 'h1' ); - root._document = createDocumentMock(); + const root = new RootEditableElement( document, 'h1' ); root.rootName = 'header'; expect( root.rootName ).to.equal( 'header' ); @@ -42,7 +46,7 @@ describe( 'RootEditableElement', () => { let el; before( () => { - el = new RootEditableElement( 'div' ); + el = new RootEditableElement( document, 'div' ); } ); it( 'should return true for rootElement/containerElement/editable/element, also with correct name and element name', () => { @@ -88,7 +92,7 @@ describe( 'RootEditableElement', () => { describe( '_name', () => { it( 'should set new name to element', () => { - const el = new RootEditableElement( '$root' ); + const el = new RootEditableElement( document, '$root' ); expect( el.name ).to.equal( '$root' ); @@ -99,13 +103,12 @@ describe( 'RootEditableElement', () => { } ); it( 'should be cloned properly', () => { - const root = new RootEditableElement( 'h1' ); - root._document = createDocumentMock(); + const root = new RootEditableElement( document, 'h1' ); root.rootName = 'header'; const newRoot = root._clone(); - expect( newRoot._document ).to.equal( root._document ); + expect( newRoot.document ).to.equal( root.document ); expect( newRoot.rootName ).to.equal( root.rootName ); } ); } ); diff --git a/tests/view/selection.js b/tests/view/selection.js index fe09a0aa1..ed9ba57e0 100644 --- a/tests/view/selection.js +++ b/tests/view/selection.js @@ -18,13 +18,15 @@ import testUtils from '@ckeditor/ckeditor5-core/tests/_utils/utils'; import { expectToThrowCKEditorError } from '@ckeditor/ckeditor5-utils/tests/_utils/utils'; describe( 'Selection', () => { - let selection, el, range1, range2, range3; + let selection, el, range1, range2, range3, viewDocument; testUtils.createSinonSandbox(); beforeEach( () => { - const text = new Text( 'xxxxxxxxxxxxxxxxxxxx' ); - el = new Element( 'p', null, text ); + viewDocument = new Document(); + + const text = new Text( viewDocument, 'xxxxxxxxxxxxxxxxxxxx' ); + el = new Element( viewDocument, 'p', null, text ); selection = new Selection(); @@ -714,8 +716,8 @@ describe( 'Selection', () => { } ); it( 'should collapse selection at node and offset', () => { - const foo = new Text( 'foo' ); - const p = new Element( 'p', null, foo ); + const foo = new Text( viewDocument, 'foo' ); + const p = new Element( viewDocument, 'p', null, foo ); selection.setTo( foo, 0 ); let range = selection.getFirstRange(); @@ -733,7 +735,7 @@ describe( 'Selection', () => { } ); it( 'should throw an error when the second parameter is not passed and first is an item', () => { - const foo = new Text( 'foo' ); + const foo = new Text( viewDocument, 'foo' ); expectToThrowCKEditorError( () => { selection.setTo( foo ); @@ -741,8 +743,8 @@ describe( 'Selection', () => { } ); it( 'should collapse selection at node and flag', () => { - const foo = new Text( 'foo' ); - const p = new Element( 'p', null, foo ); + const foo = new Text( viewDocument, 'foo' ); + const p = new Element( viewDocument, 'p', null, foo ); selection.setTo( foo, 'end' ); let range = selection.getFirstRange(); @@ -898,10 +900,10 @@ describe( 'Selection', () => { } ); it( 'should allow setting selection on an item', () => { - const textNode1 = new Text( 'foo' ); - const textNode2 = new Text( 'bar' ); - const textNode3 = new Text( 'baz' ); - const element = new Element( 'p', null, [ textNode1, textNode2, textNode3 ] ); + const textNode1 = new Text( viewDocument, 'foo' ); + const textNode2 = new Text( viewDocument, 'bar' ); + const textNode3 = new Text( viewDocument, 'baz' ); + const element = new Element( viewDocument, 'p', null, [ textNode1, textNode2, textNode3 ] ); selection.setTo( textNode2, 'on' ); @@ -914,7 +916,7 @@ describe( 'Selection', () => { } ); it( 'should allow setting selection inside an element', () => { - const element = new Element( 'p', null, [ new Text( 'foo' ), new Text( 'bar' ) ] ); + const element = new Element( viewDocument, 'p', null, [ new Text( viewDocument, 'foo' ), new Text( viewDocument, 'bar' ) ] ); selection.setTo( element, 'in' ); @@ -927,7 +929,7 @@ describe( 'Selection', () => { } ); it( 'should allow setting backward selection inside an element', () => { - const element = new Element( 'p', null, [ new Text( 'foo' ), new Text( 'bar' ) ] ); + const element = new Element( viewDocument, 'p', null, [ new Text( viewDocument, 'foo' ), new Text( viewDocument, 'bar' ) ] ); selection.setTo( element, 'in', { backward: true } ); @@ -953,10 +955,9 @@ describe( 'Selection', () => { } ); it( 'should return EditableElement when selection is placed inside', () => { - const viewDocument = new Document(); selection.setTo( viewDocument.selection ); const root = createViewRoot( viewDocument, 'div', 'main' ); - const element = new Element( 'p' ); + const element = new Element( viewDocument, 'p' ); root._appendChild( element ); selection.setTo( Range._createFromParentsAndOffsets( element, 0, element, 0 ) ); diff --git a/tests/view/text.js b/tests/view/text.js index 8d76c6f3d..810f0ede9 100644 --- a/tests/view/text.js +++ b/tests/view/text.js @@ -5,11 +5,18 @@ import Node from '../../src/view/node'; import Text from '../../src/view/text'; +import Document from '../../src/view/document'; describe( 'Text', () => { + let document; + + beforeEach( () => { + document = new Document(); + } ); + describe( 'constructor()', () => { it( 'should create element without attributes', () => { - const text = new Text( 'foo' ); + const text = new Text( document, 'foo' ); expect( text ).to.be.an.instanceof( Node ); expect( text.data ).to.equal( 'foo' ); @@ -21,7 +28,7 @@ describe( 'Text', () => { let text; before( () => { - text = new Text( 'foo' ); + text = new Text( document, 'foo' ); } ); it( 'should return true for node, text', () => { @@ -49,7 +56,7 @@ describe( 'Text', () => { describe( '_clone()', () => { it( 'should return new text with same data', () => { - const text = new Text( 'foo bar' ); + const text = new Text( document, 'foo bar' ); const clone = text._clone(); expect( clone ).to.not.equal( text ); @@ -58,7 +65,7 @@ describe( 'Text', () => { } ); describe( 'isSimilar', () => { - const text = new Text( 'foo' ); + const text = new Text( document, 'foo' ); it( 'should return false when comparing to non-text', () => { expect( text.isSimilar( null ) ).to.be.false; @@ -70,7 +77,7 @@ describe( 'Text', () => { } ); it( 'should return true when data is the same', () => { - const other = new Text( 'foo' ); + const other = new Text( document, 'foo' ); expect( text.isSimilar( other ) ).to.be.true; } ); @@ -85,15 +92,15 @@ describe( 'Text', () => { describe( 'setText', () => { it( 'should change the text', () => { - const text = new Text( 'foo' ); + const text = new Text( document, 'foo' ); text._data = 'bar'; expect( text.data ).to.equal( 'bar' ); } ); it( 'works when using addition assignment operator (+=)', () => { - const foo = new Text( 'foo' ); - const bar = new Text( 'bar' ); + const foo = new Text( document, 'foo' ); + const bar = new Text( document, 'bar' ); foo._data += bar.data; expect( foo.data ).to.equal( 'foobar' ); diff --git a/tests/view/textproxy.js b/tests/view/textproxy.js index e403d49f2..a6c82c355 100644 --- a/tests/view/textproxy.js +++ b/tests/view/textproxy.js @@ -11,14 +11,16 @@ import RootEditableElement from '../../src/view/rooteditableelement'; import createDocumentMock from '../../tests/view/_utils/createdocumentmock'; import { expectToThrowCKEditorError } from '@ckeditor/ckeditor5-utils/tests/_utils/utils'; +import Document from '../../src/view/document'; describe( 'TextProxy', () => { - let text, parent, wrapper, textProxy; + let text, parent, wrapper, textProxy, document; beforeEach( () => { - text = new Text( 'abcdefgh' ); - parent = new ContainerElement( 'p', [], [ text ] ); - wrapper = new ContainerElement( 'div', [], parent ); + document = new Document(); + text = new Text( document, 'abcdefgh' ); + parent = new ContainerElement( document, 'p', [], [ text ] ); + wrapper = new ContainerElement( document, 'div', [], parent ); textProxy = new TextProxy( text, 2, 3 ); } ); @@ -90,31 +92,25 @@ describe( 'TextProxy', () => { } ); describe( 'getDocument', () => { - it( 'should return null if any parent has not set Document', () => { - expect( textProxy.document ).to.be.null; - } ); - it( 'should return Document attached to the parent element', () => { - const docMock = createDocumentMock(); - const root = new RootEditableElement( 'div' ); - root._document = docMock; + const root = new RootEditableElement( document, 'div' ); wrapper.parent = root; - expect( textProxy.document ).to.equal( docMock ); + expect( textProxy.document ).to.equal( document ); } ); - it( 'should return null if element is inside DocumentFragment', () => { - new DocumentFragment( [ wrapper ] ); // eslint-disable-line no-new + it( 'should return Document if element is inside DocumentFragment', () => { + new DocumentFragment( document, [ wrapper ] ); // eslint-disable-line no-new - expect( textProxy.document ).to.be.null; + expect( textProxy.document ).to.equal( document ); } ); } ); describe( 'getRoot', () => { it( 'should return root element', () => { - const root = new RootEditableElement( 'div' ); - root._document = createDocumentMock(); + const docMock = createDocumentMock(); + const root = new RootEditableElement( docMock, 'div' ); wrapper.parent = root; diff --git a/tests/view/treewalker.js b/tests/view/treewalker.js index 3a99ba5d8..3217982e4 100644 --- a/tests/view/treewalker.js +++ b/tests/view/treewalker.js @@ -33,14 +33,14 @@ describe( 'TreeWalker', () => { // | // |- X - textAbcd = new Text( 'abcd' ); - bold = new AttributeElement( 'b', null, [ textAbcd ] ); - charY = new Text( 'y' ); - img2 = new ContainerElement( 'img2' ); - charX = new Text( 'x' ); + textAbcd = new Text( doc, 'abcd' ); + bold = new AttributeElement( doc, 'b', null, [ textAbcd ] ); + charY = new Text( doc, 'y' ); + img2 = new ContainerElement( doc, 'img2' ); + charX = new Text( doc, 'x' ); - paragraph = new ContainerElement( 'p', null, [ bold, charY, img2, charX ] ); - img1 = new ContainerElement( 'img1' ); + paragraph = new ContainerElement( doc, 'p', null, [ bold, charY, img2, charX ] ); + img1 = new ContainerElement( doc, 'img1' ); root._insertChild( 0, [ img1, paragraph ] ); @@ -994,11 +994,11 @@ describe( 'TreeWalker', () => { } ); it( 'should iterate over document fragment', () => { - const foo = new Text( 'foo' ); - const bar = new Text( 'bar' ); - const p = new ContainerElement( 'p', null, foo ); - const b = new AttributeElement( 'b', null, bar ); - const docFrag = new DocumentFragment( [ p, b ] ); + const foo = new Text( doc, 'foo' ); + const bar = new Text( doc, 'bar' ); + const p = new ContainerElement( doc, 'p', null, foo ); + const b = new AttributeElement( doc, 'b', null, bar ); + const docFrag = new DocumentFragment( doc, [ p, b ] ); const expected = [ { diff --git a/tests/view/uielement.js b/tests/view/uielement.js index 2f22f61ee..9bfa37969 100644 --- a/tests/view/uielement.js +++ b/tests/view/uielement.js @@ -7,13 +7,16 @@ import UIElement from '../../src/view/uielement'; import Element from '../../src/view/element'; +import Document from '../../src/view/document'; import { expectToThrowCKEditorError } from '@ckeditor/ckeditor5-utils/tests/_utils/utils'; describe( 'UIElement', () => { - let uiElement; + let uiElement, doc; beforeEach( () => { - uiElement = new UIElement( 'span', { + doc = new Document(); + + uiElement = new UIElement( doc, 'span', { foo: 'bar', style: 'margin-top: 2em;color: white;', class: 'foo bar' @@ -32,7 +35,7 @@ describe( 'UIElement', () => { it( 'should throw if child elements are passed to constructor', () => { expectToThrowCKEditorError( () => { - new UIElement( 'img', null, [ new Element( 'i' ) ] ); // eslint-disable-line no-new + new UIElement( doc, 'img', null, [ new Element( doc, 'i' ) ] ); // eslint-disable-line no-new }, 'view-uielement-cannot-add: Cannot add child nodes to UIElement instance.' ); } ); } ); @@ -41,7 +44,7 @@ describe( 'UIElement', () => { let el; before( () => { - el = new UIElement( 'span' ); + el = new UIElement( doc, 'span' ); } ); it( 'should return true for uiElement/element, also with correct name and element name', () => { @@ -82,7 +85,7 @@ describe( 'UIElement', () => { describe( '_appendChild()', () => { it( 'should throw when try to append new child element', () => { expectToThrowCKEditorError( () => { - uiElement._appendChild( new Element( 'i' ) ); + uiElement._appendChild( new Element( doc, 'i' ) ); }, 'view-uielement-cannot-add: Cannot add child nodes to UIElement instance.' ); } ); } ); @@ -90,7 +93,7 @@ describe( 'UIElement', () => { describe( '_insertChild()', () => { it( 'should throw when try to insert new child element', () => { expectToThrowCKEditorError( () => { - uiElement._insertChild( 0, new Element( 'i' ) ); + uiElement._insertChild( 0, new Element( doc, 'i' ) ); }, 'view-uielement-cannot-add: Cannot add child nodes to UIElement instance.' ); } ); } ); diff --git a/tests/view/view/jumpoveruielement.js b/tests/view/view/jumpoveruielement.js index 74d72a61b..c28318e80 100644 --- a/tests/view/view/jumpoveruielement.js +++ b/tests/view/view/jumpoveruielement.js @@ -21,7 +21,7 @@ describe( 'View', () => { let view, viewDocument, domRoot, domSelection, viewRoot, foo, bar, ui, ui2; function createUIElement( name, contents ) { - const element = new UIElement( name ); + const element = new UIElement( viewDocument, name ); element.render = function( domDocument ) { const domElement = this.toDomElement( domDocument ); @@ -49,8 +49,8 @@ describe( 'View', () => { viewDocument.isFocused = true; - foo = new ViewText( 'foo' ); - bar = new ViewText( 'bar' ); + foo = new ViewText( viewDocument, 'foo' ); + bar = new ViewText( viewDocument, 'bar' ); ui = createUIElement( 'span', 'xxx' ); ui2 = createUIElement( 'span', 'yyy' ); } ); @@ -88,7 +88,7 @@ describe( 'View', () => { describe( 'collapsed selection', () => { it( 'do nothing when another key is pressed', () => { // fooxxx{}bar - const p = new ViewContainerElement( 'p', null, [ foo, ui, bar ] ); + const p = new ViewContainerElement( viewDocument, 'p', null, [ foo, ui, bar ] ); viewRoot._appendChild( p ); view.change( writer => { @@ -106,7 +106,7 @@ describe( 'View', () => { it( 'jump over ui element when right arrow is pressed before ui element - directly before ui element', () => { // foo[]xxxbar - const p = new ViewContainerElement( 'p', null, [ foo, ui, bar ] ); + const p = new ViewContainerElement( viewDocument, 'p', null, [ foo, ui, bar ] ); viewRoot._appendChild( p ); view.change( writer => { @@ -126,7 +126,7 @@ describe( 'View', () => { it( 'jump over ui element when right arrow is pressed before ui element - not directly before ui element', () => { // foo{}xxxbar - const p = new ViewContainerElement( 'p', null, [ foo, ui, bar ] ); + const p = new ViewContainerElement( viewDocument, 'p', null, [ foo, ui, bar ] ); viewRoot._appendChild( p ); view.change( writer => { @@ -146,7 +146,7 @@ describe( 'View', () => { it( 'jump over multiple ui elements when right arrow is pressed before ui element', () => { // foo{}xxxyyybar' - const p = new ViewContainerElement( 'p', null, [ foo, ui, ui2, bar ] ); + const p = new ViewContainerElement( viewDocument, 'p', null, [ foo, ui, ui2, bar ] ); viewRoot._appendChild( p ); view.change( writer => { @@ -166,8 +166,8 @@ describe( 'View', () => { it( 'jump over ui elements at the end of container element', () => { // foo{}xxxyyy - const p = new ViewContainerElement( 'p', null, [ foo, ui, ui2 ] ); - const div = new ViewContainerElement( 'div' ); + const p = new ViewContainerElement( viewDocument, 'p', null, [ foo, ui, ui2 ] ); + const div = new ViewContainerElement( viewDocument, 'div' ); view.change( writer => { viewRoot._appendChild( p ); @@ -188,8 +188,8 @@ describe( 'View', () => { it( 'jump over ui element if selection is in attribute element - case 1', () => { // foo{}xxxbar - const b = new ViewAttribtueElement( 'b', null, foo ); - const p = new ViewContainerElement( 'p', null, [ b, ui, bar ] ); + const b = new ViewAttribtueElement( viewDocument, 'b', null, foo ); + const p = new ViewContainerElement( viewDocument, 'p', null, [ b, ui, bar ] ); viewRoot._appendChild( p ); view.change( writer => { @@ -209,8 +209,8 @@ describe( 'View', () => { it( 'jump over ui element if selection is in attribute element - case 2', () => { // foo[]xxxbar - const b = new ViewAttribtueElement( 'b', null, foo ); - const p = new ViewContainerElement( 'p', null, [ b, ui, bar ] ); + const b = new ViewAttribtueElement( viewDocument, 'b', null, foo ); + const p = new ViewContainerElement( viewDocument, 'p', null, [ b, ui, bar ] ); viewRoot._appendChild( p ); view.change( writer => { @@ -238,9 +238,9 @@ describe( 'View', () => { // // bar // - const b = new ViewAttribtueElement( 'b', null, foo ); - const i = new ViewAttribtueElement( 'i', null, b ); - const p = new ViewContainerElement( 'p', null, [ i, ui, bar ] ); + const b = new ViewAttribtueElement( viewDocument, 'b', null, foo ); + const i = new ViewAttribtueElement( viewDocument, 'i', null, b ); + const p = new ViewContainerElement( viewDocument, 'p', null, [ i, ui, bar ] ); viewRoot._appendChild( p ); @@ -268,9 +268,9 @@ describe( 'View', () => { // // bar // - const b1 = new ViewAttribtueElement( 'b' ); - const b2 = new ViewAttribtueElement( 'b' ); - const p = new ViewContainerElement( 'p', null, [ foo, b1, ui, ui2, b2, bar ] ); + const b1 = new ViewAttribtueElement( viewDocument, 'b' ); + const b2 = new ViewAttribtueElement( viewDocument, 'b' ); + const p = new ViewContainerElement( viewDocument, 'p', null, [ foo, b1, ui, ui2, b2, bar ] ); viewRoot._appendChild( p ); @@ -299,9 +299,9 @@ describe( 'View', () => { // bar // - const b1 = new ViewAttribtueElement( 'b' ); - const b2 = new ViewAttribtueElement( 'b' ); - const p = new ViewContainerElement( 'p', null, [ foo, b1, ui, ui2, b2, bar ] ); + const b1 = new ViewAttribtueElement( viewDocument, 'b' ); + const b2 = new ViewAttribtueElement( viewDocument, 'b' ); + const p = new ViewContainerElement( viewDocument, 'p', null, [ foo, b1, ui, ui2, b2, bar ] ); viewRoot._appendChild( p ); @@ -380,7 +380,7 @@ describe( 'View', () => { it( 'jump over ui element if shift key is pressed', () => { // fo{o}xxxbar - const p = new ViewContainerElement( 'p', null, [ foo, ui, bar ] ); + const p = new ViewContainerElement( viewDocument, 'p', null, [ foo, ui, bar ] ); viewRoot._appendChild( p ); @@ -407,9 +407,9 @@ describe( 'View', () => { // xxx // bar // - const b = new ViewAttribtueElement( 'b', null, foo ); - const i = new ViewAttribtueElement( 'i', null, b ); - const p = new ViewContainerElement( 'p', null, [ i, ui, bar ] ); + const b = new ViewAttribtueElement( viewDocument, 'b', null, foo ); + const i = new ViewAttribtueElement( viewDocument, 'i', null, b ); + const p = new ViewContainerElement( viewDocument, 'p', null, [ i, ui, bar ] ); viewRoot._appendChild( p ); view.change( writer => { @@ -436,9 +436,9 @@ describe( 'View', () => { // // bar // - const b1 = new ViewAttribtueElement( 'b' ); - const b2 = new ViewAttribtueElement( 'b' ); - const p = new ViewContainerElement( 'p', null, [ foo, b1, ui, ui2, b2, bar ] ); + const b1 = new ViewAttribtueElement( viewDocument, 'b' ); + const b2 = new ViewAttribtueElement( viewDocument, 'b' ); + const p = new ViewContainerElement( viewDocument, 'p', null, [ foo, b1, ui, ui2, b2, bar ] ); viewRoot._appendChild( p ); view.change( writer => { diff --git a/tests/view/view/view.js b/tests/view/view/view.js index 7f42ff235..58139e89b 100644 --- a/tests/view/view/view.js +++ b/tests/view/view/view.js @@ -580,7 +580,7 @@ describe( 'view', () => { createViewRoot( viewDocument, 'div', 'main' ); view.attachDomRoot( domDiv ); - viewDocument.getRoot()._appendChild( new ViewElement( 'p' ) ); + viewDocument.getRoot()._appendChild( new ViewElement( viewDocument, 'p' ) ); view.forceRender(); expect( domDiv.childNodes.length ).to.equal( 1 ); @@ -598,7 +598,7 @@ describe( 'view', () => { view.attachDomRoot( domRoot ); - const viewP = new ViewElement( 'p', { class: 'foo' } ); + const viewP = new ViewElement( viewDocument, 'p', { class: 'foo' } ); viewRoot._appendChild( viewP ); view.forceRender(); From 2f4357fea7000af85bdb30c2b353add336d55b7b Mon Sep 17 00:00:00 2001 From: Kamil Piechaczek Date: Thu, 13 Feb 2020 15:35:20 +0100 Subject: [PATCH 05/34] Reverted invalid changes. --- src/dev-utils/view.js | 2 -- tests/view/placeholder.js | 2 +- 2 files changed, 1 insertion(+), 3 deletions(-) diff --git a/src/dev-utils/view.js b/src/dev-utils/view.js index 4cbeddb8a..a6c6735f1 100644 --- a/src/dev-utils/view.js +++ b/src/dev-utils/view.js @@ -471,9 +471,7 @@ class RangeParser { } text = text.replace( regexp, '' ); - node._data = text; - const index = node.index; const parent = node.parent; diff --git a/tests/view/placeholder.js b/tests/view/placeholder.js index 6a5774dca..051124e02 100644 --- a/tests/view/placeholder.js +++ b/tests/view/placeholder.js @@ -83,7 +83,7 @@ describe( 'placeholder', () => { expect( element.hasClass( 'ck-placeholder' ) ).to.be.true; } ); - it.only( 'if element has selection inside set only data attribute', () => { + it( 'if element has selection inside set only data attribute', () => { setData( view, '
[]
another div
' ); const element = viewRoot.getChild( 0 ); From 3b361f881eaa52db0110d0f8aa870d4c6a659da9 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Maciej=20Go=C5=82aszewski?= Date: Thu, 13 Feb 2020 15:58:06 +0100 Subject: [PATCH 06/34] Assign parent element document to the inserted children. --- src/view/element.js | 1 + 1 file changed, 1 insertion(+) diff --git a/src/view/element.js b/src/view/element.js index 0997dde46..ab53183d7 100644 --- a/src/view/element.js +++ b/src/view/element.js @@ -620,6 +620,7 @@ export default class Element extends Node { } node.parent = this; + node.document = this.document; this._children.splice( index, 0, node ); index++; From c7e0226a4ca96c2a3ce2acf5d1561f9ad74a17a9 Mon Sep 17 00:00:00 2001 From: Kamil Piechaczek Date: Mon, 17 Feb 2020 11:59:50 +0100 Subject: [PATCH 07/34] Cannot based on checking the "#document" property on view elements because it always be defined. --- src/conversion/downcasthelpers.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/conversion/downcasthelpers.js b/src/conversion/downcasthelpers.js index 5ae3e060e..4e3202ab5 100644 --- a/src/conversion/downcasthelpers.js +++ b/src/conversion/downcasthelpers.js @@ -544,7 +544,7 @@ export function clearAttributes() { // Not collapsed selection should not have artifacts. if ( range.isCollapsed ) { // Position might be in the node removed by the view writer. - if ( range.end.parent.document ) { + if ( range.end.parent.parent ) { conversionApi.writer.mergeAttributes( range.start ); } } From 9831535ac33c8e80723fc4d970e9cedbd3b8a34b Mon Sep 17 00:00:00 2001 From: Kamil Piechaczek Date: Mon, 17 Feb 2020 12:01:01 +0100 Subject: [PATCH 08/34] DomConverter.domToView() requires an instance of view.Document as a first argument. --- src/dataprocessor/htmldataprocessor.js | 4 +++- src/dataprocessor/xmldataprocessor.js | 4 +++- src/view/domconverter.js | 13 ++++++------- src/view/observer/mutationobserver.js | 4 ++-- src/view/renderer.js | 19 +++++++++++++------ src/view/view.js | 2 +- 6 files changed, 28 insertions(+), 18 deletions(-) diff --git a/src/dataprocessor/htmldataprocessor.js b/src/dataprocessor/htmldataprocessor.js index 72e008c27..f9d82bb62 100644 --- a/src/dataprocessor/htmldataprocessor.js +++ b/src/dataprocessor/htmldataprocessor.js @@ -11,6 +11,7 @@ import BasicHtmlWriter from './basichtmlwriter'; import DomConverter from '../view/domconverter'; +import ViewDocument from '../view/document'; /** * The HTML data processor class. @@ -72,9 +73,10 @@ export default class HtmlDataProcessor { toView( data ) { // Convert input HTML data to DOM DocumentFragment. const domFragment = this._toDom( data ); + const viewDocument = new ViewDocument(); // Convert DOM DocumentFragment to view DocumentFragment. - return this._domConverter.domToView( domFragment ); + return this._domConverter.domToView( viewDocument, domFragment ); } /** diff --git a/src/dataprocessor/xmldataprocessor.js b/src/dataprocessor/xmldataprocessor.js index 50f797caa..5d66c01ca 100644 --- a/src/dataprocessor/xmldataprocessor.js +++ b/src/dataprocessor/xmldataprocessor.js @@ -11,6 +11,7 @@ import BasicHtmlWriter from './basichtmlwriter'; import DomConverter from '../view/domconverter'; +import ViewDocument from '../view/document'; /** * The XML data processor class. @@ -90,9 +91,10 @@ export default class XmlDataProcessor { toView( data ) { // Convert input XML data to DOM DocumentFragment. const domFragment = this._toDom( data ); + const viewDocument = new ViewDocument(); // Convert DOM DocumentFragment to view DocumentFragment. - return this._domConverter.domToView( domFragment, { keepOriginalCase: true } ); + return this._domConverter.domToView( viewDocument, domFragment, { keepOriginalCase: true } ); } /** diff --git a/src/view/domconverter.js b/src/view/domconverter.js index 6d92db3cd..996517fad 100644 --- a/src/view/domconverter.js +++ b/src/view/domconverter.js @@ -14,7 +14,6 @@ import ViewElement from './element'; import ViewPosition from './position'; import ViewRange from './range'; import ViewSelection from './selection'; -import ViewDocument from './document'; import ViewDocumentFragment from './documentfragment'; import ViewTreeWalker from './treewalker'; import { BR_FILLER, getDataWithoutFiller, INLINE_FILLER_LENGTH, isInlineFiller, NBSP_FILLER, startsWithFiller } from './filler'; @@ -374,6 +373,7 @@ export default class DomConverter { * {@link module:engine/view/filler fillers} `null` will be returned. * For all DOM elements rendered by {@link module:engine/view/uielement~UIElement} that UIElement will be returned. * + * @param {module:engine/view/document~Document} viewDocument View document where the created node will belong to. * @param {Node|DocumentFragment} domNode DOM node or document fragment to transform. * @param {Object} [options] Conversion options. * @param {Boolean} [options.bind=false] Determines whether new elements will be bound. @@ -382,13 +382,11 @@ export default class DomConverter { * @returns {module:engine/view/node~Node|module:engine/view/documentfragment~DocumentFragment|null} Converted node or document fragment * or `null` if DOM node is a {@link module:engine/view/filler filler} or the given node is an empty text node. */ - domToView( domNode, options = {} ) { + domToView( viewDocument, domNode, options = {} ) { if ( this.isBlockFiller( domNode, this.blockFillerMode ) ) { return null; } - const viewDocument = new ViewDocument(); - // When node is inside UIElement return that UIElement as it's view representation. const uiElement = this.getParentUIElement( domNode, this._domToViewMapping ); @@ -438,7 +436,7 @@ export default class DomConverter { } if ( options.withChildren || options.withChildren === undefined ) { - for ( const child of this.domChildrenToView( domNode, options ) ) { + for ( const child of this.domChildrenToView( viewDocument, domNode, options ) ) { viewElement._appendChild( child ); } } @@ -452,14 +450,15 @@ export default class DomConverter { * the {@link module:engine/view/domconverter~DomConverter#domToView} method. * Additionally this method omits block {@link module:engine/view/filler filler}, if it exists in the DOM parent. * + * @param {module:engine/view/document~Document} viewDocument View document where the created node will belong to. * @param {HTMLElement} domElement Parent DOM element. * @param {Object} options See {@link module:engine/view/domconverter~DomConverter#domToView} options parameter. * @returns {Iterable.} View nodes. */ - * domChildrenToView( domElement, options = {} ) { + * domChildrenToView( viewDocument, domElement, options = {} ) { for ( let i = 0; i < domElement.childNodes.length; i++ ) { const domChild = domElement.childNodes[ i ]; - const viewChild = this.domToView( domChild, options ); + const viewChild = this.domToView( viewDocument, domChild, options ); if ( viewChild !== null ) { yield viewChild; diff --git a/src/view/observer/mutationobserver.js b/src/view/observer/mutationobserver.js index 44cd39af1..17f365fa7 100644 --- a/src/view/observer/mutationobserver.js +++ b/src/view/observer/mutationobserver.js @@ -206,7 +206,7 @@ export default class MutationObserver extends Observer { for ( const viewElement of mutatedElements ) { const domElement = domConverter.mapViewToDom( viewElement ); const viewChildren = Array.from( viewElement.getChildren() ); - const newViewChildren = Array.from( domConverter.domChildrenToView( domElement, { withChildren: false } ) ); + const newViewChildren = Array.from( domConverter.domChildrenToView( this.document, domElement, { withChildren: false } ) ); // It may happen that as a result of many changes (sth was inserted and then removed), // both elements haven't really changed. #1031 @@ -287,7 +287,7 @@ export default class MutationObserver extends Observer { // Check if mutation added only one node on the end of its parent. if ( mutation.nextSibling === null && mutation.removedNodes.length === 0 && mutation.addedNodes.length == 1 ) { - addedNode = this.domConverter.domToView( mutation.addedNodes[ 0 ], { + addedNode = this.domConverter.domToView( this.document, mutation.addedNodes[ 0 ], { withChildren: false } ); } diff --git a/src/view/renderer.js b/src/view/renderer.js index 49b2ad61a..26aa16fbc 100644 --- a/src/view/renderer.js +++ b/src/view/renderer.js @@ -41,10 +41,9 @@ export default class Renderer { /** * Creates a renderer instance. * - * @param {module:engine/view/domconverter~DomConverter} domConverter Converter instance. - * @param {module:engine/view/documentselection~DocumentSelection} selection View selection. + * @param {module:engine/view/view~View} view View editing controller. */ - constructor( domConverter, selection ) { + constructor( view ) { /** * Set of DOM Documents instances. * @@ -59,7 +58,7 @@ export default class Renderer { * @readonly * @member {module:engine/view/domconverter~DomConverter} */ - this.domConverter = domConverter; + this.domConverter = view.domConverter; /** * Set of nodes which attributes changed and may need to be rendered. @@ -91,7 +90,7 @@ export default class Renderer { * @readonly * @member {module:engine/view/documentselection~DocumentSelection} */ - this.selection = selection; + this.selection = view.document.selection; /** * Indicates if the view document is focused and selection can be rendered. Selection will not be rendered if @@ -116,6 +115,14 @@ export default class Renderer { * @type {null|HTMLElement} */ this._fakeSelectionContainer = null; + + /** + * Reference to the {@link module:engine/view/view~View#document}. + * + * @private + * @member {module:engine/view/document~Document} + */ + this._viewDocument = view.document; } /** @@ -557,7 +564,7 @@ export default class Renderer { remove( actualDomChildren[ i ] ); } else { // 'equal' // Force updating text nodes inside elements which did not change and do not need to be re-rendered (#1125). - this._markDescendantTextToSync( this.domConverter.domToView( expectedDomChildren[ i ] ) ); + this._markDescendantTextToSync( this.domConverter.domToView( this._viewDocument, expectedDomChildren[ i ] ) ); i++; } } diff --git a/src/view/view.js b/src/view/view.js index c380ac5f2..800e4c7a5 100644 --- a/src/view/view.js +++ b/src/view/view.js @@ -103,7 +103,7 @@ export default class View { * @protected * @type {module:engine/view/renderer~Renderer} */ - this._renderer = new Renderer( this.domConverter, this.document.selection ); + this._renderer = new Renderer( this ); this._renderer.bind( 'isFocused' ).to( this.document ); /** From 88b9089ec685b4750011ab0e9239d6b140ccea23 Mon Sep 17 00:00:00 2001 From: Kamil Piechaczek Date: Mon, 17 Feb 2020 12:02:27 +0100 Subject: [PATCH 09/34] Removed obsolete and invalid code. --- src/view/node.js | 16 ---------------- 1 file changed, 16 deletions(-) diff --git a/src/view/node.js b/src/view/node.js index 788f6a9a3..c4b7a4300 100644 --- a/src/view/node.js +++ b/src/view/node.js @@ -117,22 +117,6 @@ export default class Node { return root; } - /** - * {@link module:engine/view/document~Document View document} that owns this node, or `null` if the node is inside - * {@link module:engine/view/documentfragment~DocumentFragment document fragment}. - * - * @readonly - * @type {module:engine/view/document~Document|null} - */ - // get document() { - // // Parent might be Node, null or DocumentFragment. - // if ( this.parent instanceof Node ) { - // return this.parent.document; - // } else { - // return null; - // } - // } - /** * Gets a path to the node. The path is an array containing indices of consecutive ancestors of this node, * beginning from {@link module:engine/view/node~Node#root root}, down to this node's index. From 034b04433314a207bf9d3773db3b599f326934bb Mon Sep 17 00:00:00 2001 From: Kamil Piechaczek Date: Mon, 17 Feb 2020 12:03:21 +0100 Subject: [PATCH 10/34] Use more precise name for an argument in the "needsPlaceholder()" function. --- src/view/placeholder.js | 16 ++++++++-------- 1 file changed, 8 insertions(+), 8 deletions(-) diff --git a/src/view/placeholder.js b/src/view/placeholder.js index 6829ca152..806383056 100644 --- a/src/view/placeholder.js +++ b/src/view/placeholder.js @@ -140,21 +140,21 @@ export function hidePlaceholder( writer, element ) { * {@link module:engine/view/placeholder~enablePlaceholder `enablePlaceholder()`} in that case or make * sure the correct element is passed to the helper. * - * @param {module:engine/view/element~Element} element + * @param {module:engine/view/element~Element|module:engine/view/documentfragment~DocumentFragment} elementOrDocumentFragment * @returns {Boolean} */ -export function needsPlaceholder( element ) { - const doc = element.document; - - // The element was removed from document. - if ( !doc ) { +export function needsPlaceholder( elementOrDocumentFragment ) { + // TODO: How to check whether the element was removed from the document? + if ( elementOrDocumentFragment.root.is( 'documentFragment' ) ) { return false; } // The element is empty only as long as it contains nothing but uiElements. - const isEmptyish = !Array.from( element.getChildren() ) + const isEmptyish = !Array.from( elementOrDocumentFragment.getChildren() ) .some( element => !element.is( 'uiElement' ) ); + const doc = elementOrDocumentFragment.document; + // If the element is empty and the document is blurred. if ( !doc.isFocused && isEmptyish ) { return true; @@ -164,7 +164,7 @@ export function needsPlaceholder( element ) { const selectionAnchor = viewSelection.anchor; // If document is focused and the element is empty but the selection is not anchored inside it. - if ( isEmptyish && selectionAnchor && selectionAnchor.parent !== element ) { + if ( isEmptyish && selectionAnchor && selectionAnchor.parent !== elementOrDocumentFragment ) { return true; } From 8af8720149e9b1472535cc2b1099a5a977331065 Mon Sep 17 00:00:00 2001 From: Kamil Piechaczek Date: Mon, 17 Feb 2020 12:04:58 +0100 Subject: [PATCH 11/34] Adjusted all tests. --- tests/view/domconverter/binding.js | 22 +++---- tests/view/domconverter/dom-to-view.js | 82 +++++++++++++------------- tests/view/domconverter/uielement.js | 10 ++-- tests/view/observer/domeventdata.js | 2 +- tests/view/renderer.js | 16 ++--- 5 files changed, 66 insertions(+), 66 deletions(-) diff --git a/tests/view/domconverter/binding.js b/tests/view/domconverter/binding.js index 0107baadd..029344cd6 100644 --- a/tests/view/domconverter/binding.js +++ b/tests/view/domconverter/binding.js @@ -60,7 +60,7 @@ describe( 'DomConverter', () => { it( 'should return corresponding view document fragment', () => { const domFragment = document.createDocumentFragment(); - const viewFragment = converter.domToView( domFragment ); + const viewFragment = converter.domToView( viewDocument, domFragment ); converter.bindElements( domFragment, viewFragment ); @@ -83,7 +83,7 @@ describe( 'DomConverter', () => { converter.bindElements( domImg, viewImg ); - const viewP = converter.domToView( domP ); + const viewP = converter.domToView( viewDocument, domP ); const viewText = viewP.getChild( 1 ); expect( converter.findCorrespondingViewText( domText ) ).to.equal( viewText ); @@ -93,7 +93,7 @@ describe( 'DomConverter', () => { const domText = document.createTextNode( 'foo' ); const domP = createElement( document, 'p', null, domText ); - const viewP = converter.domToView( domP ); + const viewP = converter.domToView( viewDocument, domP ); const viewText = viewP.getChild( 0 ); converter.bindElements( domP, viewP ); @@ -106,7 +106,7 @@ describe( 'DomConverter', () => { const domText = document.createTextNode( 'foo' ); const domP = createElement( document, 'p', null, [ domImg, domText ] ); - const viewP = converter.domToView( domP ); + const viewP = converter.domToView( viewDocument, domP ); converter.bindElements( domP, viewP ); @@ -118,7 +118,7 @@ describe( 'DomConverter', () => { const domTextBar = document.createTextNode( 'bar' ); const domP = createElement( document, 'p', null, [ domTextFoo, domTextBar ] ); - const viewP = converter.domToView( domP ); + const viewP = converter.domToView( viewDocument, domP ); converter.bindElements( domP, viewP ); @@ -136,7 +136,7 @@ describe( 'DomConverter', () => { const domFiller = document.createTextNode( INLINE_FILLER ); const domP = createElement( document, 'p', null, domFiller ); - const viewP = converter.domToView( domP ); + const viewP = converter.domToView( viewDocument, domP ); converter.bindElements( domP, viewP ); @@ -209,7 +209,7 @@ describe( 'DomConverter', () => { converter.bindElements( domImg, viewImg ); - const viewP = converter.domToView( domP ); + const viewP = converter.domToView( viewDocument, domP ); const viewText = viewP.getChild( 1 ); expect( converter.findCorrespondingDomText( viewText ) ).to.equal( domText ); @@ -221,7 +221,7 @@ describe( 'DomConverter', () => { domP.appendChild( domText ); - const viewP = converter.domToView( domP ); + const viewP = converter.domToView( viewDocument, domP ); const viewText = viewP.getChild( 0 ); converter.bindElements( domP, viewP ); @@ -237,7 +237,7 @@ describe( 'DomConverter', () => { domP.appendChild( domImg ); domP.appendChild( domText ); - const viewP = converter.domToView( domP ); + const viewP = converter.domToView( viewDocument, domP ); const viewText = viewP.getChild( 1 ); converter.bindElements( domP, viewP ); @@ -251,7 +251,7 @@ describe( 'DomConverter', () => { domP.appendChild( domText ); - const viewP = converter.domToView( domP ); + const viewP = converter.domToView( viewDocument, domP ); const viewText = viewP.getChild( 0 ); expect( converter.findCorrespondingDomText( viewText ) ).to.be.null; @@ -259,7 +259,7 @@ describe( 'DomConverter', () => { it( 'should return null if there is no previous sibling and parent', () => { const domText = document.createTextNode( 'foo' ); - const viewText = converter.domToView( domText ); + const viewText = converter.domToView( viewDocument, domText ); expect( converter.findCorrespondingDomText( viewText ) ).to.be.null; } ); diff --git a/tests/view/domconverter/dom-to-view.js b/tests/view/domconverter/dom-to-view.js index 6bb9a68b2..6f0ea61b5 100644 --- a/tests/view/domconverter/dom-to-view.js +++ b/tests/view/domconverter/dom-to-view.js @@ -35,7 +35,7 @@ describe( 'DomConverter', () => { converter.bindElements( domImg, viewImg ); - const viewP = converter.domToView( domP ); + const viewP = converter.domToView( viewDocument, domP ); expect( viewP ).to.be.an.instanceof( ViewElement ); expect( viewP.name ).to.equal( 'p' ); @@ -56,7 +56,7 @@ describe( 'DomConverter', () => { const domText = document.createTextNode( 'foo' ); const domP = createElement( document, 'p', { 'class': 'foo' }, [ domImg, domText ] ); - const viewP = converter.domToView( domP, { bind: true } ); + const viewP = converter.domToView( viewDocument, domP, { bind: true } ); expect( viewP ).to.be.an.instanceof( ViewElement ); expect( viewP.name ).to.equal( 'p' ); @@ -76,7 +76,7 @@ describe( 'DomConverter', () => { const domText = document.createTextNode( 'நிலைக்கு' ); const domP = createElement( document, 'p', { 'class': 'foo' }, [ domText ] ); - const viewP = converter.domToView( domP, { bind: true } ); + const viewP = converter.domToView( viewDocument, domP, { bind: true } ); expect( viewP.childCount ).to.equal( 1 ); @@ -96,7 +96,7 @@ describe( 'DomConverter', () => { converter.bindElements( domImg, viewImg ); - const viewP = converter.domToView( domP, { withChildren: false } ); + const viewP = converter.domToView( viewDocument, domP, { withChildren: false } ); expect( viewP ).to.be.an.instanceof( ViewElement ); expect( viewP.name ).to.equal( 'p' ); @@ -116,7 +116,7 @@ describe( 'DomConverter', () => { domFragment.appendChild( domImg ); domFragment.appendChild( domText ); - const viewFragment = converter.domToView( domFragment, { bind: true } ); + const viewFragment = converter.domToView( viewDocument, domFragment, { bind: true } ); expect( viewFragment ).to.be.an.instanceof( ViewDocumentFragment ); expect( viewFragment.childCount ).to.equal( 2 ); @@ -139,7 +139,7 @@ describe( 'DomConverter', () => { converter.bindElements( domImg, viewImg ); - const viewFragment = converter.domToView( domFragment, { withChildren: false } ); + const viewFragment = converter.domToView( viewDocument, domFragment, { withChildren: false } ); expect( viewFragment ).to.be.an.instanceof( ViewDocumentFragment ); @@ -153,7 +153,7 @@ describe( 'DomConverter', () => { converter.bindDocumentFragments( domFragment, viewFragment ); - const viewFragment2 = converter.domToView( domFragment ); + const viewFragment2 = converter.domToView( viewDocument, domFragment ); expect( viewFragment2 ).to.equal( viewFragment ); } ); @@ -162,19 +162,19 @@ describe( 'DomConverter', () => { // eslint-disable-next-line new-cap const domFiller = BR_FILLER( document ); - expect( converter.domToView( domFiller ) ).to.be.null; + expect( converter.domToView( viewDocument, domFiller ) ).to.be.null; } ); it( 'should return null for empty text node', () => { const textNode = document.createTextNode( '' ); - expect( converter.domToView( textNode ) ).to.be.null; + expect( converter.domToView( viewDocument, textNode ) ).to.be.null; } ); it( 'should return null for a comment', () => { const comment = document.createComment( 'abc' ); - expect( converter.domToView( comment ) ).to.be.null; + expect( converter.domToView( viewDocument, comment ) ).to.be.null; } ); describe( 'it should clear whitespaces', () => { @@ -189,7 +189,7 @@ describe( 'DomConverter', () => { ] ) ] ); - const viewDiv = converter.domToView( domDiv ); + const viewDiv = converter.domToView( viewDocument, domDiv ); expect( viewDiv.childCount ).to.equal( 2 ); expect( viewDiv.getChild( 0 ).getChild( 0 ).data ).to.equal( 'foo' ); @@ -207,7 +207,7 @@ describe( 'DomConverter', () => { document.createTextNode( ' ' ) ] ); - const viewDiv = converter.domToView( domDiv ); + const viewDiv = converter.domToView( viewDocument, domDiv ); expect( viewDiv.childCount ).to.equal( 2 ); expect( viewDiv.getChild( 0 ).getChild( 0 ).data ).to.equal( 'foo' ); @@ -222,7 +222,7 @@ describe( 'DomConverter', () => { document.createTextNode( ' ' ) ] ); - const viewDiv = converter.domToView( domDiv ); + const viewDiv = converter.domToView( viewDocument, domDiv ); expect( viewDiv.childCount ).to.equal( 1 ); expect( viewDiv.getChild( 0 ).getChild( 0 ).data ).to.equal( 'foo' ); @@ -236,7 +236,7 @@ describe( 'DomConverter', () => { document.createTextNode( '\n' ) ] ); - const viewDiv = converter.domToView( domDiv ); + const viewDiv = converter.domToView( viewDocument, domDiv ); expect( viewDiv.childCount ).to.equal( 1 ); expect( viewDiv.getChild( 0 ).getChild( 0 ).data ).to.equal( 'foo' ); @@ -250,7 +250,7 @@ describe( 'DomConverter', () => { document.createTextNode( '\r' ) ] ); - const viewDiv = converter.domToView( domDiv ); + const viewDiv = converter.domToView( viewDocument, domDiv ); expect( viewDiv.childCount ).to.equal( 1 ); expect( viewDiv.getChild( 0 ).getChild( 0 ).data ).to.equal( 'foo' ); @@ -264,7 +264,7 @@ describe( 'DomConverter', () => { document.createTextNode( '\t' ) ] ); - const viewDiv = converter.domToView( domDiv ); + const viewDiv = converter.domToView( viewDocument, domDiv ); expect( viewDiv.childCount ).to.equal( 1 ); expect( viewDiv.getChild( 0 ).getChild( 0 ).data ).to.equal( 'foo' ); @@ -282,7 +282,7 @@ describe( 'DomConverter', () => { ] ) ] ); - const viewDiv = converter.domToView( domDiv ); + const viewDiv = converter.domToView( viewDocument, domDiv ); expect( viewDiv.childCount ).to.equal( 2 ); expect( viewDiv.getChild( 0 ).getChild( 0 ).data ) @@ -299,7 +299,7 @@ describe( 'DomConverter', () => { ] ) ] ); - const viewDiv = converter.domToView( domDiv ); + const viewDiv = converter.domToView( viewDocument, domDiv ); expect( viewDiv.childCount ).to.equal( 1 ); expect( viewDiv.getChild( 0 ).getChild( 0 ).data ).to.equal( 'foo' ); @@ -313,7 +313,7 @@ describe( 'DomConverter', () => { ] ) ] ); - const viewDiv = converter.domToView( domDiv ); + const viewDiv = converter.domToView( viewDocument, domDiv ); expect( viewDiv.childCount ).to.equal( 1 ); expect( viewDiv.getChild( 0 ).getChild( 0 ).data ).to.equal( 'foo' ); @@ -326,7 +326,7 @@ describe( 'DomConverter', () => { document.createTextNode( ' bar' ) ] ); - const viewP = converter.domToView( domP ); + const viewP = converter.domToView( viewDocument, domP ); expect( viewP.childCount ).to.equal( 3 ); expect( viewP.getChild( 2 ).data ).to.equal( 'bar' ); @@ -339,7 +339,7 @@ describe( 'DomConverter', () => { document.createTextNode( ' \u00a0bar' ) ] ); - const viewP = converter.domToView( domP ); + const viewP = converter.domToView( viewDocument, domP ); expect( viewP.childCount ).to.equal( 3 ); expect( viewP.getChild( 2 ).data ).to.equal( ' bar' ); @@ -354,7 +354,7 @@ describe( 'DomConverter', () => { document.createTextNode( ' bar' ) ] ); - const viewP = converter.domToView( domP ); + const viewP = converter.domToView( viewDocument, domP ); expect( viewP.childCount ).to.equal( 3 ); expect( viewP.getChild( 2 ).data ).to.equal( 'bar' ); @@ -369,7 +369,7 @@ describe( 'DomConverter', () => { ] ) ] ); - const viewP = converter.domToView( domP ); + const viewP = converter.domToView( viewDocument, domP ); expect( viewP.childCount ).to.equal( 3 ); expect( viewP.getChild( 2 ).getChild( 0 ).data ).to.equal( 'bar' ); @@ -384,7 +384,7 @@ describe( 'DomConverter', () => { document.createTextNode( 'x' ) ] ); - const viewP = converter.domToView( domP ); + const viewP = converter.domToView( viewDocument, domP ); expect( viewP.childCount ).to.equal( 5 ); expect( viewP.getChild( 2 ).data ).to.equal( 'foo ' ); @@ -400,7 +400,7 @@ describe( 'DomConverter', () => { ] ) ] ); - const viewDiv = converter.domToView( domDiv ); + const viewDiv = converter.domToView( viewDocument, domDiv ); expect( viewDiv.getChild( 0 ).getChild( 0 ).data ).to.equal( 'f o o' ); expect( viewDiv.getChild( 1 ).getChild( 0 ).data ).to.equal( 'fo o' ); @@ -415,7 +415,7 @@ describe( 'DomConverter', () => { document.createTextNode( '\n\n \t\r\n' ) ] ); - const viewDiv = converter.domToView( domDiv ); + const viewDiv = converter.domToView( viewDocument, domDiv ); expect( viewDiv.childCount ).to.equal( 1 ); expect( viewDiv.getChild( 0 ).getChild( 0 ).data ).to.equal( 'f o o' ); @@ -433,7 +433,7 @@ describe( 'DomConverter', () => { domElement.appendChild( document.createTextNode( text.replace( /_/g, '\u00A0' ) ) ); } - const viewElement = converter.domToView( domElement ); + const viewElement = converter.domToView( viewDocument, domElement ); let data = ''; @@ -523,7 +523,7 @@ describe( 'DomConverter', () => { ] ) ] ); - const viewDiv = converter.domToView( domDiv ); + const viewDiv = converter.domToView( viewDocument, domDiv ); expect( viewDiv.getChild( 0 ).getChild( 0 ).data ).to.equal( ' foo\n foo ' ); } ); @@ -538,7 +538,7 @@ describe( 'DomConverter', () => { document.createTextNode( 'word' ) ] ); - const viewDiv = converter.domToView( domDiv ); + const viewDiv = converter.domToView( viewDocument, domDiv ); expect( viewDiv.getChild( 1 ).name ).to.equal( 'span' ); expect( viewDiv.getChild( 1 ).childCount ).to.equal( 1 ); @@ -555,7 +555,7 @@ describe( 'DomConverter', () => { document.createTextNode( 'word' ) ] ); - const viewDiv = converter.domToView( domDiv ); + const viewDiv = converter.domToView( viewDocument, domDiv ); expect( viewDiv.getChild( 1 ).name ).to.equal( 'span' ); expect( viewDiv.getChild( 1 ).childCount ).to.equal( 1 ); @@ -579,7 +579,7 @@ describe( 'DomConverter', () => { ] ) ] ); - const viewDiv = converter.domToView( domDiv ); + const viewDiv = converter.domToView( viewDocument, domDiv ); expect( viewDiv.getChild( 0 ).name ).to.equal( 'span' ); expect( viewDiv.getChild( 0 ).childCount ).to.equal( 2 ); @@ -597,7 +597,7 @@ describe( 'DomConverter', () => { createElement( document, 'br' ) ] ); - const viewP = converter.domToView( domP ); + const viewP = converter.domToView( viewDocument, domP ); expect( viewP.childCount ).to.equal( 2 ); expect( viewP.getChild( 0 ).data ).to.equal( 'foo ' ); @@ -609,7 +609,7 @@ describe( 'DomConverter', () => { createElement( document, 'br' ) ] ); - const viewP = converter.domToView( domP ); + const viewP = converter.domToView( viewDocument, domP ); expect( viewP.childCount ).to.equal( 2 ); expect( viewP.getChild( 0 ).data ).to.equal( 'foo ' ); @@ -621,7 +621,7 @@ describe( 'DomConverter', () => { createElement( document, 'br' ) ] ); - const viewP = converter.domToView( domP ); + const viewP = converter.domToView( viewDocument, domP ); expect( viewP.childCount ).to.equal( 2 ); expect( viewP.getChild( 0 ).data ).to.equal( 'foo ' ); @@ -635,7 +635,7 @@ describe( 'DomConverter', () => { createElement( document, 'br' ) ] ); - const viewP = converter.domToView( domP ); + const viewP = converter.domToView( viewDocument, domP ); expect( viewP.childCount ).to.equal( 2 ); expect( viewP.getChild( 0 ).getChild( 0 ).data ).to.equal( 'foo ' ); @@ -649,7 +649,7 @@ describe( 'DomConverter', () => { describe( 'clearing auto filler', () => { it( 'should remove inline filler when converting dom to view', () => { const text = document.createTextNode( INLINE_FILLER + 'foo' ); - const view = converter.domToView( text ); + const view = converter.domToView( viewDocument, text ); expect( view.data ).to.equal( 'foo' ); } ); @@ -657,14 +657,14 @@ describe( 'DomConverter', () => { // See https://github.com/ckeditor/ckeditor5/issues/692. it( 'should not remove space after inline filler if previous node nor next node does not exist', () => { const text = document.createTextNode( INLINE_FILLER + ' ' ); - const view = converter.domToView( text ); + const view = converter.domToView( viewDocument, text ); expect( view.data ).to.equal( ' ' ); } ); it( 'should convert non breaking space to normal space after inline filler', () => { const text = document.createTextNode( INLINE_FILLER + '\u00A0' ); - const view = converter.domToView( text ); + const view = converter.domToView( viewDocument, text ); expect( view.data ).to.equal( ' ' ); } ); @@ -677,7 +677,7 @@ describe( 'DomConverter', () => { const domText = document.createTextNode( 'foo' ); const domP = createElement( document, 'p', null, [ domImg, domText ] ); - const viewChildren = Array.from( converter.domChildrenToView( domP ) ); + const viewChildren = Array.from( converter.domChildrenToView( viewDocument, domP ) ); expect( viewChildren.length ).to.equal( 2 ); expect( stringify( viewChildren[ 0 ] ) ).to.equal( '' ); @@ -689,7 +689,7 @@ describe( 'DomConverter', () => { const domFiller = BR_FILLER( document ); const domP = createElement( document, 'p', null, domFiller ); - const viewChildren = Array.from( converter.domChildrenToView( domP ) ); + const viewChildren = Array.from( converter.domChildrenToView( viewDocument, domP ) ); expect( viewChildren.length ).to.equal( 0 ); } ); @@ -699,7 +699,7 @@ describe( 'DomConverter', () => { const domB = createElement( document, 'b', null, 'bar' ); const domP = createElement( document, 'p', null, [ domB, domText ] ); - const viewChildren = Array.from( converter.domChildrenToView( domP, { withChildren: false } ) ); + const viewChildren = Array.from( converter.domChildrenToView( viewDocument, domP, { withChildren: false } ) ); expect( viewChildren.length ).to.equal( 2 ); expect( stringify( viewChildren[ 0 ] ) ).to.equal( '' ); diff --git a/tests/view/domconverter/uielement.js b/tests/view/domconverter/uielement.js index 0faa4c230..c3b7802ca 100644 --- a/tests/view/domconverter/uielement.js +++ b/tests/view/domconverter/uielement.js @@ -63,7 +63,7 @@ describe( 'DOMConverter UIElement integration', () => { const uiElement = createUIElement( 'div' ); const domElement = converter.viewToDom( uiElement, document, { bind: true } ); - expect( converter.domToView( domElement ) ).to.equal( uiElement ); + expect( converter.domToView( viewDocument, domElement ) ).to.equal( uiElement ); } ); it( 'should return UIElement for nodes inside', () => { @@ -73,10 +73,10 @@ describe( 'DOMConverter UIElement integration', () => { const domParagraph = domElement.childNodes[ 0 ]; const domSpan = domParagraph.childNodes[ 0 ]; - expect( converter.domToView( domParagraph ) ).to.equal( uiElement ); - expect( converter.domToView( domSpan ) ).to.be.equal( uiElement ); - expect( converter.domToView( domParagraph.childNodes[ 0 ] ) ).equal( uiElement ); - expect( converter.domToView( domSpan.childNodes[ 0 ] ) ).equal( uiElement ); + expect( converter.domToView( viewDocument, domParagraph ) ).to.equal( uiElement ); + expect( converter.domToView( viewDocument, domSpan ) ).to.be.equal( uiElement ); + expect( converter.domToView( viewDocument, domParagraph.childNodes[ 0 ] ) ).equal( uiElement ); + expect( converter.domToView( viewDocument, domSpan.childNodes[ 0 ] ) ).equal( uiElement ); } ); } ); diff --git a/tests/view/observer/domeventdata.js b/tests/view/observer/domeventdata.js index 735fbe2ea..b736d0444 100644 --- a/tests/view/observer/domeventdata.js +++ b/tests/view/observer/domeventdata.js @@ -19,7 +19,7 @@ describe( 'DomEventData', () => { domRoot.innerHTML = '
'; document.body.appendChild( domRoot ); - viewBody = view.domConverter.domToView( document.body, { bind: true } ); + viewBody = view.domConverter.domToView( viewDocument, document.body, { bind: true } ); } ); afterEach( () => { diff --git a/tests/view/renderer.js b/tests/view/renderer.js index 74522a961..26841a6a1 100644 --- a/tests/view/renderer.js +++ b/tests/view/renderer.js @@ -13,10 +13,7 @@ import ViewAttributeElement from '../../src/view/attributeelement'; import ViewText from '../../src/view/text'; import ViewRange from '../../src/view/range'; import ViewPosition from '../../src/view/position'; -import ViewDocument from '../../src/view/document'; import UIElement from '../../src/view/uielement'; -import DocumentSelection from '../../src/view/documentselection'; -import DomConverter from '../../src/view/domconverter'; import Renderer from '../../src/view/renderer'; import DocumentFragment from '../../src/view/documentfragment'; import DowncastWriter from '../../src/view/downcastwriter'; @@ -31,15 +28,18 @@ import env from '@ckeditor/ckeditor5-utils/src/env'; import { expectToThrowCKEditorError } from '@ckeditor/ckeditor5-utils/tests/_utils/utils'; describe( 'Renderer', () => { - let selection, domConverter, renderer, viewDocument; + let view, selection, domConverter, renderer, viewDocument; testUtils.createSinonSandbox(); beforeEach( () => { - selection = new DocumentSelection(); - domConverter = new DomConverter(); - viewDocument = new ViewDocument(); - renderer = new Renderer( domConverter, selection ); + view = new View(); + viewDocument = view.document; + + renderer = new Renderer( view ); + domConverter = renderer.domConverter; + selection = renderer.selection; + renderer.domDocuments.add( document ); } ); From 1fdcb8bb3d4fd6f98b7af298aa1812d5e18dd44c Mon Sep 17 00:00:00 2001 From: Kamil Piechaczek Date: Mon, 17 Feb 2020 12:22:19 +0100 Subject: [PATCH 12/34] Added test for checking whether #document property is being updated after inserting a children to an element. --- tests/view/element.js | 9 +++++++++ 1 file changed, 9 insertions(+) diff --git a/tests/view/element.js b/tests/view/element.js index d221095c3..436c60529 100644 --- a/tests/view/element.js +++ b/tests/view/element.js @@ -403,6 +403,15 @@ describe( 'Element', () => { expect( element.getChild( 0 ) ).to.be.instanceof( Text ); expect( element.getChild( 0 ).data ).to.equal( 'cxy' ); } ); + + it( 'set proper #document on inserted children', () => { + const anotherDocument = new Document(); + const anotherEl = new Element( anotherDocument, 'p' ); + + parent._insertChild( 0, anotherEl ); + + expect( anotherEl.document ).to.be.equal( document ); + } ); } ); describe( 'getChildIndex', () => { From dd78af173f886e3769e37fa6ac640f0cfc2bed77 Mon Sep 17 00:00:00 2001 From: Kamil Piechaczek Date: Mon, 17 Feb 2020 16:04:41 +0100 Subject: [PATCH 13/34] Improved writers constructor docs. --- src/view/downcastwriter.js | 3 +++ src/view/upcastwriter.js | 3 +++ 2 files changed, 6 insertions(+) diff --git a/src/view/downcastwriter.js b/src/view/downcastwriter.js index 4455c5ddd..e695cf5b7 100644 --- a/src/view/downcastwriter.js +++ b/src/view/downcastwriter.js @@ -37,6 +37,9 @@ import { isPlainObject } from 'lodash-es'; * section of the {@glink framework/guides/architecture/editing-engine Editing engine architecture} guide. */ export default class DowncastWriter { + /** + * @param {module:engine/view/document~Document} document + */ constructor( document ) { /** * @readonly diff --git a/src/view/upcastwriter.js b/src/view/upcastwriter.js index 0777b2345..71361db2f 100644 --- a/src/view/upcastwriter.js +++ b/src/view/upcastwriter.js @@ -35,6 +35,9 @@ import Selection from './selection'; * writer.appendChild( text, someViewElement ); */ export default class UpcastWriter { + /** + * @param {module:engine/view/document~Document} document + */ constructor( document ) { /** * @readonly From 8b56db16b82e7826ff8ca4e4085758e785f91645 Mon Sep 17 00:00:00 2001 From: Kamil Piechaczek Date: Tue, 18 Feb 2020 13:53:29 +0100 Subject: [PATCH 14/34] StylesProcessor is not singleton anymore. --- src/conversion/viewconsumable.js | 21 +++++--- src/view/document.js | 12 ++++- src/view/element.js | 2 +- src/view/stylesmap.js | 70 ++++--------------------- tests/conversion/viewconsumable.js | 16 +++--- tests/view/_utils/createdocumentmock.js | 2 + tests/view/document.js | 5 +- tests/view/element.js | 7 ++- tests/view/styles/background.js | 7 ++- tests/view/styles/border.js | 7 ++- tests/view/styles/margin.js | 7 ++- tests/view/styles/padding.js | 7 ++- tests/view/stylesmap.js | 17 +----- 13 files changed, 68 insertions(+), 112 deletions(-) diff --git a/src/conversion/viewconsumable.js b/src/conversion/viewconsumable.js index 8b693e64b..3f7d45cb4 100644 --- a/src/conversion/viewconsumable.js +++ b/src/conversion/viewconsumable.js @@ -9,7 +9,6 @@ import { isArray } from 'lodash-es'; import CKEditorError from '@ckeditor/ckeditor5-utils/src/ckeditorerror'; -import StylesMap from '../view/stylesmap'; /** * Class used for handling consumption of view {@link module:engine/view/element~Element elements}, @@ -89,7 +88,7 @@ export default class ViewConsumable { // For elements create new ViewElementConsumables or update already existing one. if ( !this._consumables.has( element ) ) { - elementConsumables = new ViewElementConsumables(); + elementConsumables = new ViewElementConsumables( element ); this._consumables.set( element, elementConsumables ); } else { elementConsumables = this._consumables.get( element ); @@ -239,6 +238,7 @@ export default class ViewConsumable { */ static consumablesFromElement( element ) { const consumables = { + element, name: true, attributes: [], classes: [], @@ -284,7 +284,7 @@ export default class ViewConsumable { */ static createFrom( from, instance ) { if ( !instance ) { - instance = new ViewConsumable(); + instance = new ViewConsumable( from ); } if ( from.is( 'text' ) ) { @@ -319,8 +319,17 @@ export default class ViewConsumable { class ViewElementConsumables { /** * Creates ViewElementConsumables instance. + * + * @param {module:engine/view/node~Node|module:engine/view/documentfragment~DocumentFragment} from View node or document fragment + * from which `ViewElementConsumables` is being created. */ - constructor() { + constructor( from ) { + /** + * @readonly + * @member {module:engine/view/node~Node|module:engine/view/documentfragment~DocumentFragment} + */ + this.element = from; + /** * Flag indicating if name of the element can be consumed. * @@ -510,7 +519,7 @@ class ViewElementConsumables { consumables.set( name, true ); if ( type === 'styles' ) { - for ( const alsoName of StylesMap.getRelatedStyles( name ) ) { + for ( const alsoName of this.element.document.stylesProcessor.getRelatedStyles( name ) ) { consumables.set( alsoName, true ); } } @@ -577,7 +586,7 @@ class ViewElementConsumables { consumables.set( name, false ); if ( type == 'styles' ) { - for ( const toConsume of StylesMap.getRelatedStyles( name ) ) { + for ( const toConsume of this.element.document.stylesProcessor.getRelatedStyles( name ) ) { consumables.set( toConsume, false ); } } diff --git a/src/view/document.js b/src/view/document.js index 0cc471375..595e25693 100644 --- a/src/view/document.js +++ b/src/view/document.js @@ -11,7 +11,7 @@ import DocumentSelection from './documentselection'; import Collection from '@ckeditor/ckeditor5-utils/src/collection'; import mix from '@ckeditor/ckeditor5-utils/src/mix'; import ObservableMixin from '@ckeditor/ckeditor5-utils/src/observablemixin'; -import StylesMap from './stylesmap'; +import { StylesProcessor } from './stylesmap'; // @if CK_DEBUG_ENGINE // const { logDocument } = require( '../dev-utils/utils' ); @@ -47,6 +47,14 @@ export default class Document { */ this.roots = new Collection( { idProperty: 'rootName' } ); + /** + * StylesProcessor is responsible for writing and reading a normalized styles object. + * + * @readonly + * @member {module:engine/view/stylesmap~StylesProcessor} + */ + this.stylesProcessor = new StylesProcessor(); + /** * Defines whether document is in read-only mode. * @@ -174,7 +182,7 @@ export default class Document { * @param {Function} callback */ addStyleProcessorRules( callback ) { - callback( StylesMap._styleProcessor ); + callback( this.stylesProcessor ); } /** diff --git a/src/view/element.js b/src/view/element.js index ab53183d7..aba080731 100644 --- a/src/view/element.js +++ b/src/view/element.js @@ -111,7 +111,7 @@ export default class Element extends Node { * @protected * @member {module:engine/view/stylesmap~StylesMap} module:engine/view/element~Element#_styles */ - this._styles = new StylesMap(); + this._styles = new StylesMap( this.document.stylesProcessor ); if ( this._attrs.has( 'style' ) ) { // Remove style attribute and handle it by styles map. diff --git a/src/view/stylesmap.js b/src/view/stylesmap.js index 8f54ff62e..4b877c3fe 100644 --- a/src/view/stylesmap.js +++ b/src/view/stylesmap.js @@ -17,28 +17,28 @@ import { get, isObject, merge, set, unset } from 'lodash-es'; export default class StylesMap { /** * Creates Styles instance. + * + * @param {module:engine/view/stylesmap~StylesProcessor} styleProcessor */ - constructor() { + constructor( styleProcessor ) { /** * Keeps an internal representation of styles map. Normalized styles are kept as object tree to allow unified modification and * value access model using lodash's get, set, unset, etc methods. * * When no style processor rules are defined the it acts as simple key-value storage. * - * @type {Object} * @private + * @type {Object} */ this._styles = {}; - // Hide _styleProcessor from the watchdog by making this property non-enumarable. Watchdog checks errors for their editor origin - // by checking if two objects are connected through properties. Using singleton is against this check as it would detect - // that two editors are connected through single style processor instance. - Object.defineProperty( this, '_styleProcessor', { - get() { - return StylesMap._styleProcessor; - }, - enumerable: false - } ); + /** + * An instance of the {@link module:engine/view/stylesmap~StylesProcessor}. + * + * @private + * @member {module:engine/view/stylesmap~StylesProcessor} + */ + this._styleProcessor = styleProcessor; } /** @@ -371,28 +371,6 @@ export default class StylesMap { this._styles = {}; } - /** - * Returns related style names. - * - * // Enable 'margin' shorthand processing: - * editor.editing.view.document.addStyleProcessorRules( addMarginRules ); - * - * StylesMap.getRelatedStyles( 'margin' ); - * // will return: [ 'margin-top', 'margin-right', 'margin-bottom', 'margin-left' ]; - * - * StylesMap.getRelatedStyles( 'margin-top' ); - * // will return: [ 'margin' ]; - * - * **Note**: To define new style relations load an existing style processor (as shown above) or use - * {@link module:engine/view/stylesmap~StylesProcessor#setStyleRelation `StylesProcessor.setStyleRelation()`}. - * - * @param {String} name - * @returns {Array.} - */ - static getRelatedStyles( name ) { - return this._styleProcessor.getRelatedStyles( name ); - } - /** * Returns normalized styles entries for further processing. * @@ -439,32 +417,6 @@ export default class StylesMap { this.remove( parentPath ); } } - - /** - * Returns global StylesProcessor instance. - * - * @returns {module:engine/view/stylesmap~StylesProcessor} - * @private - */ - static get _styleProcessor() { - if ( !this._processor ) { - this._processor = new StylesProcessor(); - } - - return this._processor; - } - - /** - * Set new StylesProcessor instance. - * - * This is an internal method used mostly in tests. - * - * @param processor - * @protected - */ - static _setProcessor( processor ) { - this._processor = processor; - } } /** diff --git a/tests/conversion/viewconsumable.js b/tests/conversion/viewconsumable.js index 79f04bd80..8abd8faf1 100644 --- a/tests/conversion/viewconsumable.js +++ b/tests/conversion/viewconsumable.js @@ -8,7 +8,6 @@ import ViewElement from '../../src/view/element'; import ViewText from '../../src/view/text'; import ViewDocumentFragment from '../../src/view/documentfragment'; import ViewConsumable from '../../src/conversion/viewconsumable'; -import StylesMap, { StylesProcessor } from '../../src/view/stylesmap'; import { addBorderRules } from '../../src/view/styles/border'; import { addMarginRules } from '../../src/view/styles/margin'; import { addPaddingRules } from '../../src/view/styles/padding'; @@ -16,8 +15,15 @@ import { addPaddingRules } from '../../src/view/styles/padding'; describe( 'ViewConsumable', () => { let viewConsumable, el, viewDocument; - beforeEach( () => { + before( () => { viewDocument = new ViewDocument(); + + addBorderRules( viewDocument.stylesProcessor ); + addMarginRules( viewDocument.stylesProcessor ); + addPaddingRules( viewDocument.stylesProcessor ); + } ); + + beforeEach( () => { viewConsumable = new ViewConsumable(); el = new ViewElement( viewDocument, 'p' ); } ); @@ -558,13 +564,7 @@ describe( 'ViewConsumable', () => { describe( 'style shorthands handling', () => { before( () => { - const stylesProcessor = new StylesProcessor(); - - StylesMap._setProcessor( stylesProcessor ); - addBorderRules( stylesProcessor ); - addMarginRules( stylesProcessor ); - addPaddingRules( stylesProcessor ); } ); describe( 'add', () => { diff --git a/tests/view/_utils/createdocumentmock.js b/tests/view/_utils/createdocumentmock.js index 43ecbebc0..05e645b91 100644 --- a/tests/view/_utils/createdocumentmock.js +++ b/tests/view/_utils/createdocumentmock.js @@ -5,6 +5,7 @@ import ObservableMixin from '@ckeditor/ckeditor5-utils/src/observablemixin'; import DocumentSelection from '../../../src/view/documentselection'; +import { StylesProcessor } from '../../../src/view/stylesmap'; /** * Creates {@link module:engine/view/document~Document view Document} mock. @@ -16,6 +17,7 @@ export default function createDocumentMock() { doc.set( 'isFocused', false ); doc.set( 'isReadOnly', false ); doc.selection = new DocumentSelection(); + doc.stylesProcessor = new StylesProcessor(); return doc; } diff --git a/tests/view/document.js b/tests/view/document.js index 16c442d76..8bf2e919f 100644 --- a/tests/view/document.js +++ b/tests/view/document.js @@ -10,7 +10,6 @@ import Document from '../../src/view/document'; import testUtils from '@ckeditor/ckeditor5-core/tests/_utils/utils'; import count from '@ckeditor/ckeditor5-utils/src/count'; import createViewRoot from './_utils/createroot'; -import StylesMap from '../../src/view/stylesmap'; describe( 'Document', () => { let domRoot, viewDocument; @@ -94,13 +93,13 @@ describe( 'Document', () => { } ); describe( 'addStyleProcessorRules()', () => { - it( 'should ', () => { + it( 'should execute callback with an instance of StyleProcessor as the first argument', () => { const spy = sinon.spy(); viewDocument.addStyleProcessorRules( spy ); sinon.assert.calledOnce( spy ); - sinon.assert.calledWithExactly( spy, StylesMap._styleProcessor ); + sinon.assert.calledWithExactly( spy, viewDocument.stylesProcessor ); } ); } ); } ); diff --git a/tests/view/element.js b/tests/view/element.js index 436c60529..d227d1741 100644 --- a/tests/view/element.js +++ b/tests/view/element.js @@ -237,7 +237,12 @@ describe( 'Element', () => { } ); describe( 'isSimilar()', () => { - const el = new Element( document, 'p', { foo: 'bar' } ); + let el; + + beforeEach( () => { + el = new Element( document, 'p', { foo: 'bar' } ); + } ); + it( 'should return false when comparing to non-element', () => { expect( el.isSimilar( null ) ).to.be.false; expect( el.isSimilar( {} ) ).to.be.false; diff --git a/tests/view/styles/background.js b/tests/view/styles/background.js index e10c680b6..bb8c3aa6a 100644 --- a/tests/view/styles/background.js +++ b/tests/view/styles/background.js @@ -7,16 +7,15 @@ import StylesMap, { StylesProcessor } from '../../../src/view/stylesmap'; import { addBackgroundRules } from '../../../src/view/styles/background'; describe( 'Background styles normalization', () => { - let styles; + let styles, stylesProcessor; before( () => { - const stylesProcessor = new StylesProcessor(); - StylesMap._setProcessor( stylesProcessor ); + stylesProcessor = new StylesProcessor(); addBackgroundRules( stylesProcessor ); } ); beforeEach( () => { - styles = new StylesMap(); + styles = new StylesMap( stylesProcessor ); } ); it( 'should normalize background', () => { diff --git a/tests/view/styles/border.js b/tests/view/styles/border.js index cbab88c8f..b8ff58f2f 100644 --- a/tests/view/styles/border.js +++ b/tests/view/styles/border.js @@ -7,16 +7,15 @@ import StylesMap, { StylesProcessor } from '../../../src/view/stylesmap'; import { addBorderRules } from '../../../src/view/styles/border'; describe( 'Border styles normalization', () => { - let styles; + let styles, stylesProcessor; before( () => { - const stylesProcessor = new StylesProcessor(); - StylesMap._setProcessor( stylesProcessor ); + stylesProcessor = new StylesProcessor(); addBorderRules( stylesProcessor ); } ); beforeEach( () => { - styles = new StylesMap(); + styles = new StylesMap( stylesProcessor ); } ); it( 'should parse border shorthand', () => { diff --git a/tests/view/styles/margin.js b/tests/view/styles/margin.js index d21d56374..e60d52d91 100644 --- a/tests/view/styles/margin.js +++ b/tests/view/styles/margin.js @@ -7,16 +7,15 @@ import StylesMap, { StylesProcessor } from '../../../src/view/stylesmap'; import { addMarginRules } from '../../../src/view/styles/margin'; describe( 'Margin styles normalizer', () => { - let styles; + let styles, stylesProcessor; before( () => { - const stylesProcessor = new StylesProcessor(); - StylesMap._setProcessor( stylesProcessor ); + stylesProcessor = new StylesProcessor(); addMarginRules( stylesProcessor ); } ); beforeEach( () => { - styles = new StylesMap(); + styles = new StylesMap( stylesProcessor ); } ); it( 'should set all margins (1 value defined)', () => { diff --git a/tests/view/styles/padding.js b/tests/view/styles/padding.js index a1e8fd228..76baa9823 100644 --- a/tests/view/styles/padding.js +++ b/tests/view/styles/padding.js @@ -7,16 +7,15 @@ import StylesMap, { StylesProcessor } from '../../../src/view/stylesmap'; import { addPaddingRules } from '../../../src/view/styles/padding'; describe( 'Padding styles normalization', () => { - let styles; + let styles, stylesProcessor; before( () => { - const stylesProcessor = new StylesProcessor(); - StylesMap._setProcessor( stylesProcessor ); + stylesProcessor = new StylesProcessor(); addPaddingRules( stylesProcessor ); } ); beforeEach( () => { - styles = new StylesMap(); + styles = new StylesMap( stylesProcessor ); } ); it( 'should set all padding values (1 value defined)', () => { diff --git a/tests/view/stylesmap.js b/tests/view/stylesmap.js index 25a7726d3..8a004c698 100644 --- a/tests/view/stylesmap.js +++ b/tests/view/stylesmap.js @@ -26,8 +26,7 @@ describe( 'StylesMap', () => { stylesProcessor.setReducer( 'foo', getBoxSidesValueReducer( 'foo' ) ); addMarginRules( stylesProcessor ); - StylesMap._setProcessor( stylesProcessor ); - stylesMap = new StylesMap(); + stylesMap = new StylesMap( stylesProcessor ); } ); describe( 'size getter', () => { @@ -272,18 +271,4 @@ describe( 'StylesMap', () => { expect( stylesMap.getStyleNames() ).to.deep.equal( [ 'foo' ] ); } ); } ); - - describe( 'static _styleProcessor getter', () => { - it( 'should return StyleProcessor instance', () => { - // Set undefined to reset field value for code coverage. - StylesMap._setProcessor( undefined ); - expect( StylesMap._styleProcessor ).to.be.instanceOf( StylesProcessor ); - } ); - - it( 'should return the same StyleProcessor instance on consecutive calls', () => { - const stylesProcessor = StylesMap._styleProcessor; - - expect( StylesMap._styleProcessor ).to.equal( stylesProcessor ); - } ); - } ); } ); From 8681e0aaef17f6a5e959a0c3a920c2e9b5b4ba5a Mon Sep 17 00:00:00 2001 From: Kamil Piechaczek Date: Tue, 18 Feb 2020 16:15:35 +0100 Subject: [PATCH 15/34] Styles Processor must be unique across the entire editor instance. --- src/controller/datacontroller.js | 13 +++++++++++-- src/controller/editingcontroller.js | 5 +++-- src/dataprocessor/htmldataprocessor.js | 14 ++++++++++++-- src/view/document.js | 7 ++++--- src/view/view.js | 7 +++++-- 5 files changed, 35 insertions(+), 11 deletions(-) diff --git a/src/controller/datacontroller.js b/src/controller/datacontroller.js index 0e0a36a81..cfd3499bb 100644 --- a/src/controller/datacontroller.js +++ b/src/controller/datacontroller.js @@ -47,10 +47,11 @@ export default class DataController { * Creates a data controller instance. * * @param {module:engine/model/model~Model} model Data model. + * @param {module:engine/view/stylesmap~StylesProcessor} stylesProcessor Styles processor. * @param {module:engine/dataprocessor/dataprocessor~DataProcessor} [dataProcessor] Data processor that should be used * by the controller. */ - constructor( model, dataProcessor ) { + constructor( model, stylesProcessor, dataProcessor ) { /** * Data model. * @@ -59,6 +60,14 @@ export default class DataController { */ this.model = model; + /** + * Styles processor. + * + * @readonly + * @member {module:engine/view/stylesmap~StylesProcessor} + */ + this.stylesProcessor = stylesProcessor; + /** * Data processor used during the conversion. * @@ -187,7 +196,7 @@ export default class DataController { // First, convert elements. const modelRange = ModelRange._createIn( modelElementOrFragment ); - const viewDocument = new ViewDocument(); + const viewDocument = new ViewDocument( this.stylesProcessor ); const viewDocumentFragment = new ViewDocumentFragment( viewDocument ); diff --git a/src/controller/editingcontroller.js b/src/controller/editingcontroller.js index 819a2cebc..a8a4c673e 100644 --- a/src/controller/editingcontroller.js +++ b/src/controller/editingcontroller.js @@ -31,8 +31,9 @@ export default class EditingController { * Creates an editing controller instance. * * @param {module:engine/model/model~Model} model Editing model. + * @param {module:engine/view/stylesmap~StylesProcessor} stylesProcessor Styles processor. */ - constructor( model ) { + constructor( model, stylesProcessor ) { /** * Editor model. * @@ -47,7 +48,7 @@ export default class EditingController { * @readonly * @member {module:engine/view/view~View} */ - this.view = new View(); + this.view = new View( stylesProcessor ); /** * Mapper which describes the model-view binding. diff --git a/src/dataprocessor/htmldataprocessor.js b/src/dataprocessor/htmldataprocessor.js index f9d82bb62..cc6c4069b 100644 --- a/src/dataprocessor/htmldataprocessor.js +++ b/src/dataprocessor/htmldataprocessor.js @@ -22,8 +22,18 @@ import ViewDocument from '../view/document'; export default class HtmlDataProcessor { /** * Creates a new instance of the HTML data processor class. + * + * @param {module:engine/view/stylesmap~StylesProcessor} stylesProcessor Styles processor. */ - constructor() { + constructor( stylesProcessor ) { + /** + * Styles processor. + * + * @readonly + * @member {module:engine/view/stylesmap~StylesProcessor} + */ + this.stylesProcessor = stylesProcessor; + /** * A DOM parser instance used to parse an HTML string to an HTML document. * @@ -73,7 +83,7 @@ export default class HtmlDataProcessor { toView( data ) { // Convert input HTML data to DOM DocumentFragment. const domFragment = this._toDom( data ); - const viewDocument = new ViewDocument(); + const viewDocument = new ViewDocument( this.stylesProcessor ); // Convert DOM DocumentFragment to view DocumentFragment. return this._domConverter.domToView( viewDocument, domFragment ); diff --git a/src/view/document.js b/src/view/document.js index 595e25693..43159a6ec 100644 --- a/src/view/document.js +++ b/src/view/document.js @@ -11,7 +11,6 @@ import DocumentSelection from './documentselection'; import Collection from '@ckeditor/ckeditor5-utils/src/collection'; import mix from '@ckeditor/ckeditor5-utils/src/mix'; import ObservableMixin from '@ckeditor/ckeditor5-utils/src/observablemixin'; -import { StylesProcessor } from './stylesmap'; // @if CK_DEBUG_ENGINE // const { logDocument } = require( '../dev-utils/utils' ); @@ -24,8 +23,10 @@ import { StylesProcessor } from './stylesmap'; export default class Document { /** * Creates a Document instance. + * + * @param {module:engine/view/stylesmap~StylesProcessor} stylesProcessor Styles processor. */ - constructor() { + constructor( stylesProcessor ) { /** * Selection done on this document. * @@ -53,7 +54,7 @@ export default class Document { * @readonly * @member {module:engine/view/stylesmap~StylesProcessor} */ - this.stylesProcessor = new StylesProcessor(); + this.stylesProcessor = stylesProcessor; /** * Defines whether document is in read-only mode. diff --git a/src/view/view.js b/src/view/view.js index 800e4c7a5..4d4f004b3 100644 --- a/src/view/view.js +++ b/src/view/view.js @@ -62,14 +62,17 @@ import env from '@ckeditor/ckeditor5-utils/src/env'; * @mixes module:utils/observablemixin~ObservableMixin */ export default class View { - constructor() { + /** + * @param {module:engine/view/stylesmap~StylesProcessor} stylesProcessor Styles processor. + */ + constructor( stylesProcessor ) { /** * Instance of the {@link module:engine/view/document~Document} associated with this view controller. * * @readonly * @type {module:engine/view/document~Document} */ - this.document = new Document(); + this.document = new Document( stylesProcessor ); /** * Instance of the {@link module:engine/view/domconverter~DomConverter domConverter} used by From a23ad5d3115514c6c043fa4209118545eefeea9e Mon Sep 17 00:00:00 2001 From: Kamil Piechaczek Date: Wed, 19 Feb 2020 14:04:38 +0100 Subject: [PATCH 16/34] Updated tests to new APIs. --- src/dataprocessor/xmldataprocessor.js | 13 ++++- src/dev-utils/model.js | 4 +- src/dev-utils/view.js | 16 ++++++- tests/controller/datacontroller.js | 14 ++++-- tests/controller/editingcontroller.js | 15 ++++-- tests/conversion/conversion.js | 11 ++++- tests/conversion/downcasthelpers.js | 29 +++++++++--- tests/conversion/mapper.js | 8 ++-- tests/conversion/upcastdispatcher.js | 8 +++- tests/conversion/upcasthelpers.js | 17 ++++++- tests/conversion/viewconsumable.js | 12 +++-- tests/dataprocessor/htmldataprocessor.js | 15 ++++-- tests/dataprocessor/xmldataprocessor.js | 17 +++++-- tests/dev-utils/view.js | 19 +++++--- tests/tickets/1323.js | 9 +++- tests/view/attributeelement.js | 28 +++++++---- tests/view/containerelement.js | 9 +++- tests/view/document.js | 9 +++- tests/view/documentfragment.js | 9 +++- tests/view/documentselection.js | 10 +++- tests/view/domconverter/binding.js | 11 +++-- tests/view/domconverter/dom-to-view.js | 7 +-- tests/view/domconverter/domconverter.js | 12 +++-- tests/view/domconverter/uielement.js | 9 +++- tests/view/domconverter/view-to-dom.js | 6 ++- tests/view/downcastwriter/breakattributes.js | 9 +++- tests/view/downcastwriter/breakcontainer.js | 9 +++- tests/view/downcastwriter/clear.js | 9 +++- tests/view/downcastwriter/insert.js | 9 +++- tests/view/downcastwriter/mergeattributes.js | 9 +++- tests/view/downcastwriter/mergecontainers.js | 9 +++- tests/view/downcastwriter/move.js | 9 +++- tests/view/downcastwriter/remove.js | 9 +++- tests/view/downcastwriter/rename.js | 9 +++- tests/view/downcastwriter/unwrap.js | 9 +++- tests/view/downcastwriter/wrap.js | 9 +++- tests/view/downcastwriter/writer.js | 8 +++- tests/view/editableelement.js | 9 +++- tests/view/element.js | 11 +++-- tests/view/emptyelement.js | 8 +++- tests/view/matcher.js | 9 +++- tests/view/node.js | 7 ++- tests/view/observer/mutationobserver.js | 50 +++++++++++++------- tests/view/position.js | 10 ++-- tests/view/range.js | 9 +++- tests/view/renderer.js | 20 +++++--- tests/view/selection.js | 8 +++- tests/view/text.js | 9 +++- tests/view/textproxy.js | 8 +++- tests/view/treewalker.js | 5 +- tests/view/uielement.js | 9 +++- tests/view/upcastwriter.js | 8 ++-- tests/view/utils-tests/createroot.js | 9 +++- tests/view/view/view.js | 9 +++- 54 files changed, 477 insertions(+), 145 deletions(-) diff --git a/src/dataprocessor/xmldataprocessor.js b/src/dataprocessor/xmldataprocessor.js index 5d66c01ca..96f64d88a 100644 --- a/src/dataprocessor/xmldataprocessor.js +++ b/src/dataprocessor/xmldataprocessor.js @@ -25,10 +25,19 @@ export default class XmlDataProcessor { /** * Creates a new instance of the XML data processor class. * + * @param {module:engine/view/stylesmap~StylesProcessor} stylesProcessor Styles processor. * @param {Object} options Configuration options. * @param {Array} [options.namespaces=[]] A list of namespaces allowed to use in the XML input. */ - constructor( options = {} ) { + constructor( stylesProcessor, options = {} ) { + /** + * Styles processor. + * + * @readonly + * @member {module:engine/view/stylesmap~StylesProcessor} + */ + this.stylesProcessor = stylesProcessor; + /** * A list of namespaces allowed to use in the XML input. * @@ -91,7 +100,7 @@ export default class XmlDataProcessor { toView( data ) { // Convert input XML data to DOM DocumentFragment. const domFragment = this._toDom( data ); - const viewDocument = new ViewDocument(); + const viewDocument = new ViewDocument( this.stylesProcessor ); // Convert DOM DocumentFragment to view DocumentFragment. return this._domConverter.domToView( viewDocument, domFragment, { keepOriginalCase: true } ); diff --git a/src/dev-utils/model.js b/src/dev-utils/model.js index 1d47d267d..2c3d2c9a2 100644 --- a/src/dev-utils/model.js +++ b/src/dev-utils/model.js @@ -39,6 +39,7 @@ import { import { isPlainObject } from 'lodash-es'; import toMap from '@ckeditor/ckeditor5-utils/src/tomap'; +import { StylesProcessor } from '../view/stylesmap'; /** * Writes the content of a model {@link module:engine/model/document~Document document} to an HTML-like string. @@ -210,7 +211,8 @@ export function stringify( node, selectionOrPositionOrRange = null, markers = nu // Set up conversion. // Create a temporary view controller. - const view = new View(); + const stylesProcessor = new StylesProcessor(); + const view = new View( stylesProcessor ); const viewDocument = view.document; const viewRoot = new ViewRootEditableElement( viewDocument, 'div' ); diff --git a/src/dev-utils/view.js b/src/dev-utils/view.js index a6c6735f1..30307ae55 100644 --- a/src/dev-utils/view.js +++ b/src/dev-utils/view.js @@ -24,6 +24,7 @@ import AttributeElement from '../view/attributeelement'; import ContainerElement from '../view/containerelement'; import EmptyElement from '../view/emptyelement'; import UIElement from '../view/uielement'; +import { StylesProcessor } from '../view/stylesmap'; const ELEMENT_RANGE_START_TOKEN = '['; const ELEMENT_RANGE_END_TOKEN = ']'; @@ -98,7 +99,10 @@ export function setData( view, data, options = {} ) { const root = document.getRoot( rootName ); view.change( writer => { - const result = setData._parse( data, { rootElement: root } ); + const result = setData._parse( data, { + rootElement: root, + stylesProcessor: document.stylesProcessor + } ); if ( result.view && result.selection ) { writer.setSelection( result.selection ); @@ -321,16 +325,24 @@ export function stringify( node, selectionOrPositionOrRange = null, options = {} * this node will be used as the root for all parsed nodes. * @param {Boolean} [options.sameSelectionCharacters=false] When set to `false`, the selection inside the text should be marked using * `{` and `}` and the selection outside the ext using `[` and `]`. When set to `true`, both should be marked with `[` and `]` only. + * @param {module:engine/view/stylesmap~StylesProcessor} [options.stylesProcessor] Styles processor. * @returns {module:engine/view/text~Text|module:engine/view/element~Element|module:engine/view/documentfragment~DocumentFragment|Object} * Returns the parsed view node or an object with two fields: `view` and `selection` when selection ranges were included in the data * to parse. */ export function parse( data, options = {} ) { + if ( !options.stylesProcessor ) { + // console.log( 'Missing "stylesProcessor". parse()' ); + options.stylesProcessor = new StylesProcessor(); + } + + const stylesProcessor = options.stylesProcessor; + options.order = options.order || []; const rangeParser = new RangeParser( { sameSelectionCharacters: options.sameSelectionCharacters } ); - const processor = new XmlDataProcessor( { + const processor = new XmlDataProcessor( stylesProcessor, { namespaces: Object.keys( allowedTypes ) } ); diff --git a/tests/controller/datacontroller.js b/tests/controller/datacontroller.js index 9670cc0fd..a93fc16b8 100644 --- a/tests/controller/datacontroller.js +++ b/tests/controller/datacontroller.js @@ -21,9 +21,15 @@ import count from '@ckeditor/ckeditor5-utils/src/count'; import UpcastHelpers from '../../src/conversion/upcasthelpers'; import DowncastHelpers from '../../src/conversion/downcasthelpers'; import { expectToThrowCKEditorError } from '@ckeditor/ckeditor5-utils/tests/_utils/utils'; +import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'DataController', () => { let model, modelDocument, htmlDataProcessor, data, schema, upcastHelpers, downcastHelpers, viewDocument; + let stylesProcessor; + + before( () => { + stylesProcessor = new StylesProcessor(); + } ); beforeEach( () => { model = new Model(); @@ -36,10 +42,10 @@ describe( 'DataController', () => { schema.register( '$title', { inheritAllFrom: '$root' } ); - htmlDataProcessor = new HtmlDataProcessor(); - viewDocument = new ViewDocument(); + htmlDataProcessor = new HtmlDataProcessor( stylesProcessor ); + viewDocument = new ViewDocument( stylesProcessor ); - data = new DataController( model, htmlDataProcessor ); + data = new DataController( model, stylesProcessor, htmlDataProcessor ); upcastHelpers = new UpcastHelpers( [ data.upcastDispatcher ] ); downcastHelpers = new DowncastHelpers( [ data.downcastDispatcher ] ); @@ -47,7 +53,7 @@ describe( 'DataController', () => { describe( 'constructor()', () => { it( 'works without data processor', () => { - const data = new DataController( model ); + const data = new DataController( model, stylesProcessor ); expect( data.processor ).to.be.undefined; } ); diff --git a/tests/controller/editingcontroller.js b/tests/controller/editingcontroller.js index b4c7bb638..2c562f754 100644 --- a/tests/controller/editingcontroller.js +++ b/tests/controller/editingcontroller.js @@ -22,14 +22,21 @@ import ModelDocumentFragment from '../../src/model/documentfragment'; import { getData as getModelData, parse } from '../../src/dev-utils/model'; import { getData as getViewData } from '../../src/dev-utils/view'; +import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'EditingController', () => { + let stylesProcessor; + + before( () => { + stylesProcessor = new StylesProcessor(); + } ); + describe( 'constructor()', () => { let model, editing; beforeEach( () => { model = new Model(); - editing = new EditingController( model ); + editing = new EditingController( model, stylesProcessor ); } ); afterEach( () => { @@ -77,7 +84,7 @@ describe( 'EditingController', () => { model = new Model(); modelRoot = model.document.createRoot(); - editing = new EditingController( model ); + editing = new EditingController( model, stylesProcessor ); domRoot = document.createElement( 'div' ); domRoot.contentEditable = true; @@ -477,7 +484,7 @@ describe( 'EditingController', () => { model.document.createRoot(); model.schema.register( 'paragraph', { inheritAllFrom: '$block' } ); - const editing = new EditingController( model ); + const editing = new EditingController( model, stylesProcessor ); const spy = sinon.spy(); @@ -501,7 +508,7 @@ describe( 'EditingController', () => { model.document.createRoot(); model.schema.register( 'paragraph', { inheritAllFrom: '$block' } ); - const editing = new EditingController( model ); + const editing = new EditingController( model, stylesProcessor ); const spy = sinon.spy( editing.view, 'destroy' ); diff --git a/tests/conversion/conversion.js b/tests/conversion/conversion.js index e722c237e..78e1dd039 100644 --- a/tests/conversion/conversion.js +++ b/tests/conversion/conversion.js @@ -18,10 +18,17 @@ import { parse as viewParse, stringify as viewStringify } from '../../src/dev-ut import { stringify as modelStringify } from '../../src/dev-utils/model'; import ConversionHelpers from '../../src/conversion/conversionhelpers'; import { expectToThrowCKEditorError } from '@ckeditor/ckeditor5-utils/tests/_utils/utils'; +import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'Conversion', () => { let conversion, downcastDispA, upcastDispaA, downcastDispB; + let stylesProcessor; + + before( () => { + stylesProcessor = new StylesProcessor(); + } ); + beforeEach( () => { // Placeholders. Will be used only to see if their were given as attribute for a spy function. downcastDispA = Symbol( 'downA' ); @@ -121,7 +128,7 @@ describe( 'Conversion', () => { beforeEach( () => { model = new Model(); - const controller = new EditingController( model ); + const controller = new EditingController( model, stylesProcessor ); const modelDoc = model.document; modelRoot = modelDoc.createRoot(); @@ -719,7 +726,7 @@ describe( 'Conversion', () => { } function loadData( input ) { - const parsedView = viewParse( input ); + const parsedView = viewParse( input, { stylesProcessor } ); let convertedModel; model.change( writer => { diff --git a/tests/conversion/downcasthelpers.js b/tests/conversion/downcasthelpers.js index 898c1a46d..042f69936 100644 --- a/tests/conversion/downcasthelpers.js +++ b/tests/conversion/downcasthelpers.js @@ -35,18 +35,22 @@ import View from '../../src/view/view'; import createViewRoot from '../view/_utils/createroot'; import { setData as setModelData } from '../../src/dev-utils/model'; import { expectToThrowCKEditorError } from '@ckeditor/ckeditor5-utils/tests/_utils/utils'; +import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'DowncastHelpers', () => { let model, modelRoot, viewRoot, downcastHelpers, controller; + let modelRootStart, stylesProcessor; - let modelRootStart; + before( () => { + stylesProcessor = new StylesProcessor(); + } ); beforeEach( () => { model = new Model(); const modelDoc = model.document; modelRoot = modelDoc.createRoot(); - controller = new EditingController( model ); + controller = new EditingController( model, stylesProcessor ); // Set name of view root the same as dom root. // This is a mock of attaching view root to dom root. @@ -1323,7 +1327,7 @@ describe( 'DowncastHelpers', () => { let markerRange, viewDocument; beforeEach( () => { - viewDocument = new ViewDocument(); + viewDocument = new ViewDocument( stylesProcessor ); downcastHelpers.elementToElement( { model: 'div', @@ -1451,12 +1455,18 @@ describe( 'DowncastHelpers', () => { describe( 'downcast converters', () => { let dispatcher, modelDoc, modelRoot, viewRoot, controller, modelRootStart, model; + let stylesProcessor; + + before( () => { + stylesProcessor = new StylesProcessor(); + } ); + beforeEach( () => { model = new Model(); modelDoc = model.document; modelRoot = modelDoc.createRoot(); - controller = new EditingController( model ); + controller = new EditingController( model, stylesProcessor ); viewRoot = controller.view.document.getRoot(); // Set name of view root the same as dom root. @@ -1505,7 +1515,7 @@ describe( 'downcast converters', () => { let viewDocument; beforeEach( () => { - viewDocument = new ViewDocument(); + viewDocument = new ViewDocument( stylesProcessor ); } ); it( 'should remove items from view accordingly to changes in model #1', () => { @@ -1697,7 +1707,7 @@ describe( 'downcast converters', () => { let viewDocument; beforeEach( () => { - viewDocument = new ViewDocument(); + viewDocument = new ViewDocument( stylesProcessor ); } ); it( 'should return attribute element from descriptor object', () => { @@ -1787,6 +1797,11 @@ describe( 'downcast converters', () => { describe( 'downcast selection converters', () => { let dispatcher, mapper, model, view, modelDoc, modelRoot, docSelection, viewDoc, viewRoot, viewSelection, downcastHelpers; + let stylesProcessor; + + before( () => { + stylesProcessor = new StylesProcessor(); + } ); beforeEach( () => { model = new Model(); @@ -1926,7 +1941,7 @@ describe( 'downcast selection converters', () => { let marker, viewDocument; beforeEach( () => { - viewDocument = new ViewDocument(); + viewDocument = new ViewDocument( stylesProcessor ); } ); it( 'in container', () => { diff --git a/tests/conversion/mapper.js b/tests/conversion/mapper.js index 70c7ca7c7..8acb2dd37 100644 --- a/tests/conversion/mapper.js +++ b/tests/conversion/mapper.js @@ -17,12 +17,14 @@ import ViewUIElement from '../../src/view/uielement'; import ViewText from '../../src/view/text'; import ViewPosition from '../../src/view/position'; import ViewRange from '../../src/view/range'; +import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'Mapper', () => { - let viewDocument; + let viewDocument, stylesProcessor; - beforeEach( () => { - viewDocument = new ViewDocument(); + before( () => { + stylesProcessor = new StylesProcessor(); + viewDocument = new ViewDocument( stylesProcessor ); } ); describe( 'clearBindings', () => { diff --git a/tests/conversion/upcastdispatcher.js b/tests/conversion/upcastdispatcher.js index b4a0856b6..5c7b6a4e3 100644 --- a/tests/conversion/upcastdispatcher.js +++ b/tests/conversion/upcastdispatcher.js @@ -21,13 +21,19 @@ import ModelWriter from '../../src/model/writer'; import first from '@ckeditor/ckeditor5-utils/src/first'; import { expectToThrowCKEditorError } from '@ckeditor/ckeditor5-utils/tests/_utils/utils'; +import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'UpcastDispatcher', () => { let model, viewDocument; + let stylesProcessor; + + before( () => { + stylesProcessor = new StylesProcessor(); + } ); beforeEach( () => { model = new Model(); - viewDocument = new ViewDocument(); + viewDocument = new ViewDocument( stylesProcessor ); } ); describe( 'constructor()', () => { diff --git a/tests/conversion/upcasthelpers.js b/tests/conversion/upcasthelpers.js index c5784080c..852050495 100644 --- a/tests/conversion/upcasthelpers.js +++ b/tests/conversion/upcasthelpers.js @@ -28,13 +28,20 @@ import { setData as viewSetData } from '../../src/dev-utils/view'; import Mapper from '../../src/conversion/mapper'; import ViewSelection from '../../src/view/selection'; import ViewRange from '../../src/view/range'; +import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'UpcastHelpers', () => { let upcastDispatcher, model, schema, upcastHelpers, viewDocument; + let stylesProcessor; + + before( () => { + stylesProcessor = new StylesProcessor(); + } ); + beforeEach( () => { model = new Model(); - viewDocument = new ViewDocument(); + viewDocument = new ViewDocument( stylesProcessor ); schema = model.schema; @@ -700,9 +707,15 @@ describe( 'UpcastHelpers', () => { describe( 'upcast-converters', () => { let dispatcher, schema, context, model, viewDocument; + let stylesProcessor; + + before( () => { + stylesProcessor = new StylesProcessor(); + } ); + beforeEach( () => { model = new Model(); - viewDocument = new ViewDocument(); + viewDocument = new ViewDocument( stylesProcessor ); schema = model.schema; schema.register( 'paragraph', { inheritAllFrom: '$block' } ); diff --git a/tests/conversion/viewconsumable.js b/tests/conversion/viewconsumable.js index 8abd8faf1..2354308e3 100644 --- a/tests/conversion/viewconsumable.js +++ b/tests/conversion/viewconsumable.js @@ -11,16 +11,18 @@ import ViewConsumable from '../../src/conversion/viewconsumable'; import { addBorderRules } from '../../src/view/styles/border'; import { addMarginRules } from '../../src/view/styles/margin'; import { addPaddingRules } from '../../src/view/styles/padding'; +import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'ViewConsumable', () => { - let viewConsumable, el, viewDocument; + let viewConsumable, el, viewDocument, stylesProcessor; before( () => { - viewDocument = new ViewDocument(); + stylesProcessor = new StylesProcessor(); + viewDocument = new ViewDocument( stylesProcessor ); - addBorderRules( viewDocument.stylesProcessor ); - addMarginRules( viewDocument.stylesProcessor ); - addPaddingRules( viewDocument.stylesProcessor ); + addBorderRules( stylesProcessor ); + addMarginRules( stylesProcessor ); + addPaddingRules( stylesProcessor ); } ); beforeEach( () => { diff --git a/tests/dataprocessor/htmldataprocessor.js b/tests/dataprocessor/htmldataprocessor.js index acb0f8c3c..1684742fc 100644 --- a/tests/dataprocessor/htmldataprocessor.js +++ b/tests/dataprocessor/htmldataprocessor.js @@ -9,9 +9,18 @@ import HtmlDataProcessor from '../../src/dataprocessor/htmldataprocessor'; import xssTemplates from '../../tests/dataprocessor/_utils/xsstemplates'; import ViewDocumentFragment from '../../src/view/documentfragment'; import { stringify, parse } from '../../src/dev-utils/view'; +import { StylesProcessor } from '../../src/view/stylesmap'; +import ViewDocument from '../../src/view/document'; describe( 'HtmlDataProcessor', () => { - const dataProcessor = new HtmlDataProcessor(); + const stylesProcessor = new StylesProcessor(); + const dataProcessor = new HtmlDataProcessor( stylesProcessor ); + + let viewDocument; + + beforeEach( () => { + viewDocument = new ViewDocument( stylesProcessor ); + } ); describe( 'toView()', () => { it( 'should return empty DocumentFragment when empty string is passed', () => { @@ -89,13 +98,13 @@ describe( 'HtmlDataProcessor', () => { describe( 'toData()', () => { it( 'should return empty string when empty DocumentFragment is passed', () => { - const fragment = new ViewDocumentFragment(); + const fragment = new ViewDocumentFragment( viewDocument ); expect( dataProcessor.toData( fragment ) ).to.equal( '' ); } ); it( 'should return text if document fragment with single text node is passed', () => { - const fragment = new ViewDocumentFragment(); + const fragment = new ViewDocumentFragment( viewDocument ); fragment._appendChild( parse( 'foo bar' ) ); expect( dataProcessor.toData( fragment ) ).to.equal( 'foo bar' ); diff --git a/tests/dataprocessor/xmldataprocessor.js b/tests/dataprocessor/xmldataprocessor.js index efa678ee7..bd5bf4c7f 100644 --- a/tests/dataprocessor/xmldataprocessor.js +++ b/tests/dataprocessor/xmldataprocessor.js @@ -8,13 +8,20 @@ import XmlDataProcessor from '../../src/dataprocessor/xmldataprocessor'; import xssTemplates from '../../tests/dataprocessor/_utils/xsstemplates'; import ViewDocumentFragment from '../../src/view/documentfragment'; +import ViewDocument from '../../src/view/document'; import { stringify, parse } from '../../src/dev-utils/view'; +import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'XmlDataProcessor', () => { - let dataProcessor; + let stylesProcessor, dataProcessor, viewDocument; + + before( () => { + stylesProcessor = new StylesProcessor(); + } ); beforeEach( () => { - dataProcessor = new XmlDataProcessor(); + dataProcessor = new XmlDataProcessor( stylesProcessor ); + viewDocument = new ViewDocument( stylesProcessor ); } ); describe( 'toView', () => { @@ -43,7 +50,7 @@ describe( 'XmlDataProcessor', () => { } ); it( 'should allow to use registered namespaces', () => { - dataProcessor = new XmlDataProcessor( { + dataProcessor = new XmlDataProcessor( stylesProcessor, { namespaces: [ 'foo', 'bar' ] } ); @@ -82,13 +89,13 @@ describe( 'XmlDataProcessor', () => { describe( 'toData', () => { it( 'should return empty string when empty DocumentFragment is passed', () => { - const fragment = new ViewDocumentFragment(); + const fragment = new ViewDocumentFragment( viewDocument ); expect( dataProcessor.toData( fragment ) ).to.equal( '' ); } ); it( 'should return text if document fragment with single text node is passed', () => { - const fragment = new ViewDocumentFragment(); + const fragment = new ViewDocumentFragment( viewDocument ); fragment._appendChild( parse( 'foo bar' ) ); expect( dataProcessor.toData( fragment ) ).to.equal( 'foo bar' ); diff --git a/tests/dev-utils/view.js b/tests/dev-utils/view.js index 0086de817..e07884aec 100644 --- a/tests/dev-utils/view.js +++ b/tests/dev-utils/view.js @@ -20,8 +20,15 @@ import Range from '../../src/view/range'; import View from '../../src/view/view'; import XmlDataProcessor from '../../src/dataprocessor/xmldataprocessor'; import createViewRoot from '../view/_utils/createroot'; +import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'view test utils', () => { + let stylesProcessor; + + before( () => { + stylesProcessor = new StylesProcessor(); + } ); + describe( 'getData, setData', () => { afterEach( () => { sinon.restore(); @@ -31,7 +38,7 @@ describe( 'view test utils', () => { it( 'should use stringify method', () => { const element = document.createElement( 'div' ); const stringifySpy = sinon.spy( getData, '_stringify' ); - const view = new View(); + const view = new View( stylesProcessor ); const viewDocument = view.document; const options = { showType: false, @@ -58,7 +65,7 @@ describe( 'view test utils', () => { it( 'should use stringify method with selection', () => { const element = document.createElement( 'div' ); const stringifySpy = sinon.spy( getData, '_stringify' ); - const view = new View(); + const view = new View( stylesProcessor ); const viewDocument = view.document; const options = { showType: false, showPriority: false }; const root = createAttachedRoot( viewDocument, element ); @@ -89,7 +96,7 @@ describe( 'view test utils', () => { describe( 'setData', () => { it( 'should use parse method', () => { - const view = new View(); + const view = new View( stylesProcessor ); const viewDocument = view.document; const data = 'foobarbaz'; const parseSpy = sinon.spy( setData, '_parse' ); @@ -108,7 +115,7 @@ describe( 'view test utils', () => { } ); it( 'should use parse method with selection', () => { - const view = new View(); + const view = new View( stylesProcessor ); const viewDocument = view.document; const data = '[baz]'; const parseSpy = sinon.spy( setData, '_parse' ); @@ -137,7 +144,7 @@ describe( 'view test utils', () => { let viewDocument; beforeEach( () => { - viewDocument = new ViewDocument(); + viewDocument = new ViewDocument( stylesProcessor ); } ); it( 'should write text', () => { @@ -426,7 +433,7 @@ describe( 'view test utils', () => { let viewDocument; beforeEach( () => { - viewDocument = new ViewDocument(); + viewDocument = new ViewDocument( stylesProcessor ); } ); it( 'should return empty DocumentFragment for empty string', () => { diff --git a/tests/tickets/1323.js b/tests/tickets/1323.js index 36f3c5826..f8a91865e 100644 --- a/tests/tickets/1323.js +++ b/tests/tickets/1323.js @@ -9,14 +9,21 @@ import Model from '../../src/model/model'; import ModelText from '../../src/model/text'; import MarkerOperation from '../../src/model/operation/markeroperation'; +import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'Bug ckeditor5-engine@1323', () => { + let stylesProcessor; + + before( () => { + stylesProcessor = new StylesProcessor(); + } ); + describe( 'constructor()', () => { let model, editing, root, range; beforeEach( () => { model = new Model(); - editing = new EditingController( model ); + editing = new EditingController( model, stylesProcessor ); root = model.document.createRoot(); root._appendChild( new ModelText( 'foo' ) ); range = model.createRange( model.createPositionAt( root, 0 ), model.createPositionAt( root, 0 ) ); diff --git a/tests/view/attributeelement.js b/tests/view/attributeelement.js index 472f7e25a..a3241fef3 100644 --- a/tests/view/attributeelement.js +++ b/tests/view/attributeelement.js @@ -8,12 +8,18 @@ import Element from '../../src/view/element'; import Document from '../../src/view/document'; import { parse } from '../../src/dev-utils/view'; import { expectToThrowCKEditorError } from '@ckeditor/ckeditor5-utils/tests/_utils/utils'; +import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'AttributeElement', () => { let document; + let stylesProcessor; + + before( () => { + stylesProcessor = new StylesProcessor(); + } ); beforeEach( () => { - document = new Document(); + document = new Document( stylesProcessor ); } ); describe( 'constructor()', () => { @@ -151,7 +157,7 @@ describe( 'AttributeElement', () => { describe( 'getFillerOffset', () => { it( 'should return position 0 if it is the only element in the container', () => { - const { selection } = parse( '[]' ); + const { selection } = parse( '[]', { stylesProcessor } ); const attribute = selection.getFirstPosition().parent; expect( attribute.getFillerOffset() ).to.equals( 0 ); @@ -159,26 +165,26 @@ describe( 'AttributeElement', () => { it( 'should return position 0 if it is the only nested element in the container', () => { const { selection } = parse( - '[]' ); + '[]', { stylesProcessor } ); const attribute = selection.getFirstPosition().parent; expect( attribute.getFillerOffset() ).to.equals( 0 ); } ); it( 'should return null if element contains another element', () => { - const attribute = parse( '' ); + const attribute = parse( '', { stylesProcessor } ); expect( attribute.getFillerOffset() ).to.be.null; } ); it( 'should return null if element contains text', () => { - const attribute = parse( 'text' ); + const attribute = parse( 'text', { stylesProcessor } ); expect( attribute.getFillerOffset() ).to.be.null; } ); it( 'should return null if container element contains text', () => { - const { selection } = parse( '[]foo' ); + const { selection } = parse( '[]foo', { stylesProcessor } ); const attribute = selection.getFirstPosition().parent; expect( attribute.getFillerOffset() ).to.be.null; @@ -186,14 +192,14 @@ describe( 'AttributeElement', () => { it( 'should return null if it is the parent contains text', () => { const { selection } = parse( - '[]foo' ); + '[]foo', { stylesProcessor } ); const attribute = selection.getFirstPosition().parent; expect( attribute.getFillerOffset() ).to.be.null; } ); it( 'should return null if there is no parent container element', () => { - const { selection } = parse( '[]foo' ); + const { selection } = parse( '[]foo', { stylesProcessor } ); const attribute = selection.getFirstPosition().parent; expect( attribute.getFillerOffset() ).to.be.null; @@ -207,14 +213,16 @@ describe( 'AttributeElement', () => { it( 'should return offset after all children if it is the only nested element in the container and has UIElement inside', () => { const { selection } = parse( - '[]' ); + '[]', + { stylesProcessor } + ); const attribute = selection.getFirstPosition().parent; expect( attribute.getFillerOffset() ).to.equal( 1 ); } ); it( 'should return offset after all children if there is no parent container element and has UIElement inside', () => { - const { selection } = parse( '[]' ); + const { selection } = parse( '[]', { stylesProcessor } ); const attribute = selection.getFirstPosition().parent; expect( attribute.getFillerOffset() ).to.equal( 2 ); diff --git a/tests/view/containerelement.js b/tests/view/containerelement.js index e088158b3..a56dad111 100644 --- a/tests/view/containerelement.js +++ b/tests/view/containerelement.js @@ -7,12 +7,17 @@ import { default as ContainerElement, getFillerOffset } from '../../src/view/con import Element from '../../src/view/element'; import Document from '../../src/view/document'; import { parse } from '../../src/dev-utils/view'; +import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'ContainerElement', () => { - let document; + let document, stylesProcessor; + + before( () => { + stylesProcessor = new StylesProcessor(); + } ); beforeEach( () => { - document = new Document(); + document = new Document( stylesProcessor ); } ); describe( 'constructor()', () => { diff --git a/tests/view/document.js b/tests/view/document.js index 8bf2e919f..de432ae6b 100644 --- a/tests/view/document.js +++ b/tests/view/document.js @@ -10,9 +10,14 @@ import Document from '../../src/view/document'; import testUtils from '@ckeditor/ckeditor5-core/tests/_utils/utils'; import count from '@ckeditor/ckeditor5-utils/src/count'; import createViewRoot from './_utils/createroot'; +import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'Document', () => { - let domRoot, viewDocument; + let domRoot, viewDocument, stylesProcessor; + + before( () => { + stylesProcessor = new StylesProcessor(); + } ); testUtils.createSinonSandbox(); @@ -23,7 +28,7 @@ describe( 'Document', () => { } ); document.body.appendChild( domRoot ); - viewDocument = new Document(); + viewDocument = new Document( stylesProcessor ); } ); afterEach( () => { diff --git a/tests/view/documentfragment.js b/tests/view/documentfragment.js index d1a925d4e..484399122 100644 --- a/tests/view/documentfragment.js +++ b/tests/view/documentfragment.js @@ -9,12 +9,17 @@ import Node from '../../src/view/node'; import Text from '../../src/view/text'; import TextProxy from '../../src/view/textproxy'; import Document from '../../src/view/document'; +import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'DocumentFragment', () => { - let document; + let document, stylesProcessor; + + before( () => { + stylesProcessor = new StylesProcessor(); + } ); beforeEach( () => { - document = new Document(); + document = new Document( stylesProcessor ); } ); describe( 'constructor()', () => { diff --git a/tests/view/documentselection.js b/tests/view/documentselection.js index 4636f5bdf..ec9ea96dc 100644 --- a/tests/view/documentselection.js +++ b/tests/view/documentselection.js @@ -15,14 +15,20 @@ import createViewRoot from './_utils/createroot'; import { parse } from '../../src/dev-utils/view'; import testUtils from '@ckeditor/ckeditor5-core/tests/_utils/utils'; import { expectToThrowCKEditorError } from '@ckeditor/ckeditor5-utils/tests/_utils/utils'; +import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'DocumentSelection', () => { let documentSelection, el, range1, range2, range3, document; + let stylesProcessor; testUtils.createSinonSandbox(); + before( () => { + stylesProcessor = new StylesProcessor(); + } ); + beforeEach( () => { - document = new Document(); + document = new Document( stylesProcessor ); const text = new Text( document, 'xxxxxxxxxxxxxxxxxxxx' ); el = new Element( document, 'p', null, text ); @@ -1085,7 +1091,7 @@ describe( 'DocumentSelection', () => { } ); it( 'should return EditableElement when selection is placed inside', () => { - const viewDocument = new Document(); + const viewDocument = new Document( stylesProcessor ); documentSelection._setTo( viewDocument.selection ); const root = createViewRoot( viewDocument, 'div', 'main' ); const element = new Element( document, 'p' ); diff --git a/tests/view/domconverter/binding.js b/tests/view/domconverter/binding.js index 029344cd6..3e38f3e0f 100644 --- a/tests/view/domconverter/binding.js +++ b/tests/view/domconverter/binding.js @@ -15,13 +15,16 @@ import { INLINE_FILLER } from '../../../src/view/filler'; import { parse } from '../../../src/dev-utils/view'; import createElement from '@ckeditor/ckeditor5-utils/src/dom/createelement'; +import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'DomConverter', () => { - let converter, viewDocument; + let converter, viewDocument, stylesProcessor; before( () => { converter = new DomConverter(); - viewDocument = new ViewDocument(); + stylesProcessor = new StylesProcessor(); + + viewDocument = new ViewDocument( stylesProcessor ); } ); describe( 'bindElements()', () => { @@ -149,7 +152,7 @@ describe( 'DomConverter', () => { const domText = document.createTextNode( 'x' ); const domP = createElement( document, 'p', null, [ domB, domText, domI ] ); - const viewP = parse( '

' ); + const viewP = parse( '

', { stylesProcessor } ); const viewB = viewP.getChild( 0 ); const viewI = viewP.getChild( 1 ); @@ -164,7 +167,7 @@ describe( 'DomConverter', () => { const domText = document.createTextNode( 'x' ); const domP = createElement( document, 'p', null, domText ); - const viewP = parse( '

' ); + const viewP = parse( '

', { stylesProcessor } ); converter.bindElements( domP, viewP ); diff --git a/tests/view/domconverter/dom-to-view.js b/tests/view/domconverter/dom-to-view.js index 6f0ea61b5..c70c0b39c 100644 --- a/tests/view/domconverter/dom-to-view.js +++ b/tests/view/domconverter/dom-to-view.js @@ -11,18 +11,19 @@ import ViewDocumentSelection from '../../../src/view/documentselection'; import DomConverter from '../../../src/view/domconverter'; import ViewDocumentFragment from '../../../src/view/documentfragment'; import { BR_FILLER, INLINE_FILLER, INLINE_FILLER_LENGTH, NBSP_FILLER } from '../../../src/view/filler'; - +import { StylesProcessor } from '../../../src/view/stylesmap'; import { parse, stringify } from '../../../src/dev-utils/view'; import count from '@ckeditor/ckeditor5-utils/src/count'; import createElement from '@ckeditor/ckeditor5-utils/src/dom/createelement'; describe( 'DomConverter', () => { - let converter, viewDocument; + let converter, viewDocument, stylesProcessor; before( () => { converter = new DomConverter(); - viewDocument = new ViewDocument(); + stylesProcessor = new StylesProcessor(); + viewDocument = new ViewDocument( stylesProcessor ); } ); describe( 'domToView()', () => { diff --git a/tests/view/domconverter/domconverter.js b/tests/view/domconverter/domconverter.js index b9514654e..fd2c76255 100644 --- a/tests/view/domconverter/domconverter.js +++ b/tests/view/domconverter/domconverter.js @@ -13,12 +13,17 @@ import ViewContainerElement from '../../../src/view/containerelement'; import { BR_FILLER, INLINE_FILLER, INLINE_FILLER_LENGTH, NBSP_FILLER } from '../../../src/view/filler'; import testUtils from '@ckeditor/ckeditor5-core/tests/_utils/utils'; import global from '@ckeditor/ckeditor5-utils/src/dom/global'; +import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'DomConverter', () => { - let converter; + let converter, stylesProcessor; testUtils.createSinonSandbox(); + before( () => { + stylesProcessor = new StylesProcessor(); + } ); + beforeEach( () => { converter = new DomConverter(); } ); @@ -38,9 +43,8 @@ describe( 'DomConverter', () => { let viewEditable, domEditable, domEditableParent, viewDocument; beforeEach( () => { - viewDocument = new ViewDocument(); + viewDocument = new ViewDocument( stylesProcessor ); viewEditable = new ViewEditable( viewDocument, 'div' ); - viewEditable._document = viewDocument; domEditable = document.createElement( 'div' ); domEditableParent = document.createElement( 'div' ); @@ -203,7 +207,7 @@ describe( 'DomConverter', () => { domUiDeepSpan = document.createElement( 'span' ); domUiSpan.appendChild( domUiDeepSpan ); - viewDocument = new ViewDocument(); + viewDocument = new ViewDocument( stylesProcessor ); const viewUiSpan = new ViewUIElement( viewDocument, 'span' ); const viewElementSpan = new ViewContainerElement( viewDocument, 'span' ); diff --git a/tests/view/domconverter/uielement.js b/tests/view/domconverter/uielement.js index c3b7802ca..4dc0d4ded 100644 --- a/tests/view/domconverter/uielement.js +++ b/tests/view/domconverter/uielement.js @@ -9,9 +9,10 @@ import ViewUIElement from '../../../src/view/uielement'; import ViewContainer from '../../../src/view/containerelement'; import DomConverter from '../../../src/view/domconverter'; import ViewDocument from '../../../src/view/document'; +import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'DOMConverter UIElement integration', () => { - let converter, viewDocument; + let converter, viewDocument, stylesProcessor; function createUIElement( name ) { const element = new ViewUIElement( viewDocument, name ); @@ -26,9 +27,13 @@ describe( 'DOMConverter UIElement integration', () => { return element; } + before( () => { + stylesProcessor = new StylesProcessor(); + } ); + beforeEach( () => { converter = new DomConverter(); - viewDocument = new ViewDocument(); + viewDocument = new ViewDocument( stylesProcessor ); } ); describe( 'viewToDom()', () => { diff --git a/tests/view/domconverter/view-to-dom.js b/tests/view/domconverter/view-to-dom.js index a08c5525d..8cf9c447a 100644 --- a/tests/view/domconverter/view-to-dom.js +++ b/tests/view/domconverter/view-to-dom.js @@ -19,13 +19,15 @@ import { INLINE_FILLER, INLINE_FILLER_LENGTH } from '../../../src/view/filler'; import { parse } from '../../../src/dev-utils/view'; import createElement from '@ckeditor/ckeditor5-utils/src/dom/createelement'; +import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'DomConverter', () => { - let converter, viewDocument; + let converter, viewDocument, stylesProcessor; before( () => { + stylesProcessor = new StylesProcessor(); converter = new DomConverter(); - viewDocument = new ViewDocument(); + viewDocument = new ViewDocument( stylesProcessor ); } ); describe( 'viewToDom()', () => { diff --git a/tests/view/downcastwriter/breakattributes.js b/tests/view/downcastwriter/breakattributes.js index ef9bcaf04..224510a05 100644 --- a/tests/view/downcastwriter/breakattributes.js +++ b/tests/view/downcastwriter/breakattributes.js @@ -14,13 +14,20 @@ import Range from '../../../src/view/range'; import Position from '../../../src/view/position'; import { expectToThrowCKEditorError } from '@ckeditor/ckeditor5-utils/tests/_utils/utils'; +import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'DowncastWriter', () => { + let stylesProcessor; + + before( () => { + stylesProcessor = new StylesProcessor(); + } ); + describe( 'breakAttributes()', () => { let writer, document; beforeEach( () => { - document = new Document(); + document = new Document( stylesProcessor ); writer = new DowncastWriter( document ); } ); diff --git a/tests/view/downcastwriter/breakcontainer.js b/tests/view/downcastwriter/breakcontainer.js index 047192e9b..47b9149ec 100644 --- a/tests/view/downcastwriter/breakcontainer.js +++ b/tests/view/downcastwriter/breakcontainer.js @@ -10,8 +10,15 @@ import ContainerElement from '../../../src/view/containerelement'; import Position from '../../../src/view/position'; import Document from '../../../src/view/document'; import { expectToThrowCKEditorError } from '@ckeditor/ckeditor5-utils/tests/_utils/utils'; +import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'DowncastWriter', () => { + let stylesProcessor; + + before( () => { + stylesProcessor = new StylesProcessor(); + } ); + describe( 'breakContainer()', () => { let writer, document; @@ -28,7 +35,7 @@ describe( 'DowncastWriter', () => { } before( () => { - document = new Document(); + document = new Document( stylesProcessor ); writer = new DowncastWriter( document ); } ); diff --git a/tests/view/downcastwriter/clear.js b/tests/view/downcastwriter/clear.js index cd8583f81..91eb86ee2 100644 --- a/tests/view/downcastwriter/clear.js +++ b/tests/view/downcastwriter/clear.js @@ -13,8 +13,15 @@ import UIElement from '../../../src/view/uielement'; import Document from '../../../src/view/document'; import { expectToThrowCKEditorError } from '@ckeditor/ckeditor5-utils/tests/_utils/utils'; +import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'DowncastWriter', () => { + let stylesProcessor; + + before( () => { + stylesProcessor = new StylesProcessor(); + } ); + describe( 'clear()', () => { let writer, document; @@ -32,7 +39,7 @@ describe( 'DowncastWriter', () => { } beforeEach( () => { - document = new Document(); + document = new Document( stylesProcessor ); writer = new DowncastWriter( document ); } ); diff --git a/tests/view/downcastwriter/insert.js b/tests/view/downcastwriter/insert.js index 3e773d2be..eabe37b25 100644 --- a/tests/view/downcastwriter/insert.js +++ b/tests/view/downcastwriter/insert.js @@ -14,8 +14,15 @@ import { stringify, parse } from '../../../src/dev-utils/view'; import AttributeElement from '../../../src/view/attributeelement'; import Document from '../../../src/view/document'; import { expectToThrowCKEditorError } from '@ckeditor/ckeditor5-utils/tests/_utils/utils'; +import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'DowncastWriter', () => { + let stylesProcessor; + + before( () => { + stylesProcessor = new StylesProcessor(); + } ); + describe( 'insert()', () => { let writer, document; @@ -34,7 +41,7 @@ describe( 'DowncastWriter', () => { } beforeEach( () => { - document = new Document(); + document = new Document( stylesProcessor ); writer = new DowncastWriter( document ); } ); diff --git a/tests/view/downcastwriter/mergeattributes.js b/tests/view/downcastwriter/mergeattributes.js index cf7094690..5e9b49605 100644 --- a/tests/view/downcastwriter/mergeattributes.js +++ b/tests/view/downcastwriter/mergeattributes.js @@ -9,8 +9,15 @@ import Text from '../../../src/view/text'; import Position from '../../../src/view/position'; import { stringify, parse } from '../../../src/dev-utils/view'; import Document from '../../../src/view/document'; +import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'DowncastWriter', () => { + let stylesProcessor; + + before( () => { + stylesProcessor = new StylesProcessor(); + } ); + describe( 'mergeAttributes', () => { let writer, document; @@ -26,7 +33,7 @@ describe( 'DowncastWriter', () => { } before( () => { - document = new Document(); + document = new Document( stylesProcessor ); writer = new DowncastWriter( document ); } ); diff --git a/tests/view/downcastwriter/mergecontainers.js b/tests/view/downcastwriter/mergecontainers.js index 4ee7fcd5c..1a1fefb71 100644 --- a/tests/view/downcastwriter/mergecontainers.js +++ b/tests/view/downcastwriter/mergecontainers.js @@ -8,8 +8,15 @@ import { stringify, parse } from '../../../src/dev-utils/view'; import Document from '../../../src/view/document'; import { expectToThrowCKEditorError } from '@ckeditor/ckeditor5-utils/tests/_utils/utils'; +import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'DowncastWriter', () => { + let stylesProcessor; + + before( () => { + stylesProcessor = new StylesProcessor(); + } ); + describe( 'mergeContainers()', () => { let writer; @@ -26,7 +33,7 @@ describe( 'DowncastWriter', () => { } before( () => { - writer = new DowncastWriter( new Document() ); + writer = new DowncastWriter( new Document( stylesProcessor ) ); } ); it( 'should merge two container elements - position between elements', () => { diff --git a/tests/view/downcastwriter/move.js b/tests/view/downcastwriter/move.js index e0c65e351..ee0931046 100644 --- a/tests/view/downcastwriter/move.js +++ b/tests/view/downcastwriter/move.js @@ -16,8 +16,15 @@ import Position from '../../../src/view/position'; import Document from '../../../src/view/document'; import Mapper from '../../../src/conversion/mapper'; import { expectToThrowCKEditorError } from '@ckeditor/ckeditor5-utils/tests/_utils/utils'; +import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'DowncastWriter', () => { + let stylesProcessor; + + before( () => { + stylesProcessor = new StylesProcessor(); + } ); + describe( 'move()', () => { let writer, document; @@ -38,7 +45,7 @@ describe( 'DowncastWriter', () => { } before( () => { - document = new Document(); + document = new Document( stylesProcessor ); writer = new DowncastWriter( document ); } ); diff --git a/tests/view/downcastwriter/remove.js b/tests/view/downcastwriter/remove.js index 461c8112c..7ad5d4594 100644 --- a/tests/view/downcastwriter/remove.js +++ b/tests/view/downcastwriter/remove.js @@ -14,8 +14,15 @@ import UIElement from '../../../src/view/uielement'; import Document from '../../../src/view/document'; import { expectToThrowCKEditorError } from '@ckeditor/ckeditor5-utils/tests/_utils/utils'; +import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'DowncastWriter', () => { + let stylesProcessor; + + before( () => { + stylesProcessor = new StylesProcessor(); + } ); + describe( 'remove()', () => { let writer, document; @@ -38,7 +45,7 @@ describe( 'DowncastWriter', () => { } beforeEach( () => { - document = new Document(); + document = new Document( stylesProcessor ); writer = new DowncastWriter( document ); } ); diff --git a/tests/view/downcastwriter/rename.js b/tests/view/downcastwriter/rename.js index 258a0e8c7..9a3e3e8ff 100644 --- a/tests/view/downcastwriter/rename.js +++ b/tests/view/downcastwriter/rename.js @@ -6,13 +6,20 @@ import DowncastWriter from '../../../src/view/downcastwriter'; import { parse } from '../../../src/dev-utils/view'; import Document from '../../../src/view/document'; +import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'DowncastWriter', () => { + let stylesProcessor; + + before( () => { + stylesProcessor = new StylesProcessor(); + } ); + describe( 'rename()', () => { let root, foo, writer; before( () => { - writer = new DowncastWriter( new Document() ); + writer = new DowncastWriter( new Document( stylesProcessor ) ); } ); beforeEach( () => { diff --git a/tests/view/downcastwriter/unwrap.js b/tests/view/downcastwriter/unwrap.js index 71a39e2fe..52c177900 100644 --- a/tests/view/downcastwriter/unwrap.js +++ b/tests/view/downcastwriter/unwrap.js @@ -16,8 +16,15 @@ import Text from '../../../src/view/text'; import { stringify, parse } from '../../../src/dev-utils/view'; import Document from '../../../src/view/document'; import { expectToThrowCKEditorError } from '@ckeditor/ckeditor5-utils/tests/_utils/utils'; +import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'DowncastWriter', () => { + let stylesProcessor; + + before( () => { + stylesProcessor = new StylesProcessor(); + } ); + describe( 'unwrap()', () => { let writer, document; @@ -34,7 +41,7 @@ describe( 'DowncastWriter', () => { } beforeEach( () => { - document = new Document(); + document = new Document( stylesProcessor ); writer = new DowncastWriter( document ); } ); diff --git a/tests/view/downcastwriter/wrap.js b/tests/view/downcastwriter/wrap.js index 48ba9adcb..8221b92d2 100644 --- a/tests/view/downcastwriter/wrap.js +++ b/tests/view/downcastwriter/wrap.js @@ -19,13 +19,20 @@ import { stringify, parse } from '../../../src/dev-utils/view'; import createViewRoot from '../_utils/createroot'; import Document from '../../../src/view/document'; import { expectToThrowCKEditorError } from '@ckeditor/ckeditor5-utils/tests/_utils/utils'; +import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'DowncastWriter', () => { + let stylesProcessor; + + before( () => { + stylesProcessor = new StylesProcessor(); + } ); + describe( 'wrap()', () => { let writer, document; beforeEach( () => { - document = new Document(); + document = new Document( stylesProcessor ); writer = new DowncastWriter( document ); } ); diff --git a/tests/view/downcastwriter/writer.js b/tests/view/downcastwriter/writer.js index 05651fdb2..2bdcac85b 100644 --- a/tests/view/downcastwriter/writer.js +++ b/tests/view/downcastwriter/writer.js @@ -11,13 +11,19 @@ import ViewRange from '../../../src/view/range'; import createViewRoot from '../_utils/createroot'; import ViewElement from '../../../src/view/element'; import ViewSelection from '../../../src/view/selection'; +import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'DowncastWriter', () => { let writer, attributes, root, doc; + let stylesProcessor; + + before( () => { + stylesProcessor = new StylesProcessor(); + } ); beforeEach( () => { attributes = { foo: 'bar', baz: 'quz' }; - doc = new Document(); + doc = new Document( stylesProcessor ); root = createViewRoot( doc ); writer = new DowncastWriter( doc ); } ); diff --git a/tests/view/editableelement.js b/tests/view/editableelement.js index 4b297ddf1..7aac2a705 100644 --- a/tests/view/editableelement.js +++ b/tests/view/editableelement.js @@ -8,13 +8,20 @@ import createDocumentMock from '../../tests/view/_utils/createdocumentmock'; import EditableElement from '../../src/view/editableelement'; import Range from '../../src/view/range'; import Document from '../../src/view/document'; +import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'EditableElement', () => { + let stylesProcessor; + + before( () => { + stylesProcessor = new StylesProcessor(); + } ); + describe( 'is', () => { let el; before( () => { - el = new EditableElement( new Document(), 'div' ); + el = new EditableElement( new Document( stylesProcessor ), 'div' ); } ); it( 'should return true for containerElement/editable/element, also with correct name and element name', () => { diff --git a/tests/view/element.js b/tests/view/element.js index d227d1741..c58433e3d 100644 --- a/tests/view/element.js +++ b/tests/view/element.js @@ -9,12 +9,17 @@ import Element from '../../src/view/element'; import Text from '../../src/view/text'; import TextProxy from '../../src/view/textproxy'; import Document from '../../src/view/document'; +import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'Element', () => { - let document; + let document, stylesProcessor; + + before( () => { + stylesProcessor = new StylesProcessor(); + } ); beforeEach( () => { - document = new Document(); + document = new Document( stylesProcessor ); } ); describe( 'constructor()', () => { @@ -410,7 +415,7 @@ describe( 'Element', () => { } ); it( 'set proper #document on inserted children', () => { - const anotherDocument = new Document(); + const anotherDocument = new Document( stylesProcessor ); const anotherEl = new Element( anotherDocument, 'p' ); parent._insertChild( 0, anotherEl ); diff --git a/tests/view/emptyelement.js b/tests/view/emptyelement.js index 50c7e4456..e29da7a61 100644 --- a/tests/view/emptyelement.js +++ b/tests/view/emptyelement.js @@ -8,12 +8,18 @@ import Element from '../../src/view/element'; import Document from '../../src/view/document'; import { expectToThrowCKEditorError } from '@ckeditor/ckeditor5-utils/tests/_utils/utils'; +import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'EmptyElement', () => { let element, emptyElement, document; + let stylesProcessor; + + before( () => { + stylesProcessor = new StylesProcessor(); + } ); beforeEach( () => { - document = new Document(); + document = new Document( stylesProcessor ); element = new Element( document, 'b' ); emptyElement = new EmptyElement( document, 'img', { alt: 'alternative text', diff --git a/tests/view/matcher.js b/tests/view/matcher.js index e5ff5c4cd..ef2d3af76 100644 --- a/tests/view/matcher.js +++ b/tests/view/matcher.js @@ -6,12 +6,17 @@ import Matcher from '../../src/view/matcher'; import Element from '../../src/view/element'; import Document from '../../src/view/document'; +import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'Matcher', () => { - let document; + let document, stylesProcessor; + + before( () => { + stylesProcessor = new StylesProcessor(); + } ); beforeEach( () => { - document = new Document(); + document = new Document( stylesProcessor ); } ); describe( 'add', () => { diff --git a/tests/view/node.js b/tests/view/node.js index 906ae1cd0..62e791e46 100644 --- a/tests/view/node.js +++ b/tests/view/node.js @@ -12,14 +12,17 @@ import RootEditableElement from '../../src/view/rooteditableelement'; import createDocumentMock from '../../tests/view/_utils/createdocumentmock'; import { expectToThrowCKEditorError } from '@ckeditor/ckeditor5-utils/tests/_utils/utils'; import Document from '../../src/view/document'; +import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'Node', () => { let root, document, one, two, three, - charB, charA, charR, img; + charB, charA, charR, img, + stylesProcessor; before( () => { - document = new Document(); + stylesProcessor = new StylesProcessor(); + document = new Document( stylesProcessor ); charB = new Text( document, 'b' ); charA = new Text( document, 'a' ); diff --git a/tests/view/observer/mutationobserver.js b/tests/view/observer/mutationobserver.js index ccbddce74..672fc017c 100644 --- a/tests/view/observer/mutationobserver.js +++ b/tests/view/observer/mutationobserver.js @@ -10,16 +10,23 @@ import MutationObserver from '../../../src/view/observer/mutationobserver'; import UIElement from '../../../src/view/uielement'; import createViewRoot from '../_utils/createroot'; import { parse } from '../../../src/dev-utils/view'; +import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'MutationObserver', () => { let view, domEditor, viewDocument, viewRoot, mutationObserver, lastMutations, domRoot; + let stylesProcessor; + + before( () => { + stylesProcessor = new StylesProcessor(); + } ); + beforeEach( () => { domRoot = document.createElement( 'div' ); domRoot.innerHTML = '
'; document.body.appendChild( domRoot ); - view = new View(); + view = new View( stylesProcessor ); viewDocument = view.document; domEditor = document.getElementById( 'main' ); lastMutations = null; @@ -37,7 +44,7 @@ describe( 'MutationObserver', () => { viewRoot = viewDocument.getRoot(); - viewRoot._appendChild( parse( 'foobar' ) ); + viewRoot._appendChild( parse( 'foobar', { stylesProcessor } ) ); view.forceRender(); } ); @@ -97,7 +104,7 @@ describe( 'MutationObserver', () => { it( 'should handle unbold', () => { viewRoot._removeChildren( 0, viewRoot.childCount ); - viewRoot._appendChild( parse( 'foo' ) ); + viewRoot._appendChild( parse( 'foo', { stylesProcessor } ) ); view.forceRender(); const domP = domEditor.childNodes[ 0 ]; @@ -204,7 +211,7 @@ describe( 'MutationObserver', () => { view.attachDomRoot( domAdditionalEditor, 'additional' ); viewDocument.getRoot( 'additional' )._appendChild( - parse( 'foobar' ) ); + parse( 'foobar', { stylesProcessor } ) ); // Render AdditionalEditor (first editor has been rendered in the beforeEach function) view.forceRender(); @@ -225,7 +232,9 @@ describe( 'MutationObserver', () => { } ); it( 'should fire children mutation if the mutation occurred in the inline filler', () => { - const { view: viewContainer, selection } = parse( 'foo[]bar' ); + const { view: viewContainer, selection } = parse( + 'foo[]bar', { stylesProcessor } + ); view.change( writer => { viewRoot._appendChild( viewContainer ); @@ -243,7 +252,9 @@ describe( 'MutationObserver', () => { } ); it( 'should have no inline filler in mutation', () => { - const { view: viewContainer, selection } = parse( 'foo[]bar' ); + const { view: viewContainer, selection } = parse( + 'foo[]bar', { stylesProcessor } + ); view.change( writer => { viewRoot._appendChild( viewContainer ); @@ -254,7 +265,7 @@ describe( 'MutationObserver', () => { inlineFiller.data += 'x'; view.change( () => { - viewContainer.getChild( 1 )._appendChild( parse( 'x' ) ); + viewContainer.getChild( 1 )._appendChild( parse( 'x', { stylesProcessor } ) ); mutationObserver.flush(); } ); @@ -275,7 +286,8 @@ describe( 'MutationObserver', () => { '' + 'foo' + '[]' + - '' + '', + { stylesProcessor } ); view.change( writer => { @@ -307,7 +319,8 @@ describe( 'MutationObserver', () => { 'foo' + 'bar' + '[]' + - '' + '', + { stylesProcessor } ); view.change( writer => { @@ -350,7 +363,8 @@ describe( 'MutationObserver', () => { '' + '[]' + 'foo' + - '' + '', + { stylesProcessor } ); view.change( writer => { @@ -376,7 +390,7 @@ describe( 'MutationObserver', () => { } ); it( 'should have no block filler in mutation', () => { - viewRoot._appendChild( parse( '' ) ); + viewRoot._appendChild( parse( '', { stylesProcessor } ) ); view.forceRender(); @@ -395,7 +409,7 @@ describe( 'MutationObserver', () => { } ); it( 'should ignore mutation with bogus br inserted on the end of the empty paragraph', () => { - viewRoot._appendChild( parse( '' ) ); + viewRoot._appendChild( parse( '', { stylesProcessor } ) ); view.forceRender(); @@ -408,7 +422,7 @@ describe( 'MutationObserver', () => { } ); it( 'should ignore mutation with bogus br inserted on the end of the paragraph with text', () => { - viewRoot._appendChild( parse( 'foo' ) ); + viewRoot._appendChild( parse( 'foo', { stylesProcessor } ) ); view.forceRender(); @@ -421,7 +435,7 @@ describe( 'MutationObserver', () => { } ); it( 'should ignore mutation with bogus br inserted on the end of the paragraph while processing text mutations', () => { - viewRoot._appendChild( parse( 'foo' ) ); + viewRoot._appendChild( parse( 'foo', { stylesProcessor } ) ); view.forceRender(); @@ -438,7 +452,7 @@ describe( 'MutationObserver', () => { } ); it( 'should ignore child mutations which resulted in no changes – when element contains elements', () => { - viewRoot._appendChild( parse( '' ) ); + viewRoot._appendChild( parse( '', { stylesProcessor } ) ); view.forceRender(); @@ -472,7 +486,7 @@ describe( 'MutationObserver', () => { } ); it( 'should not ignore mutation with br inserted not on the end of the paragraph', () => { - viewRoot._appendChild( parse( 'foo' ) ); + viewRoot._appendChild( parse( 'foo', { stylesProcessor } ) ); view.forceRender(); @@ -491,7 +505,7 @@ describe( 'MutationObserver', () => { } ); it( 'should not ignore mutation inserting element different than br on the end of the empty paragraph', () => { - viewRoot._appendChild( parse( '' ) ); + viewRoot._appendChild( parse( '', { stylesProcessor } ) ); view.forceRender(); @@ -509,7 +523,7 @@ describe( 'MutationObserver', () => { } ); it( 'should not ignore mutation inserting element different than br on the end of the paragraph with text', () => { - viewRoot._appendChild( parse( 'foo' ) ); + viewRoot._appendChild( parse( 'foo', { stylesProcessor } ) ); view.forceRender(); diff --git a/tests/view/position.js b/tests/view/position.js index b6c6bd289..cd388cfcc 100644 --- a/tests/view/position.js +++ b/tests/view/position.js @@ -18,13 +18,17 @@ import createViewRoot from './_utils/createroot'; import AttributeElement from '../../src/view/attributeelement'; import ContainerElement from '../../src/view/containerelement'; import { expectToThrowCKEditorError } from '@ckeditor/ckeditor5-utils/tests/_utils/utils'; +import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'Position', () => { const parentMock = {}; let document; - beforeEach( () => { - document = new Document(); + let stylesProcessor; + + before( () => { + stylesProcessor = new StylesProcessor(); + document = new Document( stylesProcessor ); } ); describe( 'constructor()', () => { @@ -644,7 +648,7 @@ describe( 'Position', () => { let root; beforeEach( () => { - const doc = new Document(); + const doc = new Document( stylesProcessor ); root = createViewRoot( doc ); diff --git a/tests/view/range.js b/tests/view/range.js index 30e657e6c..79419f228 100644 --- a/tests/view/range.js +++ b/tests/view/range.js @@ -12,6 +12,7 @@ import TextProxy from '../../src/view/textproxy'; import TreeWalker from '../../src/view/treewalker'; import Document from '../../src/view/document'; import { parse, stringify } from '../../src/dev-utils/view'; +import { StylesProcessor } from '../../src/view/stylesmap'; function getRange( view, options = {} ) { const { selection } = parse( view, options ); @@ -20,10 +21,14 @@ function getRange( view, options = {} ) { } describe( 'Range', () => { - let document; + let document, stylesProcessor; + + before( () => { + stylesProcessor = new StylesProcessor(); + } ); beforeEach( () => { - document = new Document(); + document = new Document( stylesProcessor ); } ); describe( 'constructor()', () => { diff --git a/tests/view/renderer.js b/tests/view/renderer.js index 26841a6a1..04eb172c4 100644 --- a/tests/view/renderer.js +++ b/tests/view/renderer.js @@ -26,14 +26,20 @@ import createElement from '@ckeditor/ckeditor5-utils/src/dom/createelement'; import normalizeHtml from '@ckeditor/ckeditor5-utils/tests/_utils/normalizehtml'; import env from '@ckeditor/ckeditor5-utils/src/env'; import { expectToThrowCKEditorError } from '@ckeditor/ckeditor5-utils/tests/_utils/utils'; +import { StylesProcessor } from '../../src/view/stylesmap'; -describe( 'Renderer', () => { +describe.only( 'Renderer', () => { let view, selection, domConverter, renderer, viewDocument; + let stylesProcessor; testUtils.createSinonSandbox(); + before( () => { + stylesProcessor = new StylesProcessor(); + } ); + beforeEach( () => { - view = new View(); + view = new View( stylesProcessor ); viewDocument = view.document; renderer = new Renderer( view ); @@ -3118,7 +3124,7 @@ describe( 'Renderer', () => { '
  1. Item 1

Foo

' ) ); } ); - it( 'should handle styles change in replaced elements', () => { + it.only( 'should handle styles change in replaced elements', () => { const view = '' + '' + 'Foo' + @@ -3129,7 +3135,7 @@ describe( 'Renderer', () => { '' + ''; - viewRoot._appendChild( parse( view ) ); + viewRoot._appendChild( parse( view, { stylesProcessor } ) ); renderer.markToSync( 'children', viewRoot ); renderer.render(); @@ -3526,7 +3532,7 @@ describe( 'Renderer', () => { // #1560 describe( 'attributes manipulation on replaced element', () => { it( 'should rerender element if it was removed after having its attributes removed (attribute)', () => { - const writer = new DowncastWriter(); + const writer = new DowncastWriter( viewDocument ); // 1. Setup initial view/DOM. viewRoot._appendChild( parse( '1' ) ); @@ -3555,7 +3561,7 @@ describe( 'Renderer', () => { } ); it( 'should rerender element if it was removed after having its attributes removed (classes)', () => { - const writer = new DowncastWriter(); + const writer = new DowncastWriter( viewDocument ); // 1. Setup initial view/DOM. viewRoot._appendChild( parse( 'h1p' ) ); @@ -3585,7 +3591,7 @@ describe( 'Renderer', () => { } ); it( 'should rerender element if it was removed and have its attributes removed after', () => { - const writer = new DowncastWriter(); + const writer = new DowncastWriter( viewDocument ); // 1. Setup initial view/DOM. viewRoot._appendChild( parse( '1' ) ); diff --git a/tests/view/selection.js b/tests/view/selection.js index ed9ba57e0..34700a6dd 100644 --- a/tests/view/selection.js +++ b/tests/view/selection.js @@ -16,14 +16,20 @@ import createViewRoot from './_utils/createroot'; import { parse } from '../../src/dev-utils/view'; import testUtils from '@ckeditor/ckeditor5-core/tests/_utils/utils'; import { expectToThrowCKEditorError } from '@ckeditor/ckeditor5-utils/tests/_utils/utils'; +import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'Selection', () => { let selection, el, range1, range2, range3, viewDocument; + let stylesProcessor; testUtils.createSinonSandbox(); + before( () => { + stylesProcessor = new StylesProcessor(); + } ); + beforeEach( () => { - viewDocument = new Document(); + viewDocument = new Document( stylesProcessor ); const text = new Text( viewDocument, 'xxxxxxxxxxxxxxxxxxxx' ); el = new Element( viewDocument, 'p', null, text ); diff --git a/tests/view/text.js b/tests/view/text.js index 810f0ede9..e9850b016 100644 --- a/tests/view/text.js +++ b/tests/view/text.js @@ -6,12 +6,17 @@ import Node from '../../src/view/node'; import Text from '../../src/view/text'; import Document from '../../src/view/document'; +import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'Text', () => { - let document; + let document, stylesProcessor; + + before( () => { + stylesProcessor = new StylesProcessor(); + } ); beforeEach( () => { - document = new Document(); + document = new Document( stylesProcessor ); } ); describe( 'constructor()', () => { diff --git a/tests/view/textproxy.js b/tests/view/textproxy.js index a6c82c355..3521e614e 100644 --- a/tests/view/textproxy.js +++ b/tests/view/textproxy.js @@ -12,12 +12,18 @@ import RootEditableElement from '../../src/view/rooteditableelement'; import createDocumentMock from '../../tests/view/_utils/createdocumentmock'; import { expectToThrowCKEditorError } from '@ckeditor/ckeditor5-utils/tests/_utils/utils'; import Document from '../../src/view/document'; +import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'TextProxy', () => { let text, parent, wrapper, textProxy, document; + let stylesProcessor; + + before( () => { + stylesProcessor = new StylesProcessor(); + } ); beforeEach( () => { - document = new Document(); + document = new Document( stylesProcessor ); text = new Text( document, 'abcdefgh' ); parent = new ContainerElement( document, 'p', [], [ text ] ); wrapper = new ContainerElement( document, 'div', [], parent ); diff --git a/tests/view/treewalker.js b/tests/view/treewalker.js index 3217982e4..b926988cf 100644 --- a/tests/view/treewalker.js +++ b/tests/view/treewalker.js @@ -13,12 +13,15 @@ import Position from '../../src/view/position'; import Range from '../../src/view/range'; import createViewRoot from './_utils/createroot'; import { expectToThrowCKEditorError } from '@ckeditor/ckeditor5-utils/tests/_utils/utils'; +import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'TreeWalker', () => { let doc, root, img1, paragraph, bold, textAbcd, charY, img2, charX, rootBeginning, rootEnding; + let stylesProcessor; before( () => { - doc = new Document(); + stylesProcessor = new StylesProcessor(); + doc = new Document( stylesProcessor ); root = createViewRoot( doc ); // root diff --git a/tests/view/uielement.js b/tests/view/uielement.js index 9bfa37969..538555331 100644 --- a/tests/view/uielement.js +++ b/tests/view/uielement.js @@ -9,12 +9,17 @@ import UIElement from '../../src/view/uielement'; import Element from '../../src/view/element'; import Document from '../../src/view/document'; import { expectToThrowCKEditorError } from '@ckeditor/ckeditor5-utils/tests/_utils/utils'; +import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'UIElement', () => { - let uiElement, doc; + let uiElement, doc, stylesProcessor; + + before( () => { + stylesProcessor = new StylesProcessor(); + } ); beforeEach( () => { - doc = new Document(); + doc = new Document( stylesProcessor ); uiElement = new UIElement( doc, 'span', { foo: 'bar', diff --git a/tests/view/upcastwriter.js b/tests/view/upcastwriter.js index 314ef4bcd..08561932d 100644 --- a/tests/view/upcastwriter.js +++ b/tests/view/upcastwriter.js @@ -12,14 +12,16 @@ import ViewPosition from '../../src/view/position'; import ViewRange from '../../src/view/range'; import ViewSelection from '../../src/view/selection'; import Document from '../../src/view/document'; +import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'UpcastWriter', () => { - let writer, view, dataprocessor, document; + let writer, view, dataprocessor, document, stylesProcessor; before( () => { - document = new Document(); + stylesProcessor = new StylesProcessor(); + document = new Document( stylesProcessor ); writer = new UpcastWriter( document ); - dataprocessor = new HtmlDataProcessor(); + dataprocessor = new HtmlDataProcessor( stylesProcessor ); } ); beforeEach( () => { diff --git a/tests/view/utils-tests/createroot.js b/tests/view/utils-tests/createroot.js index ddb26986e..92dd655d9 100644 --- a/tests/view/utils-tests/createroot.js +++ b/tests/view/utils-tests/createroot.js @@ -6,12 +6,17 @@ import Document from '../../../src/view/document.js'; import RootAttributeElement from '../../../src/view/rooteditableelement.js'; import createRoot from '../_utils/createroot.js'; +import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'createRoot', () => { - let viewDoc; + let viewDoc, stylesProcessor; + + before( () => { + stylesProcessor = new StylesProcessor(); + } ); beforeEach( () => { - viewDoc = new Document(); + viewDoc = new Document( stylesProcessor ); } ); it( 'should create view root element with given data', () => { diff --git a/tests/view/view/view.js b/tests/view/view/view.js index 58139e89b..1edd46276 100644 --- a/tests/view/view/view.js +++ b/tests/view/view/view.js @@ -18,6 +18,7 @@ import ViewRange from '../../../src/view/range'; import ViewElement from '../../../src/view/element'; import ViewPosition from '../../../src/view/position'; import ViewSelection from '../../../src/view/selection'; +import { StylesProcessor } from '../../../src/view/stylesmap'; import count from '@ckeditor/ckeditor5-utils/src/count'; import global from '@ckeditor/ckeditor5-utils/src/dom/global'; @@ -31,6 +32,12 @@ describe( 'view', () => { const DEFAULT_OBSERVERS_COUNT = 6; let domRoot, view, viewDocument, ObserverMock, instantiated, enabled, ObserverMockGlobalCount; + let stylesProcessor; + + before( () => { + stylesProcessor = new StylesProcessor(); + } ); + beforeEach( () => { domRoot = createElement( document, 'div', { id: 'editor', @@ -39,7 +46,7 @@ describe( 'view', () => { document.body.appendChild( domRoot ); - view = new View(); + view = new View( stylesProcessor ); viewDocument = view.document; ObserverMock = class extends Observer { From 5145ce096bd605c886c9b6af2e57d41584e2e6ea Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Maciej=20Go=C5=82aszewski?= Date: Wed, 19 Feb 2020 14:56:15 +0100 Subject: [PATCH 17/34] Update missing StylesProcessor instances in constructors. --- tests/conversion/downcasthelpers.js | 2 +- tests/view/renderer.js | 4 ++-- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/tests/conversion/downcasthelpers.js b/tests/conversion/downcasthelpers.js index 042f69936..5fd0405eb 100644 --- a/tests/conversion/downcasthelpers.js +++ b/tests/conversion/downcasthelpers.js @@ -1811,7 +1811,7 @@ describe( 'downcast selection converters', () => { model.schema.extend( '$text', { allowIn: '$root' } ); - view = new View(); + view = new View( new StylesProcessor() ); viewDoc = view.document; viewRoot = createViewRoot( viewDoc ); viewSelection = viewDoc.selection; diff --git a/tests/view/renderer.js b/tests/view/renderer.js index 04eb172c4..30bdb8d55 100644 --- a/tests/view/renderer.js +++ b/tests/view/renderer.js @@ -28,7 +28,7 @@ import env from '@ckeditor/ckeditor5-utils/src/env'; import { expectToThrowCKEditorError } from '@ckeditor/ckeditor5-utils/tests/_utils/utils'; import { StylesProcessor } from '../../src/view/stylesmap'; -describe.only( 'Renderer', () => { +describe( 'Renderer', () => { let view, selection, domConverter, renderer, viewDocument; let stylesProcessor; @@ -3124,7 +3124,7 @@ describe.only( 'Renderer', () => { '
  1. Item 1

Foo

' ) ); } ); - it.only( 'should handle styles change in replaced elements', () => { + it( 'should handle styles change in replaced elements', () => { const view = '' + '' + 'Foo' + From 821ae00fdb41da8c50a6e134a8be825ea08c78f3 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Maciej=20Go=C5=82aszewski?= Date: Wed, 19 Feb 2020 15:42:07 +0100 Subject: [PATCH 18/34] Add missing StylesProcessor instance. --- src/model/model.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/model/model.js b/src/model/model.js index d428e57f8..f20a40f8d 100644 --- a/src/model/model.js +++ b/src/model/model.js @@ -334,7 +334,7 @@ export default class Model { * * // You can create your own HtmlDataProcessor instance or use editor.data.processor * // if you have not overridden the default one (which is the HtmlDataProcessor instance). - * const htmlDP = new HtmlDataProcessor(); + * const htmlDP = new HtmlDataProcessor( new StylesProcessor() ); * * // Convert an HTML string to a view document fragment: * const viewFragment = htmlDP.toView( htmlString ); From 2ce84924fc9316708a9d273d947d4ddb6c8bf319 Mon Sep 17 00:00:00 2001 From: Kamil Piechaczek Date: Thu, 20 Feb 2020 13:55:31 +0100 Subject: [PATCH 19/34] Aligned to changes in Editor class. --- src/controller/datacontroller.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/controller/datacontroller.js b/src/controller/datacontroller.js index cfd3499bb..c14b007d4 100644 --- a/src/controller/datacontroller.js +++ b/src/controller/datacontroller.js @@ -61,7 +61,7 @@ export default class DataController { this.model = model; /** - * Styles processor. + * StylesProcessor is responsible for writing and reading a normalized styles object. * * @readonly * @member {module:engine/view/stylesmap~StylesProcessor} From e2ed99c3e12bbd7f6d6abe75a24f0263b947b1c7 Mon Sep 17 00:00:00 2001 From: Kamil Piechaczek Date: Thu, 20 Feb 2020 14:21:51 +0100 Subject: [PATCH 20/34] Aligned tests to changes in API. --- tests/conversion/downcastdispatcher.js | 8 +++++++- tests/conversion/upcasthelpers.js | 2 +- tests/view/downcastwriter/wrap.js | 2 +- tests/view/manual/clickobserver.js | 3 ++- tests/view/manual/fakeselection.js | 3 ++- tests/view/manual/focus.js | 3 ++- tests/view/manual/focusobserver.js | 3 ++- tests/view/manual/immutable.js | 3 ++- tests/view/manual/inline-filler.js | 3 ++- tests/view/manual/keyobserver.js | 3 ++- tests/view/manual/mutationobserver.js | 3 ++- tests/view/manual/noselection-iframe.js | 3 ++- tests/view/manual/noselection.js | 3 ++- tests/view/manual/selectionobserver.js | 3 ++- tests/view/manual/x-index.js | 3 ++- tests/view/observer/clickobserver.js | 8 +++++++- tests/view/observer/compositionobserver.js | 8 +++++++- tests/view/observer/domeventdata.js | 8 +++++++- tests/view/observer/domeventobserver.js | 8 +++++++- tests/view/observer/fakeselectionobserver.js | 7 +++++-- tests/view/observer/focusobserver.js | 10 ++++++++-- tests/view/observer/inputobserver.js | 8 ++++++-- tests/view/observer/keyobserver.js | 8 +++++++- tests/view/observer/mouseobserver.js | 8 +++++++- tests/view/observer/observer.js | 9 ++++++++- tests/view/observer/selectionobserver.js | 8 +++++++- tests/view/placeholder.js | 10 ++++++++-- tests/view/renderer.js | 2 +- tests/view/view/jumpoverinlinefiller.js | 8 +++++++- tests/view/view/jumpoveruielement.js | 8 +++++++- tests/view/view/view.js | 12 ++++++------ 31 files changed, 138 insertions(+), 40 deletions(-) diff --git a/tests/conversion/downcastdispatcher.js b/tests/conversion/downcastdispatcher.js index 07f6fc3dd..83c1b84ec 100644 --- a/tests/conversion/downcastdispatcher.js +++ b/tests/conversion/downcastdispatcher.js @@ -13,13 +13,19 @@ import ModelRange from '../../src/model/range'; import View from '../../src/view/view'; import ViewContainerElement from '../../src/view/containerelement'; +import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'DowncastDispatcher', () => { let dispatcher, doc, root, differStub, model, view, mapper; + let stylesProcessor; + + before( () => { + stylesProcessor = new StylesProcessor(); + } ); beforeEach( () => { model = new Model(); - view = new View(); + view = new View( stylesProcessor ); doc = model.document; mapper = new Mapper(); dispatcher = new DowncastDispatcher( { mapper } ); diff --git a/tests/conversion/upcasthelpers.js b/tests/conversion/upcasthelpers.js index 852050495..68fec7ad8 100644 --- a/tests/conversion/upcasthelpers.js +++ b/tests/conversion/upcasthelpers.js @@ -889,7 +889,7 @@ describe( 'upcast-converters', () => { modelSetData( model, 'foobar' ); - view = new View(); + view = new View( stylesProcessor ); viewDocument = view.document; viewRoot = createViewRoot( viewDocument, 'div', 'main' ); diff --git a/tests/view/downcastwriter/wrap.js b/tests/view/downcastwriter/wrap.js index 8221b92d2..d943e30b1 100644 --- a/tests/view/downcastwriter/wrap.js +++ b/tests/view/downcastwriter/wrap.js @@ -527,7 +527,7 @@ describe( 'DowncastWriter', () => { let view, viewDocument, viewRoot; beforeEach( () => { - view = new View(); + view = new View( stylesProcessor ); viewDocument = view.document; viewRoot = createViewRoot( viewDocument ); } ); diff --git a/tests/view/manual/clickobserver.js b/tests/view/manual/clickobserver.js index df1289598..ac7f67541 100644 --- a/tests/view/manual/clickobserver.js +++ b/tests/view/manual/clickobserver.js @@ -8,8 +8,9 @@ import View from '../../../src/view/view'; import DomEventObserver from '../../../src/view/observer/domeventobserver'; import createViewRoot from '../_utils/createroot'; +import { StylesProcessor } from '../../../src/view/stylesmap'; -const view = new View(); +const view = new View( new StylesProcessor() ); const viewDocument = view.document; // Disable rendering for this example, because it re-enables all observers each time view is rendered. diff --git a/tests/view/manual/fakeselection.js b/tests/view/manual/fakeselection.js index 019a8c504..eff403434 100644 --- a/tests/view/manual/fakeselection.js +++ b/tests/view/manual/fakeselection.js @@ -10,8 +10,9 @@ import DomEventObserver from '../../../src/view/observer/domeventobserver'; import ViewRange from '../../../src/view/range'; import createViewRoot from '../_utils/createroot'; import { setData } from '../../../src/dev-utils/view'; +import { StylesProcessor } from '../../../src/view/stylesmap'; -const view = new View(); +const view = new View( new StylesProcessor() ); const viewDocument = view.document; const domEditable = document.getElementById( 'editor' ); const viewRoot = createViewRoot( viewDocument ); diff --git a/tests/view/manual/focus.js b/tests/view/manual/focus.js index 78b2a54ed..e73ad2350 100644 --- a/tests/view/manual/focus.js +++ b/tests/view/manual/focus.js @@ -9,8 +9,9 @@ import View from '../../../src/view/view'; import ViewPosition from '../../../src/view/position'; import ViewRange from '../../../src/view/range'; import createViewRoot from '../_utils/createroot'; +import { StylesProcessor } from '../../../src/view/stylesmap'; -const view = new View(); +const view = new View( new StylesProcessor() ); const viewDocument = view.document; const domEditable1 = document.getElementById( 'editable1' ); diff --git a/tests/view/manual/focusobserver.js b/tests/view/manual/focusobserver.js index ba1eef1d1..13b0ce5ca 100644 --- a/tests/view/manual/focusobserver.js +++ b/tests/view/manual/focusobserver.js @@ -7,8 +7,9 @@ import View from '../../../src/view/view'; import createViewRoot from '../_utils/createroot'; +import { StylesProcessor } from '../../../src/view/stylesmap'; -const view = new View(); +const view = new View( new StylesProcessor() ); const viewDocument = view.document; viewDocument.on( 'focus', ( evt, data ) => console.log( `Focus in ${ data.domTarget.id }.` ) ); diff --git a/tests/view/manual/immutable.js b/tests/view/manual/immutable.js index 244695a61..243cebaf6 100644 --- a/tests/view/manual/immutable.js +++ b/tests/view/manual/immutable.js @@ -8,8 +8,9 @@ import View from '../../../src/view/view'; import { setData } from '../../../src/dev-utils/view'; import createViewRoot from '../_utils/createroot'; +import { StylesProcessor } from '../../../src/view/stylesmap'; -const view = new View(); +const view = new View( new StylesProcessor() ); const viewDocument = view.document; createViewRoot( viewDocument, 'div' ); view.attachDomRoot( document.getElementById( 'editor' ) ); diff --git a/tests/view/manual/inline-filler.js b/tests/view/manual/inline-filler.js index 28bfabc17..c2b4c6238 100644 --- a/tests/view/manual/inline-filler.js +++ b/tests/view/manual/inline-filler.js @@ -8,8 +8,9 @@ import View from '../../../src/view/view'; import createViewRoot from '../_utils/createroot'; import { setData } from '../../../src/dev-utils/view'; +import { StylesProcessor } from '../../../src/view/stylesmap'; -const view = new View(); +const view = new View( new StylesProcessor() ); const viewDocument = view.document; createViewRoot( viewDocument ); view.attachDomRoot( document.getElementById( 'editor' ) ); diff --git a/tests/view/manual/keyobserver.js b/tests/view/manual/keyobserver.js index d39221af2..3cc9bd0d0 100644 --- a/tests/view/manual/keyobserver.js +++ b/tests/view/manual/keyobserver.js @@ -7,8 +7,9 @@ import View from '../../../src/view/view'; import createViewRoot from '../_utils/createroot'; +import { StylesProcessor } from '../../../src/view/stylesmap'; -const view = new View(); +const view = new View( new StylesProcessor() ); const viewDocument = view.document; viewDocument.on( 'keydown', ( evt, data ) => console.log( 'keydown', data ) ); diff --git a/tests/view/manual/mutationobserver.js b/tests/view/manual/mutationobserver.js index 85272d161..8306de744 100644 --- a/tests/view/manual/mutationobserver.js +++ b/tests/view/manual/mutationobserver.js @@ -8,8 +8,9 @@ import View from '../../../src/view/view'; import createViewRoot from '../_utils/createroot'; import { setData } from '../../../src/dev-utils/view'; +import { StylesProcessor } from '../../../src/view/stylesmap'; -const view = new View(); +const view = new View( new StylesProcessor() ); const viewDocument = view.document; createViewRoot( viewDocument ); view.attachDomRoot( document.getElementById( 'editor' ) ); diff --git a/tests/view/manual/noselection-iframe.js b/tests/view/manual/noselection-iframe.js index 0564e9fe8..2ff1a4b3b 100644 --- a/tests/view/manual/noselection-iframe.js +++ b/tests/view/manual/noselection-iframe.js @@ -8,12 +8,13 @@ import View from '../../../src/view/view'; import { setData } from '../../../src/dev-utils/view'; import createViewRoot from '../_utils/createroot'; +import { StylesProcessor } from '../../../src/view/stylesmap'; const iframe = document.getElementById( 'iframe' ); iframe.srcdoc = '
'; iframe.addEventListener( 'load', () => { - const view = new View(); + const view = new View( new StylesProcessor() ); const viewDocument = view.document; createViewRoot( viewDocument ); diff --git a/tests/view/manual/noselection.js b/tests/view/manual/noselection.js index 390f5ca43..b836460c7 100644 --- a/tests/view/manual/noselection.js +++ b/tests/view/manual/noselection.js @@ -8,8 +8,9 @@ import View from '../../../src/view/view'; import { setData } from '../../../src/dev-utils/view'; import createViewRoot from '../_utils/createroot'; +import { StylesProcessor } from '../../../src/view/stylesmap'; -const view = new View(); +const view = new View( new StylesProcessor() ); const viewDocument = view.document; createViewRoot( viewDocument ); view.attachDomRoot( document.getElementById( 'editor' ) ); diff --git a/tests/view/manual/selectionobserver.js b/tests/view/manual/selectionobserver.js index 01a5eedc4..9a81860b1 100644 --- a/tests/view/manual/selectionobserver.js +++ b/tests/view/manual/selectionobserver.js @@ -8,8 +8,9 @@ import View from '../../../src/view/view'; import { setData } from '../../../src/dev-utils/view'; import createViewRoot from '../_utils/createroot'; +import { StylesProcessor } from '../../../src/view/stylesmap'; -const view = new View(); +const view = new View( new StylesProcessor() ); const viewDocument = view.document; createViewRoot( viewDocument ); view.attachDomRoot( document.getElementById( 'editor' ) ); diff --git a/tests/view/manual/x-index.js b/tests/view/manual/x-index.js index d6087a774..801eab3cb 100644 --- a/tests/view/manual/x-index.js +++ b/tests/view/manual/x-index.js @@ -8,8 +8,9 @@ import View from '../../../src/view/view'; import { setData } from '../../../src/dev-utils/view'; import createViewRoot from '../_utils/createroot'; +import { StylesProcessor } from '../../../src/view/stylesmap'; -const view = new View(); +const view = new View( new StylesProcessor() ); const viewDocument = view.document; createViewRoot( viewDocument ); view.attachDomRoot( document.getElementById( 'editor' ) ); diff --git a/tests/view/observer/clickobserver.js b/tests/view/observer/clickobserver.js index a79b2c718..1c3aa5c8d 100644 --- a/tests/view/observer/clickobserver.js +++ b/tests/view/observer/clickobserver.js @@ -7,12 +7,18 @@ import ClickObserver from '../../../src/view/observer/clickobserver'; import View from '../../../src/view/view'; +import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'ClickObserver', () => { let view, viewDocument, observer; + let stylesProcessor; + + before( () => { + stylesProcessor = new StylesProcessor(); + } ); beforeEach( () => { - view = new View(); + view = new View( stylesProcessor ); viewDocument = view.document; observer = view.addObserver( ClickObserver ); } ); diff --git a/tests/view/observer/compositionobserver.js b/tests/view/observer/compositionobserver.js index 16f2a3bb0..3d3513732 100644 --- a/tests/view/observer/compositionobserver.js +++ b/tests/view/observer/compositionobserver.js @@ -6,12 +6,18 @@ /* globals document */ import CompositionObserver from '../../../src/view/observer/compositionobserver'; import View from '../../../src/view/view'; +import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'CompositionObserver', () => { let view, viewDocument, observer; + let stylesProcessor; + + before( () => { + stylesProcessor = new StylesProcessor(); + } ); beforeEach( () => { - view = new View(); + view = new View( stylesProcessor ); viewDocument = view.document; observer = view.getObserver( CompositionObserver ); } ); diff --git a/tests/view/observer/domeventdata.js b/tests/view/observer/domeventdata.js index b736d0444..2ffe0e7e7 100644 --- a/tests/view/observer/domeventdata.js +++ b/tests/view/observer/domeventdata.js @@ -7,12 +7,18 @@ import DomEventData from '../../../src/view/observer/domeventdata'; import View from '../../../src/view/view'; +import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'DomEventData', () => { let view, viewDocument, viewBody, domRoot; + let stylesProcessor; + + before( () => { + stylesProcessor = new StylesProcessor(); + } ); beforeEach( () => { - view = new View(); + view = new View( stylesProcessor ); viewDocument = view.document; domRoot = document.createElement( 'div' ); diff --git a/tests/view/observer/domeventobserver.js b/tests/view/observer/domeventobserver.js index f73f87c88..f1425ad29 100644 --- a/tests/view/observer/domeventobserver.js +++ b/tests/view/observer/domeventobserver.js @@ -10,6 +10,7 @@ import Observer from '../../../src/view/observer/observer'; import View from '../../../src/view/view'; import UIElement from '../../../src/view/uielement'; import createViewRoot from '../_utils/createroot'; +import { StylesProcessor } from '../../../src/view/stylesmap'; class ClickObserver extends DomEventObserver { constructor( view ) { @@ -45,9 +46,14 @@ class ClickCapturingObserver extends ClickObserver { describe( 'DomEventObserver', () => { let view, viewDocument; + let stylesProcessor; + + before( () => { + stylesProcessor = new StylesProcessor(); + } ); beforeEach( () => { - view = new View(); + view = new View( stylesProcessor ); viewDocument = view.document; } ); diff --git a/tests/view/observer/fakeselectionobserver.js b/tests/view/observer/fakeselectionobserver.js index d217a4cde..4b1d2723d 100644 --- a/tests/view/observer/fakeselectionobserver.js +++ b/tests/view/observer/fakeselectionobserver.js @@ -13,12 +13,15 @@ import createViewRoot from '../_utils/createroot'; import { keyCodes } from '@ckeditor/ckeditor5-utils/src/keyboard'; import { setData, stringify } from '../../../src/dev-utils/view'; import testUtils from '@ckeditor/ckeditor5-core/tests/_utils/utils'; +import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'FakeSelectionObserver', () => { - let observer, view, viewDocument, root, domRoot; + let observer, view, viewDocument, root, domRoot, stylesProcessor; testUtils.createSinonSandbox(); before( () => { + stylesProcessor = new StylesProcessor(); + domRoot = createElement( document, 'div', { contenteditable: 'true' } ); @@ -30,7 +33,7 @@ describe( 'FakeSelectionObserver', () => { } ); beforeEach( () => { - view = new View(); + view = new View( stylesProcessor ); viewDocument = view.document; root = createViewRoot( viewDocument ); view.attachDomRoot( domRoot ); diff --git a/tests/view/observer/focusobserver.js b/tests/view/observer/focusobserver.js index 3ac9a3de6..65eec7aec 100644 --- a/tests/view/observer/focusobserver.js +++ b/tests/view/observer/focusobserver.js @@ -8,12 +8,18 @@ import FocusObserver from '../../../src/view/observer/focusobserver'; import View from '../../../src/view/view'; import createViewRoot from '../_utils/createroot'; import { setData } from '../../../src/dev-utils/view'; +import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'FocusObserver', () => { let view, viewDocument, observer; + let stylesProcessor; + + before( () => { + stylesProcessor = new StylesProcessor(); + } ); beforeEach( () => { - view = new View(); + view = new View( stylesProcessor ); viewDocument = view.document; observer = view.getObserver( FocusObserver ); } ); @@ -157,7 +163,7 @@ describe( 'FocusObserver', () => { domRoot = document.createElement( 'div' ); document.body.appendChild( domRoot ); - view = new View(); + view = new View( stylesProcessor ); viewDocument = view.document; createViewRoot( viewDocument ); view.attachDomRoot( domRoot ); diff --git a/tests/view/observer/inputobserver.js b/tests/view/observer/inputobserver.js index 5e56c76c2..782e24757 100644 --- a/tests/view/observer/inputobserver.js +++ b/tests/view/observer/inputobserver.js @@ -6,17 +6,21 @@ import InputObserver from '../../../src/view/observer/inputobserver'; import View from '../../../src/view/view'; import env from '@ckeditor/ckeditor5-utils/src/env'; +import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'InputObserver', () => { - let view, viewDocument, observer; const oldEnvIsAndroid = env.isAndroid; + let view, viewDocument, observer; + let stylesProcessor; + before( () => { + stylesProcessor = new StylesProcessor(); env.isAndroid = true; } ); beforeEach( () => { - view = new View(); + view = new View( stylesProcessor ); viewDocument = view.document; observer = view.getObserver( InputObserver ); } ); diff --git a/tests/view/observer/keyobserver.js b/tests/view/observer/keyobserver.js index 45a73e8f6..2bdf25daf 100644 --- a/tests/view/observer/keyobserver.js +++ b/tests/view/observer/keyobserver.js @@ -8,12 +8,18 @@ import KeyObserver from '../../../src/view/observer/keyobserver'; import View from '../../../src/view/view'; import { getCode } from '@ckeditor/ckeditor5-utils/src/keyboard'; +import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'KeyObserver', () => { let view, viewDocument, observer; + let stylesProcessor; + + before( () => { + stylesProcessor = new StylesProcessor(); + } ); beforeEach( () => { - view = new View(); + view = new View( stylesProcessor ); viewDocument = view.document; observer = view.getObserver( KeyObserver ); } ); diff --git a/tests/view/observer/mouseobserver.js b/tests/view/observer/mouseobserver.js index 6d25325b1..93a67ce88 100644 --- a/tests/view/observer/mouseobserver.js +++ b/tests/view/observer/mouseobserver.js @@ -7,12 +7,18 @@ import MouseObserver from '../../../src/view/observer/mouseobserver'; import View from '../../../src/view/view'; +import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'MouseObserver', () => { let view, viewDocument, observer; + let stylesProcessor; + + before( () => { + stylesProcessor = new StylesProcessor(); + } ); beforeEach( () => { - view = new View(); + view = new View( stylesProcessor ); viewDocument = view.document; observer = view.addObserver( MouseObserver ); } ); diff --git a/tests/view/observer/observer.js b/tests/view/observer/observer.js index 6ec3fbd1f..662f911c6 100644 --- a/tests/view/observer/observer.js +++ b/tests/view/observer/observer.js @@ -5,11 +5,18 @@ import Observer from '../../../src/view/observer/observer'; import View from '../../../src/view/view'; +import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'Observer', () => { + let stylesProcessor; + + before( () => { + stylesProcessor = new StylesProcessor(); + } ); + describe( 'constructor()', () => { it( 'should create Observer with properties', () => { - const view = new View(); + const view = new View( stylesProcessor ); const observer = new Observer( view ); expect( observer ).to.be.an.instanceof( Observer ); diff --git a/tests/view/observer/selectionobserver.js b/tests/view/observer/selectionobserver.js index b9a7110ee..aa83e6eb6 100644 --- a/tests/view/observer/selectionobserver.js +++ b/tests/view/observer/selectionobserver.js @@ -13,9 +13,15 @@ import SelectionObserver from '../../../src/view/observer/selectionobserver'; import FocusObserver from '../../../src/view/observer/focusobserver'; import createViewRoot from '../_utils/createroot'; import { parse } from '../../../src/dev-utils/view'; +import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'SelectionObserver', () => { let view, viewDocument, viewRoot, selectionObserver, domRoot, domMain, domDocument; + let stylesProcessor; + + before( () => { + stylesProcessor = new StylesProcessor(); + } ); beforeEach( done => { domDocument = document; @@ -24,7 +30,7 @@ describe( 'SelectionObserver', () => { domMain = domRoot.childNodes[ 0 ]; domDocument.body.appendChild( domRoot ); - view = new View(); + view = new View( stylesProcessor ); viewDocument = view.document; createViewRoot( viewDocument ); view.attachDomRoot( domMain ); diff --git a/tests/view/placeholder.js b/tests/view/placeholder.js index 051124e02..1bf19b6ab 100644 --- a/tests/view/placeholder.js +++ b/tests/view/placeholder.js @@ -14,12 +14,18 @@ import createViewRoot from './_utils/createroot'; import View from '../../src/view/view'; import ViewRange from '../../src/view/range'; import { setData } from '../../src/dev-utils/view'; +import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'placeholder', () => { let view, viewDocument, viewRoot; + let stylesProcessor; + + before( () => { + stylesProcessor = new StylesProcessor(); + } ); beforeEach( () => { - view = new View(); + view = new View( stylesProcessor ); viewDocument = view.document; viewRoot = createViewRoot( viewDocument ); viewDocument.isFocused = true; @@ -172,7 +178,7 @@ describe( 'placeholder', () => { setData( view, '
{another div}
' ); const element = viewRoot.getChild( 0 ); - const secondView = new View(); + const secondView = new View( stylesProcessor ); const secondDocument = secondView.document; secondDocument.isFocused = true; const secondRoot = createViewRoot( secondDocument ); diff --git a/tests/view/renderer.js b/tests/view/renderer.js index 30bdb8d55..eb1fb1cb3 100644 --- a/tests/view/renderer.js +++ b/tests/view/renderer.js @@ -3729,7 +3729,7 @@ describe( 'Renderer', () => { let view, viewDoc, viewRoot, domRoot, converter; beforeEach( () => { - view = new View(); + view = new View( stylesProcessor ); viewDoc = view.document; domRoot = document.createElement( 'div' ); document.body.appendChild( domRoot ); diff --git a/tests/view/view/jumpoverinlinefiller.js b/tests/view/view/jumpoverinlinefiller.js index 670965339..64c88ae35 100644 --- a/tests/view/view/jumpoverinlinefiller.js +++ b/tests/view/view/jumpoverinlinefiller.js @@ -13,9 +13,15 @@ import { keyCodes } from '@ckeditor/ckeditor5-utils/src/keyboard'; import createElement from '@ckeditor/ckeditor5-utils/src/dom/createelement'; import { parse, setData } from '../../../src/dev-utils/view'; +import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'View', () => { let view, viewDocument, domRoot; + let stylesProcessor; + + before( () => { + stylesProcessor = new StylesProcessor(); + } ); beforeEach( () => { domRoot = createElement( document, 'div', { @@ -23,7 +29,7 @@ describe( 'View', () => { } ); document.body.appendChild( domRoot ); - view = new View(); + view = new View( stylesProcessor ); viewDocument = view.document; createViewRoot( viewDocument ); view.attachDomRoot( domRoot ); diff --git a/tests/view/view/jumpoveruielement.js b/tests/view/view/jumpoveruielement.js index c28318e80..284d501d9 100644 --- a/tests/view/view/jumpoveruielement.js +++ b/tests/view/view/jumpoveruielement.js @@ -16,9 +16,11 @@ import createElement from '@ckeditor/ckeditor5-utils/src/dom/createelement'; import createViewRoot from '../_utils/createroot'; import { setData as setViewData } from '../../../src/dev-utils/view'; import testUtils from '@ckeditor/ckeditor5-core/tests/_utils/utils'; +import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'View', () => { let view, viewDocument, domRoot, domSelection, viewRoot, foo, bar, ui, ui2; + let stylesProcessor; function createUIElement( name, contents ) { const element = new UIElement( viewDocument, name ); @@ -33,13 +35,17 @@ describe( 'View', () => { return element; } + before( () => { + stylesProcessor = new StylesProcessor(); + } ); + beforeEach( () => { domRoot = createElement( document, 'div', { contenteditable: 'true' } ); document.body.appendChild( domRoot ); - view = new View(); + view = new View( stylesProcessor ); viewDocument = view.document; viewRoot = createViewRoot( viewDocument ); view.attachDomRoot( domRoot ); diff --git a/tests/view/view/view.js b/tests/view/view/view.js index 1edd46276..cba26f6e9 100644 --- a/tests/view/view/view.js +++ b/tests/view/view/view.js @@ -97,7 +97,7 @@ describe( 'view', () => { const oldEnvIsAndroid = env.isAndroid; env.isAndroid = true; - const newView = new View(); + const newView = new View( stylesProcessor ); expect( newView.getObserver( InputObserver ) ).to.be.instanceof( InputObserver ); env.isAndroid = oldEnvIsAndroid; @@ -166,7 +166,7 @@ describe( 'view', () => { // The variable will be overwritten. view.destroy(); - view = new View(); + view = new View( stylesProcessor ); viewDocument = view.document; view._renderer.render = sinon.spy(); @@ -276,7 +276,7 @@ describe( 'view', () => { // The variable will be overwritten. view.destroy(); - view = new View(); + view = new View( stylesProcessor ); viewDocument = view.document; view._renderer.render = sinon.spy(); } ); @@ -565,7 +565,7 @@ describe( 'view', () => { createElement( document, 'p' ) ] ); - const view = new View(); + const view = new View( stylesProcessor ); const viewDocument = view.document; createViewRoot( viewDocument, 'div', 'main' ); @@ -582,7 +582,7 @@ describe( 'view', () => { it( 'should render changes in the Document', () => { const domDiv = document.createElement( 'div' ); - const view = new View(); + const view = new View( stylesProcessor ); const viewDocument = view.document; createViewRoot( viewDocument, 'div', 'main' ); view.attachDomRoot( domDiv ); @@ -599,7 +599,7 @@ describe( 'view', () => { it( 'should render attribute changes', () => { const domRoot = document.createElement( 'div' ); - const view = new View(); + const view = new View( stylesProcessor ); const viewDocument = view.document; const viewRoot = createViewRoot( viewDocument, 'div', 'main' ); From d431e83fb22014ae1e5f399fef2e4de187962ade Mon Sep 17 00:00:00 2001 From: Kamil Piechaczek Date: Thu, 20 Feb 2020 14:57:23 +0100 Subject: [PATCH 21/34] Simplified the code. --- src/dev-utils/view.js | 7 +------ 1 file changed, 1 insertion(+), 6 deletions(-) diff --git a/src/dev-utils/view.js b/src/dev-utils/view.js index 30307ae55..a6293a5b7 100644 --- a/src/dev-utils/view.js +++ b/src/dev-utils/view.js @@ -331,12 +331,7 @@ export function stringify( node, selectionOrPositionOrRange = null, options = {} * to parse. */ export function parse( data, options = {} ) { - if ( !options.stylesProcessor ) { - // console.log( 'Missing "stylesProcessor". parse()' ); - options.stylesProcessor = new StylesProcessor(); - } - - const stylesProcessor = options.stylesProcessor; + const stylesProcessor = new StylesProcessor(); options.order = options.order || []; const rangeParser = new RangeParser( { From 066db206aff6c19f79de3ba0e411ae75a056a8b7 Mon Sep 17 00:00:00 2001 From: Kamil Piechaczek Date: Mon, 24 Feb 2020 16:17:44 +0100 Subject: [PATCH 22/34] Requested changes during the review. --- src/controller/datacontroller.js | 20 +++++- src/conversion/downcasthelpers.js | 10 +-- src/dataprocessor/htmldataprocessor.js | 18 ++--- src/dataprocessor/xmldataprocessor.js | 18 ++--- src/dev-utils/view.js | 10 ++- src/model/model.js | 2 +- src/view/document.js | 16 ----- src/view/domconverter.js | 27 +++++--- src/view/element.js | 6 +- src/view/observer/mutationobserver.js | 4 +- src/view/renderer.js | 2 +- src/view/styles/background.js | 2 +- src/view/styles/border.js | 2 +- src/view/styles/margin.js | 2 +- src/view/styles/padding.js | 2 +- src/view/stylesmap.js | 12 ++-- src/view/uielement.js | 6 +- src/view/view.js | 2 +- tests/controller/datacontroller.js | 25 ++++--- tests/conversion/downcasthelpers.js | 15 +++-- tests/dataprocessor/htmldataprocessor.js | 7 +- tests/dataprocessor/xmldataprocessor.js | 9 +-- tests/view/document.js | 11 --- tests/view/domconverter/binding.js | 27 ++++---- tests/view/domconverter/dom-to-view.js | 86 ++++++++++++------------ tests/view/domconverter/domconverter.js | 18 +++-- tests/view/domconverter/uielement.js | 17 ++--- tests/view/domconverter/view-to-dom.js | 4 +- tests/view/observer/domeventdata.js | 2 +- tests/view/renderer.js | 4 +- tests/view/upcastwriter.js | 6 +- 31 files changed, 181 insertions(+), 211 deletions(-) diff --git a/src/controller/datacontroller.js b/src/controller/datacontroller.js index c14b007d4..d7b2c2199 100644 --- a/src/controller/datacontroller.js +++ b/src/controller/datacontroller.js @@ -46,12 +46,12 @@ export default class DataController { /** * Creates a data controller instance. * - * @param {module:engine/model/model~Model} model Data model. * @param {module:engine/view/stylesmap~StylesProcessor} stylesProcessor Styles processor. + * @param {module:engine/model/model~Model} model Data model. * @param {module:engine/dataprocessor/dataprocessor~DataProcessor} [dataProcessor] Data processor that should be used * by the controller. */ - constructor( model, stylesProcessor, dataProcessor ) { + constructor( stylesProcessor, model, dataProcessor ) { /** * Data model. * @@ -381,6 +381,22 @@ export default class DataController { } ); } + /** + * Adds a style processor normalization rules. + * + * The available style processors: + * + * * background: {@link module:engine/view/styles/background~addBackgroundRules} + * * border: {@link module:engine/view/styles/border~addBorderRules} + * * margin: {@link module:engine/view/styles/margin~addMarginRules} + * * padding: {@link module:engine/view/styles/padding~addPaddingRules} + * + * @param {Function} callback + */ + addStyleProcessorRules( callback ) { + callback( this.stylesProcessor ); + } + /** * Removes all event listeners set by the DataController. */ diff --git a/src/conversion/downcasthelpers.js b/src/conversion/downcasthelpers.js index 4e3202ab5..d80e1a4ee 100644 --- a/src/conversion/downcasthelpers.js +++ b/src/conversion/downcasthelpers.js @@ -416,12 +416,12 @@ export function remove() { * provided by the {@link module:engine/conversion/downcasthelpers~HighlightDescriptor highlight descriptor} object. If a priority * is not provided in the descriptor, the default priority will be used. * - * @param {module:engine/view/document~Document} document + * @param {module:engine/view/downcastwriter~DowncastWriter} writer * @param {module:engine/conversion/downcasthelpers~HighlightDescriptor} descriptor * @returns {module:engine/view/attributeelement~AttributeElement} */ -export function createViewElementFromHighlightDescriptor( document, descriptor ) { - const viewElement = new ViewAttributeElement( document, 'span', descriptor.attributes ); +export function createViewElementFromHighlightDescriptor( writer, descriptor ) { + const viewElement = writer.createAttributeElement( 'span', descriptor.attributes ); if ( descriptor.classes ) { viewElement._addClass( descriptor.classes ); @@ -921,7 +921,7 @@ function highlightText( highlightDescriptor ) { } const viewWriter = conversionApi.writer; - const viewElement = createViewElementFromHighlightDescriptor( viewWriter.document, descriptor ); + const viewElement = createViewElementFromHighlightDescriptor( viewWriter, descriptor ); const viewSelection = viewWriter.document.selection; if ( data.item instanceof ModelSelection || data.item instanceof DocumentSelection ) { @@ -1035,7 +1035,7 @@ function removeHighlight( highlightDescriptor ) { } // View element that will be used to unwrap `AttributeElement`s. - const viewHighlightElement = createViewElementFromHighlightDescriptor( conversionApi.writer.document, descriptor ); + const viewHighlightElement = createViewElementFromHighlightDescriptor( conversionApi.writer, descriptor ); // Get all elements bound with given marker name. const elements = conversionApi.mapper.markerNameToElements( data.markerName ); diff --git a/src/dataprocessor/htmldataprocessor.js b/src/dataprocessor/htmldataprocessor.js index cc6c4069b..88bb69710 100644 --- a/src/dataprocessor/htmldataprocessor.js +++ b/src/dataprocessor/htmldataprocessor.js @@ -11,7 +11,6 @@ import BasicHtmlWriter from './basichtmlwriter'; import DomConverter from '../view/domconverter'; -import ViewDocument from '../view/document'; /** * The HTML data processor class. @@ -23,17 +22,9 @@ export default class HtmlDataProcessor { /** * Creates a new instance of the HTML data processor class. * - * @param {module:engine/view/stylesmap~StylesProcessor} stylesProcessor Styles processor. + * @param {module:engine/view/document~Document} document */ - constructor( stylesProcessor ) { - /** - * Styles processor. - * - * @readonly - * @member {module:engine/view/stylesmap~StylesProcessor} - */ - this.stylesProcessor = stylesProcessor; - + constructor( document ) { /** * A DOM parser instance used to parse an HTML string to an HTML document. * @@ -48,7 +39,7 @@ export default class HtmlDataProcessor { * @private * @member {module:engine/view/domconverter~DomConverter} */ - this._domConverter = new DomConverter( { blockFillerMode: 'nbsp' } ); + this._domConverter = new DomConverter( document, { blockFillerMode: 'nbsp' } ); /** * A basic HTML writer instance used to convert DOM elements to an HTML string. @@ -83,10 +74,9 @@ export default class HtmlDataProcessor { toView( data ) { // Convert input HTML data to DOM DocumentFragment. const domFragment = this._toDom( data ); - const viewDocument = new ViewDocument( this.stylesProcessor ); // Convert DOM DocumentFragment to view DocumentFragment. - return this._domConverter.domToView( viewDocument, domFragment ); + return this._domConverter.domToView( domFragment ); } /** diff --git a/src/dataprocessor/xmldataprocessor.js b/src/dataprocessor/xmldataprocessor.js index 96f64d88a..63e0dca22 100644 --- a/src/dataprocessor/xmldataprocessor.js +++ b/src/dataprocessor/xmldataprocessor.js @@ -11,7 +11,6 @@ import BasicHtmlWriter from './basichtmlwriter'; import DomConverter from '../view/domconverter'; -import ViewDocument from '../view/document'; /** * The XML data processor class. @@ -25,19 +24,11 @@ export default class XmlDataProcessor { /** * Creates a new instance of the XML data processor class. * - * @param {module:engine/view/stylesmap~StylesProcessor} stylesProcessor Styles processor. + * @param {module:engine/view/document~Document} document * @param {Object} options Configuration options. * @param {Array} [options.namespaces=[]] A list of namespaces allowed to use in the XML input. */ - constructor( stylesProcessor, options = {} ) { - /** - * Styles processor. - * - * @readonly - * @member {module:engine/view/stylesmap~StylesProcessor} - */ - this.stylesProcessor = stylesProcessor; - + constructor( document, options = {} ) { /** * A list of namespaces allowed to use in the XML input. * @@ -63,7 +54,7 @@ export default class XmlDataProcessor { * @private * @member {module:engine/view/domconverter~DomConverter} */ - this._domConverter = new DomConverter( { blockFillerMode: 'nbsp' } ); + this._domConverter = new DomConverter( document, { blockFillerMode: 'nbsp' } ); /** * A basic HTML writer instance used to convert DOM elements to an XML string. @@ -100,10 +91,9 @@ export default class XmlDataProcessor { toView( data ) { // Convert input XML data to DOM DocumentFragment. const domFragment = this._toDom( data ); - const viewDocument = new ViewDocument( this.stylesProcessor ); // Convert DOM DocumentFragment to view DocumentFragment. - return this._domConverter.domToView( viewDocument, domFragment, { keepOriginalCase: true } ); + return this._domConverter.domToView( domFragment, { keepOriginalCase: true } ); } /** diff --git a/src/dev-utils/view.js b/src/dev-utils/view.js index a6293a5b7..38629c7a0 100644 --- a/src/dev-utils/view.js +++ b/src/dev-utils/view.js @@ -14,6 +14,7 @@ */ import View from '../view/view'; +import ViewDocument from '../view/document'; import ViewDocumentFragment from '../view/documentfragment'; import XmlDataProcessor from '../dataprocessor/xmldataprocessor'; import ViewElement from '../view/element'; @@ -99,10 +100,7 @@ export function setData( view, data, options = {} ) { const root = document.getRoot( rootName ); view.change( writer => { - const result = setData._parse( data, { - rootElement: root, - stylesProcessor: document.stylesProcessor - } ); + const result = setData._parse( data, { rootElement: root } ); if ( result.view && result.selection ) { writer.setSelection( result.selection ); @@ -331,13 +329,13 @@ export function stringify( node, selectionOrPositionOrRange = null, options = {} * to parse. */ export function parse( data, options = {} ) { - const stylesProcessor = new StylesProcessor(); + const viewDocument = new ViewDocument( new StylesProcessor() ); options.order = options.order || []; const rangeParser = new RangeParser( { sameSelectionCharacters: options.sameSelectionCharacters } ); - const processor = new XmlDataProcessor( stylesProcessor, { + const processor = new XmlDataProcessor( viewDocument, { namespaces: Object.keys( allowedTypes ) } ); diff --git a/src/model/model.js b/src/model/model.js index f20a40f8d..79c8d7761 100644 --- a/src/model/model.js +++ b/src/model/model.js @@ -334,7 +334,7 @@ export default class Model { * * // You can create your own HtmlDataProcessor instance or use editor.data.processor * // if you have not overridden the default one (which is the HtmlDataProcessor instance). - * const htmlDP = new HtmlDataProcessor( new StylesProcessor() ); + * const htmlDP = new HtmlDataProcessor( viewDocument ); * * // Convert an HTML string to a view document fragment: * const viewFragment = htmlDP.toView( htmlString ); diff --git a/src/view/document.js b/src/view/document.js index 43159a6ec..975ab1a30 100644 --- a/src/view/document.js +++ b/src/view/document.js @@ -170,22 +170,6 @@ export default class Document { this.stopListening(); } - /** - * Adds a style processor normalization rules. - * - * The available style processors: - * - * * background: {@link module:engine/view/styles/background~addBackgroundRules} - * * border: {@link module:engine/view/styles/border~addBorderRules} - * * margin: {@link module:engine/view/styles/margin~addMarginRules} - * * padding: {@link module:engine/view/styles/padding~addPaddingRules} - * - * @param {Function} callback - */ - addStyleProcessorRules( callback ) { - callback( this.stylesProcessor ); - } - /** * Performs post-fixer loops. Executes post-fixer callbacks as long as none of them has done any changes to the model. * diff --git a/src/view/domconverter.js b/src/view/domconverter.js index 996517fad..51656ff92 100644 --- a/src/view/domconverter.js +++ b/src/view/domconverter.js @@ -44,10 +44,17 @@ export default class DomConverter { /** * Creates DOM converter. * + * @param {module:engine/view/document~Document} document * @param {Object} options Object with configuration options. * @param {module:engine/view/filler~BlockFillerMode} [options.blockFillerMode='br'] The type of the block filler to use. */ - constructor( options = {} ) { + constructor( document, options = {} ) { + /** + * @readonly + * @type {module:engine/view/document~Document} + */ + this.document = document; + /** * The mode of a block filler used by DOM converter. * @@ -373,7 +380,6 @@ export default class DomConverter { * {@link module:engine/view/filler fillers} `null` will be returned. * For all DOM elements rendered by {@link module:engine/view/uielement~UIElement} that UIElement will be returned. * - * @param {module:engine/view/document~Document} viewDocument View document where the created node will belong to. * @param {Node|DocumentFragment} domNode DOM node or document fragment to transform. * @param {Object} [options] Conversion options. * @param {Boolean} [options.bind=false] Determines whether new elements will be bound. @@ -382,7 +388,7 @@ export default class DomConverter { * @returns {module:engine/view/node~Node|module:engine/view/documentfragment~DocumentFragment|null} Converted node or document fragment * or `null` if DOM node is a {@link module:engine/view/filler filler} or the given node is an empty text node. */ - domToView( viewDocument, domNode, options = {} ) { + domToView( domNode, options = {} ) { if ( this.isBlockFiller( domNode, this.blockFillerMode ) ) { return null; } @@ -400,7 +406,7 @@ export default class DomConverter { } else { const textData = this._processDataFromDomText( domNode ); - return textData === '' ? null : new ViewText( viewDocument, textData ); + return textData === '' ? null : new ViewText( this.document, textData ); } } else if ( this.isComment( domNode ) ) { return null; @@ -413,7 +419,7 @@ export default class DomConverter { if ( this.isDocumentFragment( domNode ) ) { // Create view document fragment. - viewElement = new ViewDocumentFragment( viewDocument ); + viewElement = new ViewDocumentFragment( this.document ); if ( options.bind ) { this.bindDocumentFragments( domNode, viewElement ); @@ -421,7 +427,7 @@ export default class DomConverter { } else { // Create view element. const viewName = options.keepOriginalCase ? domNode.tagName : domNode.tagName.toLowerCase(); - viewElement = new ViewElement( viewDocument, viewName ); + viewElement = new ViewElement( this.document, viewName ); if ( options.bind ) { this.bindElements( domNode, viewElement ); @@ -436,7 +442,7 @@ export default class DomConverter { } if ( options.withChildren || options.withChildren === undefined ) { - for ( const child of this.domChildrenToView( viewDocument, domNode, options ) ) { + for ( const child of this.domChildrenToView( domNode, options ) ) { viewElement._appendChild( child ); } } @@ -450,15 +456,14 @@ export default class DomConverter { * the {@link module:engine/view/domconverter~DomConverter#domToView} method. * Additionally this method omits block {@link module:engine/view/filler filler}, if it exists in the DOM parent. * - * @param {module:engine/view/document~Document} viewDocument View document where the created node will belong to. * @param {HTMLElement} domElement Parent DOM element. * @param {Object} options See {@link module:engine/view/domconverter~DomConverter#domToView} options parameter. * @returns {Iterable.} View nodes. */ - * domChildrenToView( viewDocument, domElement, options = {} ) { + * domChildrenToView( domElement, options = {} ) { for ( let i = 0; i < domElement.childNodes.length; i++ ) { const domChild = domElement.childNodes[ i ]; - const viewChild = this.domToView( viewDocument, domChild, options ); + const viewChild = this.domToView( domChild, options ); if ( viewChild !== null ) { yield viewChild; @@ -802,7 +807,7 @@ export default class DomConverter { /** * Checks if the node is an instance of the block filler for this DOM converter. * - * const converter = new DomConverter( { blockFillerMode: 'br' } ); + * const converter = new DomConverter( viewDocument, { blockFillerMode: 'br' } ); * * converter.isBlockFiller( BR_FILLER( document ) ); // true * converter.isBlockFiller( NBSP_FILLER( document ) ); // false diff --git a/src/view/element.js b/src/view/element.js index aba080731..c5db76a24 100644 --- a/src/view/element.js +++ b/src/view/element.js @@ -387,7 +387,7 @@ export default class Element extends Node { * For an element with style set to `'margin:1px'`: * * // Enable 'margin' shorthand processing: - * editor.editing.view.document.addStyleProcessorRules( addMarginRules ); + * editor.data.addStyleProcessorRules( addMarginRules ); * * const element = view.change( writer => { * const element = writer.createElement(); @@ -667,6 +667,10 @@ export default class Element extends Node { if ( key == 'class' ) { parseClasses( this._classes, value ); } else if ( key == 'style' ) { + // if (!this._styles ) { + // debugger; + // } + this._styles.setTo( value ); } else { this._attrs.set( key, value ); diff --git a/src/view/observer/mutationobserver.js b/src/view/observer/mutationobserver.js index 17f365fa7..44cd39af1 100644 --- a/src/view/observer/mutationobserver.js +++ b/src/view/observer/mutationobserver.js @@ -206,7 +206,7 @@ export default class MutationObserver extends Observer { for ( const viewElement of mutatedElements ) { const domElement = domConverter.mapViewToDom( viewElement ); const viewChildren = Array.from( viewElement.getChildren() ); - const newViewChildren = Array.from( domConverter.domChildrenToView( this.document, domElement, { withChildren: false } ) ); + const newViewChildren = Array.from( domConverter.domChildrenToView( domElement, { withChildren: false } ) ); // It may happen that as a result of many changes (sth was inserted and then removed), // both elements haven't really changed. #1031 @@ -287,7 +287,7 @@ export default class MutationObserver extends Observer { // Check if mutation added only one node on the end of its parent. if ( mutation.nextSibling === null && mutation.removedNodes.length === 0 && mutation.addedNodes.length == 1 ) { - addedNode = this.domConverter.domToView( this.document, mutation.addedNodes[ 0 ], { + addedNode = this.domConverter.domToView( mutation.addedNodes[ 0 ], { withChildren: false } ); } diff --git a/src/view/renderer.js b/src/view/renderer.js index 26aa16fbc..8f7ceebc8 100644 --- a/src/view/renderer.js +++ b/src/view/renderer.js @@ -564,7 +564,7 @@ export default class Renderer { remove( actualDomChildren[ i ] ); } else { // 'equal' // Force updating text nodes inside elements which did not change and do not need to be re-rendered (#1125). - this._markDescendantTextToSync( this.domConverter.domToView( this._viewDocument, expectedDomChildren[ i ] ) ); + this._markDescendantTextToSync( this.domConverter.domToView( expectedDomChildren[ i ] ) ); i++; } } diff --git a/src/view/styles/background.js b/src/view/styles/background.js index 3d5d49285..0974ef044 100644 --- a/src/view/styles/background.js +++ b/src/view/styles/background.js @@ -12,7 +12,7 @@ import { getShorthandValues, isAttachment, isColor, isPosition, isRepeat, isURL /** * Adds a background CSS styles processing rules. * - * editor.editing.view.document.addStyleProcessorRules( addBackgroundRules ); + * editor.data.addStyleProcessorRules( addBackgroundRules ); * * The normalized value is stored as: * diff --git a/src/view/styles/border.js b/src/view/styles/border.js index b044d9fbb..c8ecb87e8 100644 --- a/src/view/styles/border.js +++ b/src/view/styles/border.js @@ -12,7 +12,7 @@ import { getShorthandValues, getBoxSidesValueReducer, getBoxSidesValues, isLengt /** * Adds a border CSS styles processing rules. * - * editor.editing.view.document.addStyleProcessorRules( addBorderRules ); + * editor.data.addStyleProcessorRules( addBorderRules ); * * This rules merges all [border](https://developer.mozilla.org/en-US/docs/Web/CSS/border) styles notation shorthands: * diff --git a/src/view/styles/margin.js b/src/view/styles/margin.js index b308fbd64..740d2552f 100644 --- a/src/view/styles/margin.js +++ b/src/view/styles/margin.js @@ -12,7 +12,7 @@ import { getPositionShorthandNormalizer, getBoxSidesValueReducer } from './utils /** * Adds a margin CSS styles processing rules. * - * editor.editing.view.document.addStyleProcessorRules( addMarginRules ); + * editor.data.addStyleProcessorRules( addMarginRules ); * * The normalized value is stored as: * diff --git a/src/view/styles/padding.js b/src/view/styles/padding.js index 0a906e6d6..a5709e3a2 100644 --- a/src/view/styles/padding.js +++ b/src/view/styles/padding.js @@ -12,7 +12,7 @@ import { getPositionShorthandNormalizer, getBoxSidesValueReducer } from './utils /** * Adds a margin CSS styles processing rules. * - * editor.editing.view.document.addStyleProcessorRules( addPaddingRules ); + * editor.data.addStyleProcessorRules( addPaddingRules ); * * The normalized value is stored as: * diff --git a/src/view/stylesmap.js b/src/view/stylesmap.js index 4b877c3fe..63f6c62bd 100644 --- a/src/view/stylesmap.js +++ b/src/view/stylesmap.js @@ -94,7 +94,7 @@ export default class StylesMap { * **Note**: This check supports normalized style names. * * // Enable 'margin' shorthand processing: - * editor.editing.view.document.addStyleProcessorRules( addMarginRules ); + * editor.data.addStyleProcessorRules( addMarginRules ); * * styles.setTo( 'margin:2px;' ); * @@ -143,7 +143,7 @@ export default class StylesMap { * to normalize passed values. * * // Enable 'margin' shorthand processing: - * editor.editing.view.document.addStyleProcessorRules( addMarginRules ); + * editor.data.addStyleProcessorRules( addMarginRules ); * * styles.set( 'margin', '2px' ); * @@ -196,7 +196,7 @@ export default class StylesMap { * to normalize passed values. * * // Enable 'margin' shorthand processing: - * editor.editing.view.document.addStyleProcessorRules( addMarginRules ); + * editor.data.addStyleProcessorRules( addMarginRules ); * * styles.setTo( 'margin:1px' ); * @@ -220,7 +220,7 @@ export default class StylesMap { * Returns a normalized style object or a single value. * * // Enable 'margin' shorthand processing: - * editor.editing.view.document.addStyleProcessorRules( addMarginRules ); + * editor.data.addStyleProcessorRules( addMarginRules ); * * const styles = new Styles(); * styles.setTo( 'margin:1px 2px 3em;' ); @@ -256,7 +256,7 @@ export default class StylesMap { * **Note**: This method supports normalized styles if defined. * * // Enable 'margin' shorthand processing: - * editor.editing.view.document.addStyleProcessorRules( addMarginRules ); + * editor.data.addStyleProcessorRules( addMarginRules ); * * styles.set( 'margin' , '1px' ); * styles.set( 'background', '#f00' ); @@ -282,7 +282,7 @@ export default class StylesMap { * Returns property as a value string or undefined if property is not set. * * // Enable 'margin' shorthand processing: - * editor.editing.view.document.addStyleProcessorRules( addMarginRules ); + * editor.data.addStyleProcessorRules( addMarginRules ); * * const styles = new Styles(); * styles.setTo( 'margin:1px;' ); diff --git a/src/view/uielement.js b/src/view/uielement.js index fd5ee27c3..a4c5e40f2 100644 --- a/src/view/uielement.js +++ b/src/view/uielement.js @@ -43,12 +43,12 @@ export default class UIElement extends Element { * @protected * @param {module:engine/view/document~Document} document A document where the element belongs to. * @param {String} name Node name. - * @param {Object|Iterable} [attrs] Collection of attributes. + * @param {Object|Iterable} [attributes] Collection of attributes. * @param {module:engine/view/node~Node|Iterable.} [children] * A list of nodes to be inserted into created element. */ - constructor( document, name, attrs, children ) { - super( document, name, attrs, children ); + constructor( document, name, attributes, children ) { + super( document, name, attributes, children ); /** * Returns `null` because filler is not needed for UIElements. diff --git a/src/view/view.js b/src/view/view.js index 4d4f004b3..d57993c8b 100644 --- a/src/view/view.js +++ b/src/view/view.js @@ -82,7 +82,7 @@ export default class View { * @readonly * @type {module:engine/view/domconverter~DomConverter} */ - this.domConverter = new DomConverter(); + this.domConverter = new DomConverter( this.document ); /** * Roots of the DOM tree. Map on the `HTMLElement`s with roots names as keys. diff --git a/tests/controller/datacontroller.js b/tests/controller/datacontroller.js index a93fc16b8..419c0c778 100644 --- a/tests/controller/datacontroller.js +++ b/tests/controller/datacontroller.js @@ -24,14 +24,10 @@ import { expectToThrowCKEditorError } from '@ckeditor/ckeditor5-utils/tests/_uti import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'DataController', () => { - let model, modelDocument, htmlDataProcessor, data, schema, upcastHelpers, downcastHelpers, viewDocument; - let stylesProcessor; - - before( () => { - stylesProcessor = new StylesProcessor(); - } ); + let model, modelDocument, htmlDataProcessor, data, schema, upcastHelpers, downcastHelpers, viewDocument, stylesProcessor; beforeEach( () => { + stylesProcessor = new StylesProcessor(); model = new Model(); schema = model.schema; @@ -42,10 +38,10 @@ describe( 'DataController', () => { schema.register( '$title', { inheritAllFrom: '$root' } ); - htmlDataProcessor = new HtmlDataProcessor( stylesProcessor ); viewDocument = new ViewDocument( stylesProcessor ); + htmlDataProcessor = new HtmlDataProcessor( viewDocument ); - data = new DataController( model, stylesProcessor, htmlDataProcessor ); + data = new DataController( stylesProcessor, model, htmlDataProcessor ); upcastHelpers = new UpcastHelpers( [ data.upcastDispatcher ] ); downcastHelpers = new DowncastHelpers( [ data.downcastDispatcher ] ); @@ -53,7 +49,7 @@ describe( 'DataController', () => { describe( 'constructor()', () => { it( 'works without data processor', () => { - const data = new DataController( model, stylesProcessor ); + const data = new DataController( stylesProcessor, model ); expect( data.processor ).to.be.undefined; } ); @@ -577,4 +573,15 @@ describe( 'DataController', () => { expect( data ).to.respondTo( 'destroy' ); } ); } ); + + describe( 'addStyleProcessorRules()', () => { + it( 'should execute callback with an instance of StyleProcessor as the first argument', () => { + const spy = sinon.spy(); + + data.addStyleProcessorRules( spy ); + + sinon.assert.calledOnce( spy ); + sinon.assert.calledWithExactly( spy, stylesProcessor ); + } ); + } ); } ); diff --git a/tests/conversion/downcasthelpers.js b/tests/conversion/downcasthelpers.js index 5fd0405eb..5b16d03d4 100644 --- a/tests/conversion/downcasthelpers.js +++ b/tests/conversion/downcasthelpers.js @@ -36,6 +36,7 @@ import createViewRoot from '../view/_utils/createroot'; import { setData as setModelData } from '../../src/dev-utils/model'; import { expectToThrowCKEditorError } from '@ckeditor/ckeditor5-utils/tests/_utils/utils'; import { StylesProcessor } from '../../src/view/stylesmap'; +import DowncastWriter from '../../src/view/downcastwriter'; describe( 'DowncastHelpers', () => { let model, modelRoot, viewRoot, downcastHelpers, controller; @@ -1704,10 +1705,10 @@ describe( 'downcast converters', () => { } ); describe( 'createViewElementFromHighlightDescriptor()', () => { - let viewDocument; + let viewWriter; beforeEach( () => { - viewDocument = new ViewDocument( stylesProcessor ); + viewWriter = new DowncastWriter( controller.view.document ); } ); it( 'should return attribute element from descriptor object', () => { @@ -1716,7 +1717,7 @@ describe( 'downcast converters', () => { attributes: { one: '1', two: '2' }, priority: 7 }; - const element = createViewElementFromHighlightDescriptor( viewDocument, descriptor ); + const element = createViewElementFromHighlightDescriptor( viewWriter, descriptor ); expect( element.is( 'attributeElement' ) ).to.be.true; expect( element.name ).to.equal( 'span' ); @@ -1734,7 +1735,7 @@ describe( 'downcast converters', () => { attributes: { one: '1', two: '2' }, priority: 7 }; - const element = createViewElementFromHighlightDescriptor( viewDocument, descriptor ); + const element = createViewElementFromHighlightDescriptor( viewWriter, descriptor ); expect( element.is( 'attributeElement' ) ).to.be.true; expect( element.name ).to.equal( 'span' ); @@ -1752,7 +1753,7 @@ describe( 'downcast converters', () => { attributes: { one: '1', two: '2' }, priority: 7 }; - const element = createViewElementFromHighlightDescriptor( viewDocument, descriptor ); + const element = createViewElementFromHighlightDescriptor( viewWriter, descriptor ); expect( element.is( 'attributeElement' ) ).to.be.true; expect( element.name ).to.equal( 'span' ); @@ -1768,7 +1769,7 @@ describe( 'downcast converters', () => { classes: 'foo-class', attributes: { one: '1', two: '2' } }; - const element = createViewElementFromHighlightDescriptor( viewDocument, descriptor ); + const element = createViewElementFromHighlightDescriptor( viewWriter, descriptor ); expect( element.is( 'attributeElement' ) ).to.be.true; expect( element.name ).to.equal( 'span' ); @@ -1785,7 +1786,7 @@ describe( 'downcast converters', () => { classes: 'foo-class', priority: 7 }; - const element = createViewElementFromHighlightDescriptor( viewDocument, descriptor ); + const element = createViewElementFromHighlightDescriptor( viewWriter, descriptor ); expect( element.is( 'attributeElement' ) ).to.be.true; expect( element.name ).to.equal( 'span' ); diff --git a/tests/dataprocessor/htmldataprocessor.js b/tests/dataprocessor/htmldataprocessor.js index 1684742fc..475babd9e 100644 --- a/tests/dataprocessor/htmldataprocessor.js +++ b/tests/dataprocessor/htmldataprocessor.js @@ -13,13 +13,12 @@ import { StylesProcessor } from '../../src/view/stylesmap'; import ViewDocument from '../../src/view/document'; describe( 'HtmlDataProcessor', () => { - const stylesProcessor = new StylesProcessor(); - const dataProcessor = new HtmlDataProcessor( stylesProcessor ); - - let viewDocument; + let stylesProcessor, dataProcessor, viewDocument; beforeEach( () => { + stylesProcessor = new StylesProcessor(); viewDocument = new ViewDocument( stylesProcessor ); + dataProcessor = new HtmlDataProcessor( viewDocument ); } ); describe( 'toView()', () => { diff --git a/tests/dataprocessor/xmldataprocessor.js b/tests/dataprocessor/xmldataprocessor.js index bd5bf4c7f..18764bc08 100644 --- a/tests/dataprocessor/xmldataprocessor.js +++ b/tests/dataprocessor/xmldataprocessor.js @@ -15,13 +15,10 @@ import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'XmlDataProcessor', () => { let stylesProcessor, dataProcessor, viewDocument; - before( () => { - stylesProcessor = new StylesProcessor(); - } ); - beforeEach( () => { - dataProcessor = new XmlDataProcessor( stylesProcessor ); + stylesProcessor = new StylesProcessor(); viewDocument = new ViewDocument( stylesProcessor ); + dataProcessor = new XmlDataProcessor( viewDocument ); } ); describe( 'toView', () => { @@ -50,7 +47,7 @@ describe( 'XmlDataProcessor', () => { } ); it( 'should allow to use registered namespaces', () => { - dataProcessor = new XmlDataProcessor( stylesProcessor, { + dataProcessor = new XmlDataProcessor( viewDocument, { namespaces: [ 'foo', 'bar' ] } ); diff --git a/tests/view/document.js b/tests/view/document.js index de432ae6b..1504d1c0b 100644 --- a/tests/view/document.js +++ b/tests/view/document.js @@ -96,15 +96,4 @@ describe( 'Document', () => { expect( calls ).to.equal( 4 ); } ); } ); - - describe( 'addStyleProcessorRules()', () => { - it( 'should execute callback with an instance of StyleProcessor as the first argument', () => { - const spy = sinon.spy(); - - viewDocument.addStyleProcessorRules( spy ); - - sinon.assert.calledOnce( spy ); - sinon.assert.calledWithExactly( spy, viewDocument.stylesProcessor ); - } ); - } ); } ); diff --git a/tests/view/domconverter/binding.js b/tests/view/domconverter/binding.js index 3e38f3e0f..d5094e89c 100644 --- a/tests/view/domconverter/binding.js +++ b/tests/view/domconverter/binding.js @@ -20,11 +20,10 @@ import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'DomConverter', () => { let converter, viewDocument, stylesProcessor; - before( () => { - converter = new DomConverter(); + beforeEach( () => { stylesProcessor = new StylesProcessor(); - viewDocument = new ViewDocument( stylesProcessor ); + converter = new DomConverter( viewDocument ); } ); describe( 'bindElements()', () => { @@ -63,7 +62,7 @@ describe( 'DomConverter', () => { it( 'should return corresponding view document fragment', () => { const domFragment = document.createDocumentFragment(); - const viewFragment = converter.domToView( viewDocument, domFragment ); + const viewFragment = converter.domToView( domFragment ); converter.bindElements( domFragment, viewFragment ); @@ -86,7 +85,7 @@ describe( 'DomConverter', () => { converter.bindElements( domImg, viewImg ); - const viewP = converter.domToView( viewDocument, domP ); + const viewP = converter.domToView( domP ); const viewText = viewP.getChild( 1 ); expect( converter.findCorrespondingViewText( domText ) ).to.equal( viewText ); @@ -96,7 +95,7 @@ describe( 'DomConverter', () => { const domText = document.createTextNode( 'foo' ); const domP = createElement( document, 'p', null, domText ); - const viewP = converter.domToView( viewDocument, domP ); + const viewP = converter.domToView( domP ); const viewText = viewP.getChild( 0 ); converter.bindElements( domP, viewP ); @@ -109,7 +108,7 @@ describe( 'DomConverter', () => { const domText = document.createTextNode( 'foo' ); const domP = createElement( document, 'p', null, [ domImg, domText ] ); - const viewP = converter.domToView( viewDocument, domP ); + const viewP = converter.domToView( domP ); converter.bindElements( domP, viewP ); @@ -121,7 +120,7 @@ describe( 'DomConverter', () => { const domTextBar = document.createTextNode( 'bar' ); const domP = createElement( document, 'p', null, [ domTextFoo, domTextBar ] ); - const viewP = converter.domToView( viewDocument, domP ); + const viewP = converter.domToView( domP ); converter.bindElements( domP, viewP ); @@ -139,7 +138,7 @@ describe( 'DomConverter', () => { const domFiller = document.createTextNode( INLINE_FILLER ); const domP = createElement( document, 'p', null, domFiller ); - const viewP = converter.domToView( viewDocument, domP ); + const viewP = converter.domToView( domP ); converter.bindElements( domP, viewP ); @@ -212,7 +211,7 @@ describe( 'DomConverter', () => { converter.bindElements( domImg, viewImg ); - const viewP = converter.domToView( viewDocument, domP ); + const viewP = converter.domToView( domP ); const viewText = viewP.getChild( 1 ); expect( converter.findCorrespondingDomText( viewText ) ).to.equal( domText ); @@ -224,7 +223,7 @@ describe( 'DomConverter', () => { domP.appendChild( domText ); - const viewP = converter.domToView( viewDocument, domP ); + const viewP = converter.domToView( domP ); const viewText = viewP.getChild( 0 ); converter.bindElements( domP, viewP ); @@ -240,7 +239,7 @@ describe( 'DomConverter', () => { domP.appendChild( domImg ); domP.appendChild( domText ); - const viewP = converter.domToView( viewDocument, domP ); + const viewP = converter.domToView( domP ); const viewText = viewP.getChild( 1 ); converter.bindElements( domP, viewP ); @@ -254,7 +253,7 @@ describe( 'DomConverter', () => { domP.appendChild( domText ); - const viewP = converter.domToView( viewDocument, domP ); + const viewP = converter.domToView( domP ); const viewText = viewP.getChild( 0 ); expect( converter.findCorrespondingDomText( viewText ) ).to.be.null; @@ -262,7 +261,7 @@ describe( 'DomConverter', () => { it( 'should return null if there is no previous sibling and parent', () => { const domText = document.createTextNode( 'foo' ); - const viewText = converter.domToView( viewDocument, domText ); + const viewText = converter.domToView( domText ); expect( converter.findCorrespondingDomText( viewText ) ).to.be.null; } ); diff --git a/tests/view/domconverter/dom-to-view.js b/tests/view/domconverter/dom-to-view.js index c70c0b39c..43c57178b 100644 --- a/tests/view/domconverter/dom-to-view.js +++ b/tests/view/domconverter/dom-to-view.js @@ -21,9 +21,9 @@ describe( 'DomConverter', () => { let converter, viewDocument, stylesProcessor; before( () => { - converter = new DomConverter(); stylesProcessor = new StylesProcessor(); viewDocument = new ViewDocument( stylesProcessor ); + converter = new DomConverter( viewDocument ); } ); describe( 'domToView()', () => { @@ -36,7 +36,7 @@ describe( 'DomConverter', () => { converter.bindElements( domImg, viewImg ); - const viewP = converter.domToView( viewDocument, domP ); + const viewP = converter.domToView( domP ); expect( viewP ).to.be.an.instanceof( ViewElement ); expect( viewP.name ).to.equal( 'p' ); @@ -57,7 +57,7 @@ describe( 'DomConverter', () => { const domText = document.createTextNode( 'foo' ); const domP = createElement( document, 'p', { 'class': 'foo' }, [ domImg, domText ] ); - const viewP = converter.domToView( viewDocument, domP, { bind: true } ); + const viewP = converter.domToView( domP, { bind: true } ); expect( viewP ).to.be.an.instanceof( ViewElement ); expect( viewP.name ).to.equal( 'p' ); @@ -77,7 +77,7 @@ describe( 'DomConverter', () => { const domText = document.createTextNode( 'நிலைக்கு' ); const domP = createElement( document, 'p', { 'class': 'foo' }, [ domText ] ); - const viewP = converter.domToView( viewDocument, domP, { bind: true } ); + const viewP = converter.domToView( domP, { bind: true } ); expect( viewP.childCount ).to.equal( 1 ); @@ -97,7 +97,7 @@ describe( 'DomConverter', () => { converter.bindElements( domImg, viewImg ); - const viewP = converter.domToView( viewDocument, domP, { withChildren: false } ); + const viewP = converter.domToView( domP, { withChildren: false } ); expect( viewP ).to.be.an.instanceof( ViewElement ); expect( viewP.name ).to.equal( 'p' ); @@ -117,7 +117,7 @@ describe( 'DomConverter', () => { domFragment.appendChild( domImg ); domFragment.appendChild( domText ); - const viewFragment = converter.domToView( viewDocument, domFragment, { bind: true } ); + const viewFragment = converter.domToView( domFragment, { bind: true } ); expect( viewFragment ).to.be.an.instanceof( ViewDocumentFragment ); expect( viewFragment.childCount ).to.equal( 2 ); @@ -140,7 +140,7 @@ describe( 'DomConverter', () => { converter.bindElements( domImg, viewImg ); - const viewFragment = converter.domToView( viewDocument, domFragment, { withChildren: false } ); + const viewFragment = converter.domToView( domFragment, { withChildren: false } ); expect( viewFragment ).to.be.an.instanceof( ViewDocumentFragment ); @@ -154,7 +154,7 @@ describe( 'DomConverter', () => { converter.bindDocumentFragments( domFragment, viewFragment ); - const viewFragment2 = converter.domToView( viewDocument, domFragment ); + const viewFragment2 = converter.domToView( domFragment ); expect( viewFragment2 ).to.equal( viewFragment ); } ); @@ -163,19 +163,19 @@ describe( 'DomConverter', () => { // eslint-disable-next-line new-cap const domFiller = BR_FILLER( document ); - expect( converter.domToView( viewDocument, domFiller ) ).to.be.null; + expect( converter.domToView( domFiller ) ).to.be.null; } ); it( 'should return null for empty text node', () => { const textNode = document.createTextNode( '' ); - expect( converter.domToView( viewDocument, textNode ) ).to.be.null; + expect( converter.domToView( textNode ) ).to.be.null; } ); it( 'should return null for a comment', () => { const comment = document.createComment( 'abc' ); - expect( converter.domToView( viewDocument, comment ) ).to.be.null; + expect( converter.domToView( comment ) ).to.be.null; } ); describe( 'it should clear whitespaces', () => { @@ -190,7 +190,7 @@ describe( 'DomConverter', () => { ] ) ] ); - const viewDiv = converter.domToView( viewDocument, domDiv ); + const viewDiv = converter.domToView( domDiv ); expect( viewDiv.childCount ).to.equal( 2 ); expect( viewDiv.getChild( 0 ).getChild( 0 ).data ).to.equal( 'foo' ); @@ -208,7 +208,7 @@ describe( 'DomConverter', () => { document.createTextNode( ' ' ) ] ); - const viewDiv = converter.domToView( viewDocument, domDiv ); + const viewDiv = converter.domToView( domDiv ); expect( viewDiv.childCount ).to.equal( 2 ); expect( viewDiv.getChild( 0 ).getChild( 0 ).data ).to.equal( 'foo' ); @@ -223,7 +223,7 @@ describe( 'DomConverter', () => { document.createTextNode( ' ' ) ] ); - const viewDiv = converter.domToView( viewDocument, domDiv ); + const viewDiv = converter.domToView( domDiv ); expect( viewDiv.childCount ).to.equal( 1 ); expect( viewDiv.getChild( 0 ).getChild( 0 ).data ).to.equal( 'foo' ); @@ -237,7 +237,7 @@ describe( 'DomConverter', () => { document.createTextNode( '\n' ) ] ); - const viewDiv = converter.domToView( viewDocument, domDiv ); + const viewDiv = converter.domToView( domDiv ); expect( viewDiv.childCount ).to.equal( 1 ); expect( viewDiv.getChild( 0 ).getChild( 0 ).data ).to.equal( 'foo' ); @@ -251,7 +251,7 @@ describe( 'DomConverter', () => { document.createTextNode( '\r' ) ] ); - const viewDiv = converter.domToView( viewDocument, domDiv ); + const viewDiv = converter.domToView( domDiv ); expect( viewDiv.childCount ).to.equal( 1 ); expect( viewDiv.getChild( 0 ).getChild( 0 ).data ).to.equal( 'foo' ); @@ -265,7 +265,7 @@ describe( 'DomConverter', () => { document.createTextNode( '\t' ) ] ); - const viewDiv = converter.domToView( viewDocument, domDiv ); + const viewDiv = converter.domToView( domDiv ); expect( viewDiv.childCount ).to.equal( 1 ); expect( viewDiv.getChild( 0 ).getChild( 0 ).data ).to.equal( 'foo' ); @@ -283,7 +283,7 @@ describe( 'DomConverter', () => { ] ) ] ); - const viewDiv = converter.domToView( viewDocument, domDiv ); + const viewDiv = converter.domToView( domDiv ); expect( viewDiv.childCount ).to.equal( 2 ); expect( viewDiv.getChild( 0 ).getChild( 0 ).data ) @@ -300,7 +300,7 @@ describe( 'DomConverter', () => { ] ) ] ); - const viewDiv = converter.domToView( viewDocument, domDiv ); + const viewDiv = converter.domToView( domDiv ); expect( viewDiv.childCount ).to.equal( 1 ); expect( viewDiv.getChild( 0 ).getChild( 0 ).data ).to.equal( 'foo' ); @@ -314,7 +314,7 @@ describe( 'DomConverter', () => { ] ) ] ); - const viewDiv = converter.domToView( viewDocument, domDiv ); + const viewDiv = converter.domToView( domDiv ); expect( viewDiv.childCount ).to.equal( 1 ); expect( viewDiv.getChild( 0 ).getChild( 0 ).data ).to.equal( 'foo' ); @@ -327,7 +327,7 @@ describe( 'DomConverter', () => { document.createTextNode( ' bar' ) ] ); - const viewP = converter.domToView( viewDocument, domP ); + const viewP = converter.domToView( domP ); expect( viewP.childCount ).to.equal( 3 ); expect( viewP.getChild( 2 ).data ).to.equal( 'bar' ); @@ -340,7 +340,7 @@ describe( 'DomConverter', () => { document.createTextNode( ' \u00a0bar' ) ] ); - const viewP = converter.domToView( viewDocument, domP ); + const viewP = converter.domToView( domP ); expect( viewP.childCount ).to.equal( 3 ); expect( viewP.getChild( 2 ).data ).to.equal( ' bar' ); @@ -355,7 +355,7 @@ describe( 'DomConverter', () => { document.createTextNode( ' bar' ) ] ); - const viewP = converter.domToView( viewDocument, domP ); + const viewP = converter.domToView( domP ); expect( viewP.childCount ).to.equal( 3 ); expect( viewP.getChild( 2 ).data ).to.equal( 'bar' ); @@ -370,7 +370,7 @@ describe( 'DomConverter', () => { ] ) ] ); - const viewP = converter.domToView( viewDocument, domP ); + const viewP = converter.domToView( domP ); expect( viewP.childCount ).to.equal( 3 ); expect( viewP.getChild( 2 ).getChild( 0 ).data ).to.equal( 'bar' ); @@ -385,7 +385,7 @@ describe( 'DomConverter', () => { document.createTextNode( 'x' ) ] ); - const viewP = converter.domToView( viewDocument, domP ); + const viewP = converter.domToView( domP ); expect( viewP.childCount ).to.equal( 5 ); expect( viewP.getChild( 2 ).data ).to.equal( 'foo ' ); @@ -401,7 +401,7 @@ describe( 'DomConverter', () => { ] ) ] ); - const viewDiv = converter.domToView( viewDocument, domDiv ); + const viewDiv = converter.domToView( domDiv ); expect( viewDiv.getChild( 0 ).getChild( 0 ).data ).to.equal( 'f o o' ); expect( viewDiv.getChild( 1 ).getChild( 0 ).data ).to.equal( 'fo o' ); @@ -416,7 +416,7 @@ describe( 'DomConverter', () => { document.createTextNode( '\n\n \t\r\n' ) ] ); - const viewDiv = converter.domToView( viewDocument, domDiv ); + const viewDiv = converter.domToView( domDiv ); expect( viewDiv.childCount ).to.equal( 1 ); expect( viewDiv.getChild( 0 ).getChild( 0 ).data ).to.equal( 'f o o' ); @@ -434,7 +434,7 @@ describe( 'DomConverter', () => { domElement.appendChild( document.createTextNode( text.replace( /_/g, '\u00A0' ) ) ); } - const viewElement = converter.domToView( viewDocument, domElement ); + const viewElement = converter.domToView( domElement ); let data = ''; @@ -524,7 +524,7 @@ describe( 'DomConverter', () => { ] ) ] ); - const viewDiv = converter.domToView( viewDocument, domDiv ); + const viewDiv = converter.domToView( domDiv ); expect( viewDiv.getChild( 0 ).getChild( 0 ).data ).to.equal( ' foo\n foo ' ); } ); @@ -539,7 +539,7 @@ describe( 'DomConverter', () => { document.createTextNode( 'word' ) ] ); - const viewDiv = converter.domToView( viewDocument, domDiv ); + const viewDiv = converter.domToView( domDiv ); expect( viewDiv.getChild( 1 ).name ).to.equal( 'span' ); expect( viewDiv.getChild( 1 ).childCount ).to.equal( 1 ); @@ -556,7 +556,7 @@ describe( 'DomConverter', () => { document.createTextNode( 'word' ) ] ); - const viewDiv = converter.domToView( viewDocument, domDiv ); + const viewDiv = converter.domToView( domDiv ); expect( viewDiv.getChild( 1 ).name ).to.equal( 'span' ); expect( viewDiv.getChild( 1 ).childCount ).to.equal( 1 ); @@ -580,7 +580,7 @@ describe( 'DomConverter', () => { ] ) ] ); - const viewDiv = converter.domToView( viewDocument, domDiv ); + const viewDiv = converter.domToView( domDiv ); expect( viewDiv.getChild( 0 ).name ).to.equal( 'span' ); expect( viewDiv.getChild( 0 ).childCount ).to.equal( 2 ); @@ -598,7 +598,7 @@ describe( 'DomConverter', () => { createElement( document, 'br' ) ] ); - const viewP = converter.domToView( viewDocument, domP ); + const viewP = converter.domToView( domP ); expect( viewP.childCount ).to.equal( 2 ); expect( viewP.getChild( 0 ).data ).to.equal( 'foo ' ); @@ -610,7 +610,7 @@ describe( 'DomConverter', () => { createElement( document, 'br' ) ] ); - const viewP = converter.domToView( viewDocument, domP ); + const viewP = converter.domToView( domP ); expect( viewP.childCount ).to.equal( 2 ); expect( viewP.getChild( 0 ).data ).to.equal( 'foo ' ); @@ -622,7 +622,7 @@ describe( 'DomConverter', () => { createElement( document, 'br' ) ] ); - const viewP = converter.domToView( viewDocument, domP ); + const viewP = converter.domToView( domP ); expect( viewP.childCount ).to.equal( 2 ); expect( viewP.getChild( 0 ).data ).to.equal( 'foo ' ); @@ -636,7 +636,7 @@ describe( 'DomConverter', () => { createElement( document, 'br' ) ] ); - const viewP = converter.domToView( viewDocument, domP ); + const viewP = converter.domToView( domP ); expect( viewP.childCount ).to.equal( 2 ); expect( viewP.getChild( 0 ).getChild( 0 ).data ).to.equal( 'foo ' ); @@ -650,7 +650,7 @@ describe( 'DomConverter', () => { describe( 'clearing auto filler', () => { it( 'should remove inline filler when converting dom to view', () => { const text = document.createTextNode( INLINE_FILLER + 'foo' ); - const view = converter.domToView( viewDocument, text ); + const view = converter.domToView( text ); expect( view.data ).to.equal( 'foo' ); } ); @@ -658,14 +658,14 @@ describe( 'DomConverter', () => { // See https://github.com/ckeditor/ckeditor5/issues/692. it( 'should not remove space after inline filler if previous node nor next node does not exist', () => { const text = document.createTextNode( INLINE_FILLER + ' ' ); - const view = converter.domToView( viewDocument, text ); + const view = converter.domToView( text ); expect( view.data ).to.equal( ' ' ); } ); it( 'should convert non breaking space to normal space after inline filler', () => { const text = document.createTextNode( INLINE_FILLER + '\u00A0' ); - const view = converter.domToView( viewDocument, text ); + const view = converter.domToView( text ); expect( view.data ).to.equal( ' ' ); } ); @@ -678,7 +678,7 @@ describe( 'DomConverter', () => { const domText = document.createTextNode( 'foo' ); const domP = createElement( document, 'p', null, [ domImg, domText ] ); - const viewChildren = Array.from( converter.domChildrenToView( viewDocument, domP ) ); + const viewChildren = Array.from( converter.domChildrenToView( domP ) ); expect( viewChildren.length ).to.equal( 2 ); expect( stringify( viewChildren[ 0 ] ) ).to.equal( '' ); @@ -690,7 +690,7 @@ describe( 'DomConverter', () => { const domFiller = BR_FILLER( document ); const domP = createElement( document, 'p', null, domFiller ); - const viewChildren = Array.from( converter.domChildrenToView( viewDocument, domP ) ); + const viewChildren = Array.from( converter.domChildrenToView( domP ) ); expect( viewChildren.length ).to.equal( 0 ); } ); @@ -700,7 +700,7 @@ describe( 'DomConverter', () => { const domB = createElement( document, 'b', null, 'bar' ); const domP = createElement( document, 'p', null, [ domB, domText ] ); - const viewChildren = Array.from( converter.domChildrenToView( viewDocument, domP, { withChildren: false } ) ); + const viewChildren = Array.from( converter.domChildrenToView( domP, { withChildren: false } ) ); expect( viewChildren.length ).to.equal( 2 ); expect( stringify( viewChildren[ 0 ] ) ).to.equal( '' ); @@ -766,7 +766,7 @@ describe( 'DomConverter', () => { } ); it( 'should converter position inside block filler', () => { - const converter = new DomConverter( { blockFillerMode: 'nbsp' } ); + const converter = new DomConverter( viewDocument, { blockFillerMode: 'nbsp' } ); const domFiller = NBSP_FILLER( document ); // eslint-disable-line new-cap const domP = createElement( document, 'p', null, domFiller ); diff --git a/tests/view/domconverter/domconverter.js b/tests/view/domconverter/domconverter.js index fd2c76255..c3c62dee9 100644 --- a/tests/view/domconverter/domconverter.js +++ b/tests/view/domconverter/domconverter.js @@ -16,16 +16,14 @@ import global from '@ckeditor/ckeditor5-utils/src/dom/global'; import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'DomConverter', () => { - let converter, stylesProcessor; + let converter, stylesProcessor, viewDocument; testUtils.createSinonSandbox(); - before( () => { - stylesProcessor = new StylesProcessor(); - } ); - beforeEach( () => { - converter = new DomConverter(); + stylesProcessor = new StylesProcessor(); + viewDocument = new ViewDocument( stylesProcessor ); + converter = new DomConverter( viewDocument ); } ); describe( 'constructor()', () => { @@ -34,7 +32,7 @@ describe( 'DomConverter', () => { } ); it( 'should create converter with defined block mode filler', () => { - converter = new DomConverter( { blockFillerMode: 'nbsp' } ); + converter = new DomConverter( viewDocument, { blockFillerMode: 'nbsp' } ); expect( converter.blockFillerMode ).to.equal( 'nbsp' ); } ); } ); @@ -300,7 +298,7 @@ describe( 'DomConverter', () => { describe( 'isBlockFiller()', () => { describe( 'mode "nbsp"', () => { beforeEach( () => { - converter = new DomConverter( { blockFillerMode: 'nbsp' } ); + converter = new DomConverter( viewDocument, { blockFillerMode: 'nbsp' } ); } ); it( 'should return true if the node is an nbsp filler and is a single child of a block level element', () => { @@ -383,7 +381,7 @@ describe( 'DomConverter', () => { describe( 'mode "br"', () => { beforeEach( () => { - converter = new DomConverter( { blockFillerMode: 'br' } ); + converter = new DomConverter( viewDocument, { blockFillerMode: 'br' } ); } ); it( 'should return true if the node is an instance of the BR block filler', () => { @@ -395,7 +393,7 @@ describe( 'DomConverter', () => { } ); it( 'should return false if the node is an instance of the NBSP block filler', () => { - converter = new DomConverter( { blockFillerMode: 'br' } ); + converter = new DomConverter( viewDocument, { blockFillerMode: 'br' } ); const nbspFillerInstance = NBSP_FILLER( document ); // eslint-disable-line new-cap // NBSP must be check inside a context. const context = document.createElement( 'div' ); diff --git a/tests/view/domconverter/uielement.js b/tests/view/domconverter/uielement.js index 4dc0d4ded..353fe9ddc 100644 --- a/tests/view/domconverter/uielement.js +++ b/tests/view/domconverter/uielement.js @@ -27,13 +27,10 @@ describe( 'DOMConverter UIElement integration', () => { return element; } - before( () => { - stylesProcessor = new StylesProcessor(); - } ); - beforeEach( () => { - converter = new DomConverter(); + stylesProcessor = new StylesProcessor(); viewDocument = new ViewDocument( stylesProcessor ); + converter = new DomConverter( viewDocument ); } ); describe( 'viewToDom()', () => { @@ -68,7 +65,7 @@ describe( 'DOMConverter UIElement integration', () => { const uiElement = createUIElement( 'div' ); const domElement = converter.viewToDom( uiElement, document, { bind: true } ); - expect( converter.domToView( viewDocument, domElement ) ).to.equal( uiElement ); + expect( converter.domToView( domElement ) ).to.equal( uiElement ); } ); it( 'should return UIElement for nodes inside', () => { @@ -78,10 +75,10 @@ describe( 'DOMConverter UIElement integration', () => { const domParagraph = domElement.childNodes[ 0 ]; const domSpan = domParagraph.childNodes[ 0 ]; - expect( converter.domToView( viewDocument, domParagraph ) ).to.equal( uiElement ); - expect( converter.domToView( viewDocument, domSpan ) ).to.be.equal( uiElement ); - expect( converter.domToView( viewDocument, domParagraph.childNodes[ 0 ] ) ).equal( uiElement ); - expect( converter.domToView( viewDocument, domSpan.childNodes[ 0 ] ) ).equal( uiElement ); + expect( converter.domToView( domParagraph ) ).to.equal( uiElement ); + expect( converter.domToView( domSpan ) ).to.be.equal( uiElement ); + expect( converter.domToView( domParagraph.childNodes[ 0 ] ) ).equal( uiElement ); + expect( converter.domToView( domSpan.childNodes[ 0 ] ) ).equal( uiElement ); } ); } ); diff --git a/tests/view/domconverter/view-to-dom.js b/tests/view/domconverter/view-to-dom.js index 8cf9c447a..1ad1d924d 100644 --- a/tests/view/domconverter/view-to-dom.js +++ b/tests/view/domconverter/view-to-dom.js @@ -24,10 +24,10 @@ import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'DomConverter', () => { let converter, viewDocument, stylesProcessor; - before( () => { + beforeEach( () => { stylesProcessor = new StylesProcessor(); - converter = new DomConverter(); viewDocument = new ViewDocument( stylesProcessor ); + converter = new DomConverter( viewDocument ); } ); describe( 'viewToDom()', () => { diff --git a/tests/view/observer/domeventdata.js b/tests/view/observer/domeventdata.js index 2ffe0e7e7..e0ad37836 100644 --- a/tests/view/observer/domeventdata.js +++ b/tests/view/observer/domeventdata.js @@ -25,7 +25,7 @@ describe( 'DomEventData', () => { domRoot.innerHTML = '
'; document.body.appendChild( domRoot ); - viewBody = view.domConverter.domToView( viewDocument, document.body, { bind: true } ); + viewBody = view.domConverter.domToView( document.body, { bind: true } ); } ); afterEach( () => { diff --git a/tests/view/renderer.js b/tests/view/renderer.js index eb1fb1cb3..86185826d 100644 --- a/tests/view/renderer.js +++ b/tests/view/renderer.js @@ -34,11 +34,9 @@ describe( 'Renderer', () => { testUtils.createSinonSandbox(); - before( () => { + beforeEach( () => { stylesProcessor = new StylesProcessor(); - } ); - beforeEach( () => { view = new View( stylesProcessor ); viewDocument = view.document; diff --git a/tests/view/upcastwriter.js b/tests/view/upcastwriter.js index 08561932d..f5bf6703a 100644 --- a/tests/view/upcastwriter.js +++ b/tests/view/upcastwriter.js @@ -17,14 +17,12 @@ import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'UpcastWriter', () => { let writer, view, dataprocessor, document, stylesProcessor; - before( () => { + beforeEach( () => { stylesProcessor = new StylesProcessor(); document = new Document( stylesProcessor ); writer = new UpcastWriter( document ); - dataprocessor = new HtmlDataProcessor( stylesProcessor ); - } ); + dataprocessor = new HtmlDataProcessor( document ); - beforeEach( () => { const html = '' + '

Heading 1

' + '

Foo Bar Bold

' + From c62176b8a5246fdce4e2d604f2375be563f11e7a Mon Sep 17 00:00:00 2001 From: Kamil Piechaczek Date: Tue, 25 Feb 2020 08:36:34 +0100 Subject: [PATCH 23/34] Fixed docs after moving method between classes. --- src/view/downcastwriter.js | 4 ++-- src/view/element.js | 8 ++++---- src/view/stylesmap.js | 8 ++++---- src/view/upcastwriter.js | 4 ++-- 4 files changed, 12 insertions(+), 12 deletions(-) diff --git a/src/view/downcastwriter.js b/src/view/downcastwriter.js index e695cf5b7..d8db67105 100644 --- a/src/view/downcastwriter.js +++ b/src/view/downcastwriter.js @@ -328,7 +328,7 @@ export default class DowncastWriter { * }, element ); * * **Note**: The passed style can be normalized if - * {@link module:engine/view/document~Document#addStyleProcessorRules a particular style processor rule is enabled}. + * {@link module:engine/controller/datacontroller~DataController#addStyleProcessorRules a particular style processor rule is enabled}. * See {@link module:engine/view/stylesmap~StylesMap#set `StylesMap#set()`} for details. * * @param {String|Object} property Property name or object with key - value pairs. @@ -350,7 +350,7 @@ export default class DowncastWriter { * writer.removeStyle( [ 'color', 'border-top' ], element ); // Removes both 'color' and 'border-top' styles. * * **Note**: This method can work with normalized style names if - * {@link module:engine/view/document~Document#addStyleProcessorRules a particular style processor rule is enabled}. + * {@link module:engine/controller/datacontroller~DataController#addStyleProcessorRules a particular style processor rule is enabled}. * See {@link module:engine/view/stylesmap~StylesMap#remove `StylesMap#remove()`} for details. * * @param {Array.|String} property diff --git a/src/view/element.js b/src/view/element.js index c5db76a24..7443b1ac6 100644 --- a/src/view/element.js +++ b/src/view/element.js @@ -381,7 +381,7 @@ export default class Element extends Node { * If the style does not exist `undefined` is returned. * * **Note**: This method can work with normalized style names if - * {@link module:engine/view/document~Document#addStyleProcessorRules a particular style processor rule is enabled}. + * {@link module:engine/controller/datacontroller~DataController#addStyleProcessorRules a particular style processor rule is enabled}. * See {@link module:engine/view/stylesmap~StylesMap#getAsString `StylesMap#getAsString()`} for details. * * For an element with style set to `'margin:1px'`: @@ -429,7 +429,7 @@ export default class Element extends Node { * Will return a `2px` string. * * **Note**: This method will return normalized values only if - * {@link module:engine/view/document~Document#addStyleProcessorRules a particular style processor rule is enabled}. + * {@link module:engine/controller/datacontroller~DataController#addStyleProcessorRules a particular style processor rule is enabled}. * See {@link module:engine/view/stylesmap~StylesMap#getNormalized `StylesMap#getNormalized()`} for details. * * @@ -761,7 +761,7 @@ export default class Element extends Node { * } ); * * **Note**: This method can work with normalized style names if - * {@link module:engine/view/document~Document#addStyleProcessorRules a particular style processor rule is enabled}. + * {@link module:engine/controller/datacontroller~DataController#addStyleProcessorRules a particular style processor rule is enabled}. * See {@link module:engine/view/stylesmap~StylesMap#set `StylesMap#set()`} for details. * * @see module:engine/view/downcastwriter~DowncastWriter#setStyle @@ -783,7 +783,7 @@ export default class Element extends Node { * element._removeStyle( [ 'color', 'border-top' ] ); // Removes both 'color' and 'border-top' styles. * * **Note**: This method can work with normalized style names if - * {@link module:engine/view/document~Document#addStyleProcessorRules a particular style processor rule is enabled}. + * {@link module:engine/controller/datacontroller~DataController#addStyleProcessorRules a particular style processor rule is enabled}. * See {@link module:engine/view/stylesmap~StylesMap#remove `StylesMap#remove()`} for details. * * @see module:engine/view/downcastwriter~DowncastWriter#removeStyle diff --git a/src/view/stylesmap.js b/src/view/stylesmap.js index 63f6c62bd..b89a35a80 100644 --- a/src/view/stylesmap.js +++ b/src/view/stylesmap.js @@ -139,8 +139,8 @@ export default class StylesMap { * 'margin-right': '1em' * } ); * - * ***Note**:* This method uses {@link module:engine/view/document~Document#addStyleProcessorRules enabled style processor rules} - * to normalize passed values. + * ***Note**:* This method uses {@link module:engine/controller/datacontroller~DataController#addStyleProcessorRules + * enabled style processor rules} to normalize passed values. * * // Enable 'margin' shorthand processing: * editor.data.addStyleProcessorRules( addMarginRules ); @@ -192,8 +192,8 @@ export default class StylesMap { * * styles.toString(); // -> 'margin-right:2px;' * - * ***Note**:* This method uses {@link module:engine/view/document~Document#addStyleProcessorRules enabled style processor rules} - * to normalize passed values. + * ***Note**:* This method uses {@link module:engine/controller/datacontroller~DataController#addStyleProcessorRules + * enabled style processor rules} to normalize passed values. * * // Enable 'margin' shorthand processing: * editor.data.addStyleProcessorRules( addMarginRules ); diff --git a/src/view/upcastwriter.js b/src/view/upcastwriter.js index 71361db2f..251a8c214 100644 --- a/src/view/upcastwriter.js +++ b/src/view/upcastwriter.js @@ -282,7 +282,7 @@ export default class UpcastWriter { * } ); * * **Note**: This method can work with normalized style names if - * {@link module:engine/view/document~Document#addStyleProcessorRules a particular style processor rule is enabled}. + * {@link module:engine/controller/datacontroller~DataController#addStyleProcessorRules a particular style processor rule is enabled}. * See {@link module:engine/view/stylesmap~StylesMap#set `StylesMap#set()`} for details. * * @see module:engine/view/element~Element#_setStyle @@ -304,7 +304,7 @@ export default class UpcastWriter { * writer.removeStyle( element, [ 'color', 'border-top' ] ); // Removes both 'color' and 'border-top' styles. * * **Note**: This method can work with normalized style names if - * {@link module:engine/view/document~Document#addStyleProcessorRules a particular style processor rule is enabled}. + * {@link module:engine/controller/datacontroller~DataController#addStyleProcessorRules a particular style processor rule is enabled}. * See {@link module:engine/view/stylesmap~StylesMap#remove `StylesMap#remove()`} for details. * * @see module:engine/view/element~Element#_removeStyle From 42fa0f7037b420099083302769ee940ca37abb64 Mon Sep 17 00:00:00 2001 From: Kamil Piechaczek Date: Tue, 25 Feb 2020 09:01:27 +0100 Subject: [PATCH 24/34] Simplified tests. --- tests/controller/editingcontroller.js | 2 +- tests/conversion/conversion.js | 8 ++----- tests/conversion/downcastdispatcher.js | 8 ++----- tests/conversion/downcasthelpers.js | 23 +++++--------------- tests/conversion/mapper.js | 2 +- tests/conversion/upcastdispatcher.js | 8 ++----- tests/conversion/upcasthelpers.js | 8 ++----- tests/conversion/viewconsumable.js | 4 +--- tests/dev-utils/view.js | 2 +- tests/tickets/1323.js | 9 ++------ tests/view/attributeelement.js | 5 +---- tests/view/containerelement.js | 5 +---- tests/view/document.js | 6 ++--- tests/view/documentfragment.js | 5 +---- tests/view/documentselection.js | 5 +---- tests/view/downcastwriter/breakattributes.js | 2 +- tests/view/downcastwriter/breakcontainer.js | 2 +- tests/view/downcastwriter/clear.js | 2 +- tests/view/downcastwriter/insert.js | 2 +- tests/view/downcastwriter/mergeattributes.js | 2 +- tests/view/downcastwriter/mergecontainers.js | 2 +- tests/view/downcastwriter/move.js | 2 +- tests/view/downcastwriter/remove.js | 2 +- tests/view/downcastwriter/rename.js | 2 +- tests/view/downcastwriter/unwrap.js | 2 +- tests/view/downcastwriter/wrap.js | 2 +- tests/view/downcastwriter/writer.js | 2 +- tests/view/element.js | 5 +---- tests/view/emptyelement.js | 8 ++----- tests/view/matcher.js | 5 +---- tests/view/observer/clickobserver.js | 8 ++----- tests/view/observer/compositionobserver.js | 8 ++----- tests/view/observer/domeventdata.js | 8 ++----- tests/view/observer/domeventobserver.js | 8 ++----- tests/view/observer/focusobserver.js | 8 ++----- tests/view/observer/inputobserver.js | 5 ++--- tests/view/observer/keyobserver.js | 8 ++----- tests/view/observer/mouseobserver.js | 8 ++----- tests/view/observer/mutationobserver.js | 9 ++------ tests/view/observer/observer.js | 2 +- tests/view/range.js | 5 +---- tests/view/selection.js | 5 +---- tests/view/styles/background.js | 5 +---- tests/view/styles/border.js | 5 +---- tests/view/styles/margin.js | 5 +---- tests/view/styles/padding.js | 5 +---- tests/view/text.js | 5 +---- tests/view/textproxy.js | 8 ++----- tests/view/treewalker.js | 3 +-- tests/view/uielement.js | 5 +---- tests/view/utils-tests/createroot.js | 5 +---- tests/view/view/jumpoverinlinefiller.js | 7 ++---- tests/view/view/jumpoveruielement.js | 7 ++---- tests/view/view/view.js | 8 ++----- 54 files changed, 79 insertions(+), 213 deletions(-) diff --git a/tests/controller/editingcontroller.js b/tests/controller/editingcontroller.js index 2c562f754..fc2e7aa50 100644 --- a/tests/controller/editingcontroller.js +++ b/tests/controller/editingcontroller.js @@ -27,7 +27,7 @@ import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'EditingController', () => { let stylesProcessor; - before( () => { + beforeEach( () => { stylesProcessor = new StylesProcessor(); } ); diff --git a/tests/conversion/conversion.js b/tests/conversion/conversion.js index 78e1dd039..e95a104cd 100644 --- a/tests/conversion/conversion.js +++ b/tests/conversion/conversion.js @@ -21,15 +21,11 @@ import { expectToThrowCKEditorError } from '@ckeditor/ckeditor5-utils/tests/_uti import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'Conversion', () => { - let conversion, downcastDispA, upcastDispaA, downcastDispB; + let conversion, downcastDispA, upcastDispaA, downcastDispB, stylesProcessor; - let stylesProcessor; - - before( () => { + beforeEach( () => { stylesProcessor = new StylesProcessor(); - } ); - beforeEach( () => { // Placeholders. Will be used only to see if their were given as attribute for a spy function. downcastDispA = Symbol( 'downA' ); downcastDispB = Symbol( 'downB' ); diff --git a/tests/conversion/downcastdispatcher.js b/tests/conversion/downcastdispatcher.js index 83c1b84ec..51acfe16f 100644 --- a/tests/conversion/downcastdispatcher.js +++ b/tests/conversion/downcastdispatcher.js @@ -16,14 +16,10 @@ import ViewContainerElement from '../../src/view/containerelement'; import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'DowncastDispatcher', () => { - let dispatcher, doc, root, differStub, model, view, mapper; - let stylesProcessor; - - before( () => { - stylesProcessor = new StylesProcessor(); - } ); + let dispatcher, doc, root, differStub, model, view, mapper, stylesProcessor; beforeEach( () => { + stylesProcessor = new StylesProcessor(); model = new Model(); view = new View( stylesProcessor ); doc = model.document; diff --git a/tests/conversion/downcasthelpers.js b/tests/conversion/downcasthelpers.js index 5b16d03d4..9ceb85634 100644 --- a/tests/conversion/downcasthelpers.js +++ b/tests/conversion/downcasthelpers.js @@ -39,14 +39,11 @@ import { StylesProcessor } from '../../src/view/stylesmap'; import DowncastWriter from '../../src/view/downcastwriter'; describe( 'DowncastHelpers', () => { - let model, modelRoot, viewRoot, downcastHelpers, controller; - let modelRootStart, stylesProcessor; + let model, modelRoot, viewRoot, downcastHelpers, controller, modelRootStart, stylesProcessor; - before( () => { + beforeEach( () => { stylesProcessor = new StylesProcessor(); - } ); - beforeEach( () => { model = new Model(); const modelDoc = model.document; modelRoot = modelDoc.createRoot(); @@ -1454,15 +1451,10 @@ describe( 'DowncastHelpers', () => { } ); describe( 'downcast converters', () => { - let dispatcher, modelDoc, modelRoot, viewRoot, controller, modelRootStart, model; - - let stylesProcessor; - - before( () => { - stylesProcessor = new StylesProcessor(); - } ); + let dispatcher, modelDoc, modelRoot, viewRoot, controller, modelRootStart, model, stylesProcessor; beforeEach( () => { + stylesProcessor = new StylesProcessor(); model = new Model(); modelDoc = model.document; modelRoot = modelDoc.createRoot(); @@ -1800,11 +1792,8 @@ describe( 'downcast selection converters', () => { let dispatcher, mapper, model, view, modelDoc, modelRoot, docSelection, viewDoc, viewRoot, viewSelection, downcastHelpers; let stylesProcessor; - before( () => { - stylesProcessor = new StylesProcessor(); - } ); - beforeEach( () => { + stylesProcessor = new StylesProcessor(); model = new Model(); modelDoc = model.document; modelRoot = modelDoc.createRoot(); @@ -1812,7 +1801,7 @@ describe( 'downcast selection converters', () => { model.schema.extend( '$text', { allowIn: '$root' } ); - view = new View( new StylesProcessor() ); + view = new View( stylesProcessor ); viewDoc = view.document; viewRoot = createViewRoot( viewDoc ); viewSelection = viewDoc.selection; diff --git a/tests/conversion/mapper.js b/tests/conversion/mapper.js index 8acb2dd37..94c848136 100644 --- a/tests/conversion/mapper.js +++ b/tests/conversion/mapper.js @@ -22,7 +22,7 @@ import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'Mapper', () => { let viewDocument, stylesProcessor; - before( () => { + beforeEach( () => { stylesProcessor = new StylesProcessor(); viewDocument = new ViewDocument( stylesProcessor ); } ); diff --git a/tests/conversion/upcastdispatcher.js b/tests/conversion/upcastdispatcher.js index 5c7b6a4e3..008a68cf1 100644 --- a/tests/conversion/upcastdispatcher.js +++ b/tests/conversion/upcastdispatcher.js @@ -24,15 +24,11 @@ import { expectToThrowCKEditorError } from '@ckeditor/ckeditor5-utils/tests/_uti import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'UpcastDispatcher', () => { - let model, viewDocument; - let stylesProcessor; - - before( () => { - stylesProcessor = new StylesProcessor(); - } ); + let model, viewDocument, stylesProcessor; beforeEach( () => { model = new Model(); + stylesProcessor = new StylesProcessor(); viewDocument = new ViewDocument( stylesProcessor ); } ); diff --git a/tests/conversion/upcasthelpers.js b/tests/conversion/upcasthelpers.js index 68fec7ad8..3e30a8925 100644 --- a/tests/conversion/upcasthelpers.js +++ b/tests/conversion/upcasthelpers.js @@ -705,15 +705,11 @@ describe( 'UpcastHelpers', () => { } ); describe( 'upcast-converters', () => { - let dispatcher, schema, context, model, viewDocument; + let dispatcher, schema, context, model, viewDocument, stylesProcessor; - let stylesProcessor; - - before( () => { + beforeEach( () => { stylesProcessor = new StylesProcessor(); - } ); - beforeEach( () => { model = new Model(); viewDocument = new ViewDocument( stylesProcessor ); schema = model.schema; diff --git a/tests/conversion/viewconsumable.js b/tests/conversion/viewconsumable.js index 2354308e3..c3d6f2be3 100644 --- a/tests/conversion/viewconsumable.js +++ b/tests/conversion/viewconsumable.js @@ -16,16 +16,14 @@ import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'ViewConsumable', () => { let viewConsumable, el, viewDocument, stylesProcessor; - before( () => { + beforeEach( () => { stylesProcessor = new StylesProcessor(); viewDocument = new ViewDocument( stylesProcessor ); addBorderRules( stylesProcessor ); addMarginRules( stylesProcessor ); addPaddingRules( stylesProcessor ); - } ); - beforeEach( () => { viewConsumable = new ViewConsumable(); el = new ViewElement( viewDocument, 'p' ); } ); diff --git a/tests/dev-utils/view.js b/tests/dev-utils/view.js index e07884aec..2d7e1a584 100644 --- a/tests/dev-utils/view.js +++ b/tests/dev-utils/view.js @@ -25,7 +25,7 @@ import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'view test utils', () => { let stylesProcessor; - before( () => { + beforeEach( () => { stylesProcessor = new StylesProcessor(); } ); diff --git a/tests/tickets/1323.js b/tests/tickets/1323.js index f8a91865e..f0f10dbad 100644 --- a/tests/tickets/1323.js +++ b/tests/tickets/1323.js @@ -12,16 +12,11 @@ import MarkerOperation from '../../src/model/operation/markeroperation'; import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'Bug ckeditor5-engine@1323', () => { - let stylesProcessor; - - before( () => { - stylesProcessor = new StylesProcessor(); - } ); - describe( 'constructor()', () => { - let model, editing, root, range; + let model, editing, root, range, stylesProcessor; beforeEach( () => { + stylesProcessor = new StylesProcessor(); model = new Model(); editing = new EditingController( model, stylesProcessor ); root = model.document.createRoot(); diff --git a/tests/view/attributeelement.js b/tests/view/attributeelement.js index a3241fef3..f0bcf58b3 100644 --- a/tests/view/attributeelement.js +++ b/tests/view/attributeelement.js @@ -14,11 +14,8 @@ describe( 'AttributeElement', () => { let document; let stylesProcessor; - before( () => { - stylesProcessor = new StylesProcessor(); - } ); - beforeEach( () => { + stylesProcessor = new StylesProcessor(); document = new Document( stylesProcessor ); } ); diff --git a/tests/view/containerelement.js b/tests/view/containerelement.js index a56dad111..fba18c798 100644 --- a/tests/view/containerelement.js +++ b/tests/view/containerelement.js @@ -12,11 +12,8 @@ import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'ContainerElement', () => { let document, stylesProcessor; - before( () => { - stylesProcessor = new StylesProcessor(); - } ); - beforeEach( () => { + stylesProcessor = new StylesProcessor(); document = new Document( stylesProcessor ); } ); diff --git a/tests/view/document.js b/tests/view/document.js index 1504d1c0b..9d02eb6fc 100644 --- a/tests/view/document.js +++ b/tests/view/document.js @@ -15,13 +15,11 @@ import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'Document', () => { let domRoot, viewDocument, stylesProcessor; - before( () => { - stylesProcessor = new StylesProcessor(); - } ); - testUtils.createSinonSandbox(); beforeEach( () => { + stylesProcessor = new StylesProcessor(); + domRoot = createElement( document, 'div', { id: 'editor', contenteditable: 'true' diff --git a/tests/view/documentfragment.js b/tests/view/documentfragment.js index 484399122..4be51880d 100644 --- a/tests/view/documentfragment.js +++ b/tests/view/documentfragment.js @@ -14,11 +14,8 @@ import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'DocumentFragment', () => { let document, stylesProcessor; - before( () => { - stylesProcessor = new StylesProcessor(); - } ); - beforeEach( () => { + stylesProcessor = new StylesProcessor(); document = new Document( stylesProcessor ); } ); diff --git a/tests/view/documentselection.js b/tests/view/documentselection.js index ec9ea96dc..2988c6047 100644 --- a/tests/view/documentselection.js +++ b/tests/view/documentselection.js @@ -23,11 +23,8 @@ describe( 'DocumentSelection', () => { testUtils.createSinonSandbox(); - before( () => { - stylesProcessor = new StylesProcessor(); - } ); - beforeEach( () => { + stylesProcessor = new StylesProcessor(); document = new Document( stylesProcessor ); const text = new Text( document, 'xxxxxxxxxxxxxxxxxxxx' ); el = new Element( document, 'p', null, text ); diff --git a/tests/view/downcastwriter/breakattributes.js b/tests/view/downcastwriter/breakattributes.js index 224510a05..5b97491cd 100644 --- a/tests/view/downcastwriter/breakattributes.js +++ b/tests/view/downcastwriter/breakattributes.js @@ -19,7 +19,7 @@ import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'DowncastWriter', () => { let stylesProcessor; - before( () => { + beforeEach( () => { stylesProcessor = new StylesProcessor(); } ); diff --git a/tests/view/downcastwriter/breakcontainer.js b/tests/view/downcastwriter/breakcontainer.js index 47b9149ec..af4fc9a69 100644 --- a/tests/view/downcastwriter/breakcontainer.js +++ b/tests/view/downcastwriter/breakcontainer.js @@ -15,7 +15,7 @@ import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'DowncastWriter', () => { let stylesProcessor; - before( () => { + beforeEach( () => { stylesProcessor = new StylesProcessor(); } ); diff --git a/tests/view/downcastwriter/clear.js b/tests/view/downcastwriter/clear.js index 91eb86ee2..aca7ee629 100644 --- a/tests/view/downcastwriter/clear.js +++ b/tests/view/downcastwriter/clear.js @@ -18,7 +18,7 @@ import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'DowncastWriter', () => { let stylesProcessor; - before( () => { + beforeEach( () => { stylesProcessor = new StylesProcessor(); } ); diff --git a/tests/view/downcastwriter/insert.js b/tests/view/downcastwriter/insert.js index eabe37b25..e8a6b621f 100644 --- a/tests/view/downcastwriter/insert.js +++ b/tests/view/downcastwriter/insert.js @@ -19,7 +19,7 @@ import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'DowncastWriter', () => { let stylesProcessor; - before( () => { + beforeEach( () => { stylesProcessor = new StylesProcessor(); } ); diff --git a/tests/view/downcastwriter/mergeattributes.js b/tests/view/downcastwriter/mergeattributes.js index 5e9b49605..d727bbf42 100644 --- a/tests/view/downcastwriter/mergeattributes.js +++ b/tests/view/downcastwriter/mergeattributes.js @@ -14,7 +14,7 @@ import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'DowncastWriter', () => { let stylesProcessor; - before( () => { + beforeEach( () => { stylesProcessor = new StylesProcessor(); } ); diff --git a/tests/view/downcastwriter/mergecontainers.js b/tests/view/downcastwriter/mergecontainers.js index 1a1fefb71..8441d2c5b 100644 --- a/tests/view/downcastwriter/mergecontainers.js +++ b/tests/view/downcastwriter/mergecontainers.js @@ -13,7 +13,7 @@ import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'DowncastWriter', () => { let stylesProcessor; - before( () => { + beforeEach( () => { stylesProcessor = new StylesProcessor(); } ); diff --git a/tests/view/downcastwriter/move.js b/tests/view/downcastwriter/move.js index ee0931046..39e6dd926 100644 --- a/tests/view/downcastwriter/move.js +++ b/tests/view/downcastwriter/move.js @@ -21,7 +21,7 @@ import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'DowncastWriter', () => { let stylesProcessor; - before( () => { + beforeEach( () => { stylesProcessor = new StylesProcessor(); } ); diff --git a/tests/view/downcastwriter/remove.js b/tests/view/downcastwriter/remove.js index 7ad5d4594..6f04b5ec5 100644 --- a/tests/view/downcastwriter/remove.js +++ b/tests/view/downcastwriter/remove.js @@ -19,7 +19,7 @@ import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'DowncastWriter', () => { let stylesProcessor; - before( () => { + beforeEach( () => { stylesProcessor = new StylesProcessor(); } ); diff --git a/tests/view/downcastwriter/rename.js b/tests/view/downcastwriter/rename.js index 9a3e3e8ff..c378c1e7a 100644 --- a/tests/view/downcastwriter/rename.js +++ b/tests/view/downcastwriter/rename.js @@ -11,7 +11,7 @@ import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'DowncastWriter', () => { let stylesProcessor; - before( () => { + beforeEach( () => { stylesProcessor = new StylesProcessor(); } ); diff --git a/tests/view/downcastwriter/unwrap.js b/tests/view/downcastwriter/unwrap.js index 52c177900..bb6084ad5 100644 --- a/tests/view/downcastwriter/unwrap.js +++ b/tests/view/downcastwriter/unwrap.js @@ -21,7 +21,7 @@ import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'DowncastWriter', () => { let stylesProcessor; - before( () => { + beforeEach( () => { stylesProcessor = new StylesProcessor(); } ); diff --git a/tests/view/downcastwriter/wrap.js b/tests/view/downcastwriter/wrap.js index d943e30b1..45ca7d949 100644 --- a/tests/view/downcastwriter/wrap.js +++ b/tests/view/downcastwriter/wrap.js @@ -24,7 +24,7 @@ import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'DowncastWriter', () => { let stylesProcessor; - before( () => { + beforeEach( () => { stylesProcessor = new StylesProcessor(); } ); diff --git a/tests/view/downcastwriter/writer.js b/tests/view/downcastwriter/writer.js index 2bdcac85b..46e3e8060 100644 --- a/tests/view/downcastwriter/writer.js +++ b/tests/view/downcastwriter/writer.js @@ -17,7 +17,7 @@ describe( 'DowncastWriter', () => { let writer, attributes, root, doc; let stylesProcessor; - before( () => { + beforeEach( () => { stylesProcessor = new StylesProcessor(); } ); diff --git a/tests/view/element.js b/tests/view/element.js index c58433e3d..82e02a181 100644 --- a/tests/view/element.js +++ b/tests/view/element.js @@ -14,11 +14,8 @@ import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'Element', () => { let document, stylesProcessor; - before( () => { - stylesProcessor = new StylesProcessor(); - } ); - beforeEach( () => { + stylesProcessor = new StylesProcessor(); document = new Document( stylesProcessor ); } ); diff --git a/tests/view/emptyelement.js b/tests/view/emptyelement.js index e29da7a61..23448aa2d 100644 --- a/tests/view/emptyelement.js +++ b/tests/view/emptyelement.js @@ -11,14 +11,10 @@ import { expectToThrowCKEditorError } from '@ckeditor/ckeditor5-utils/tests/_uti import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'EmptyElement', () => { - let element, emptyElement, document; - let stylesProcessor; - - before( () => { - stylesProcessor = new StylesProcessor(); - } ); + let element, emptyElement, document, stylesProcessor; beforeEach( () => { + stylesProcessor = new StylesProcessor(); document = new Document( stylesProcessor ); element = new Element( document, 'b' ); emptyElement = new EmptyElement( document, 'img', { diff --git a/tests/view/matcher.js b/tests/view/matcher.js index ef2d3af76..1c620e51c 100644 --- a/tests/view/matcher.js +++ b/tests/view/matcher.js @@ -11,11 +11,8 @@ import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'Matcher', () => { let document, stylesProcessor; - before( () => { - stylesProcessor = new StylesProcessor(); - } ); - beforeEach( () => { + stylesProcessor = new StylesProcessor(); document = new Document( stylesProcessor ); } ); diff --git a/tests/view/observer/clickobserver.js b/tests/view/observer/clickobserver.js index 1c3aa5c8d..1efb9cabd 100644 --- a/tests/view/observer/clickobserver.js +++ b/tests/view/observer/clickobserver.js @@ -10,14 +10,10 @@ import View from '../../../src/view/view'; import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'ClickObserver', () => { - let view, viewDocument, observer; - let stylesProcessor; - - before( () => { - stylesProcessor = new StylesProcessor(); - } ); + let view, viewDocument, observer, stylesProcessor; beforeEach( () => { + stylesProcessor = new StylesProcessor(); view = new View( stylesProcessor ); viewDocument = view.document; observer = view.addObserver( ClickObserver ); diff --git a/tests/view/observer/compositionobserver.js b/tests/view/observer/compositionobserver.js index 3d3513732..2eb11a0dd 100644 --- a/tests/view/observer/compositionobserver.js +++ b/tests/view/observer/compositionobserver.js @@ -9,14 +9,10 @@ import View from '../../../src/view/view'; import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'CompositionObserver', () => { - let view, viewDocument, observer; - let stylesProcessor; - - before( () => { - stylesProcessor = new StylesProcessor(); - } ); + let view, viewDocument, observer, stylesProcessor; beforeEach( () => { + stylesProcessor = new StylesProcessor(); view = new View( stylesProcessor ); viewDocument = view.document; observer = view.getObserver( CompositionObserver ); diff --git a/tests/view/observer/domeventdata.js b/tests/view/observer/domeventdata.js index e0ad37836..8c17e7b5a 100644 --- a/tests/view/observer/domeventdata.js +++ b/tests/view/observer/domeventdata.js @@ -10,14 +10,10 @@ import View from '../../../src/view/view'; import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'DomEventData', () => { - let view, viewDocument, viewBody, domRoot; - let stylesProcessor; - - before( () => { - stylesProcessor = new StylesProcessor(); - } ); + let view, viewDocument, viewBody, domRoot, stylesProcessor; beforeEach( () => { + stylesProcessor = new StylesProcessor(); view = new View( stylesProcessor ); viewDocument = view.document; diff --git a/tests/view/observer/domeventobserver.js b/tests/view/observer/domeventobserver.js index f1425ad29..1041733f0 100644 --- a/tests/view/observer/domeventobserver.js +++ b/tests/view/observer/domeventobserver.js @@ -45,14 +45,10 @@ class ClickCapturingObserver extends ClickObserver { } describe( 'DomEventObserver', () => { - let view, viewDocument; - let stylesProcessor; - - before( () => { - stylesProcessor = new StylesProcessor(); - } ); + let view, viewDocument, stylesProcessor; beforeEach( () => { + stylesProcessor = new StylesProcessor(); view = new View( stylesProcessor ); viewDocument = view.document; } ); diff --git a/tests/view/observer/focusobserver.js b/tests/view/observer/focusobserver.js index 65eec7aec..330d60ce9 100644 --- a/tests/view/observer/focusobserver.js +++ b/tests/view/observer/focusobserver.js @@ -11,14 +11,10 @@ import { setData } from '../../../src/dev-utils/view'; import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'FocusObserver', () => { - let view, viewDocument, observer; - let stylesProcessor; - - before( () => { - stylesProcessor = new StylesProcessor(); - } ); + let view, viewDocument, observer, stylesProcessor; beforeEach( () => { + stylesProcessor = new StylesProcessor(); view = new View( stylesProcessor ); viewDocument = view.document; observer = view.getObserver( FocusObserver ); diff --git a/tests/view/observer/inputobserver.js b/tests/view/observer/inputobserver.js index 782e24757..cea6b0eab 100644 --- a/tests/view/observer/inputobserver.js +++ b/tests/view/observer/inputobserver.js @@ -11,15 +11,14 @@ import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'InputObserver', () => { const oldEnvIsAndroid = env.isAndroid; - let view, viewDocument, observer; - let stylesProcessor; + let view, viewDocument, observer, stylesProcessor; before( () => { - stylesProcessor = new StylesProcessor(); env.isAndroid = true; } ); beforeEach( () => { + stylesProcessor = new StylesProcessor(); view = new View( stylesProcessor ); viewDocument = view.document; observer = view.getObserver( InputObserver ); diff --git a/tests/view/observer/keyobserver.js b/tests/view/observer/keyobserver.js index 2bdf25daf..3e85e5990 100644 --- a/tests/view/observer/keyobserver.js +++ b/tests/view/observer/keyobserver.js @@ -11,14 +11,10 @@ import { getCode } from '@ckeditor/ckeditor5-utils/src/keyboard'; import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'KeyObserver', () => { - let view, viewDocument, observer; - let stylesProcessor; - - before( () => { - stylesProcessor = new StylesProcessor(); - } ); + let view, viewDocument, observer, stylesProcessor; beforeEach( () => { + stylesProcessor = new StylesProcessor(); view = new View( stylesProcessor ); viewDocument = view.document; observer = view.getObserver( KeyObserver ); diff --git a/tests/view/observer/mouseobserver.js b/tests/view/observer/mouseobserver.js index 93a67ce88..f313086ab 100644 --- a/tests/view/observer/mouseobserver.js +++ b/tests/view/observer/mouseobserver.js @@ -10,14 +10,10 @@ import View from '../../../src/view/view'; import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'MouseObserver', () => { - let view, viewDocument, observer; - let stylesProcessor; - - before( () => { - stylesProcessor = new StylesProcessor(); - } ); + let view, viewDocument, observer, stylesProcessor; beforeEach( () => { + stylesProcessor = new StylesProcessor(); view = new View( stylesProcessor ); viewDocument = view.document; observer = view.addObserver( MouseObserver ); diff --git a/tests/view/observer/mutationobserver.js b/tests/view/observer/mutationobserver.js index 672fc017c..f1da5c947 100644 --- a/tests/view/observer/mutationobserver.js +++ b/tests/view/observer/mutationobserver.js @@ -13,15 +13,10 @@ import { parse } from '../../../src/dev-utils/view'; import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'MutationObserver', () => { - let view, domEditor, viewDocument, viewRoot, mutationObserver, lastMutations, domRoot; - - let stylesProcessor; - - before( () => { - stylesProcessor = new StylesProcessor(); - } ); + let view, domEditor, viewDocument, viewRoot, mutationObserver, lastMutations, domRoot, stylesProcessor; beforeEach( () => { + stylesProcessor = new StylesProcessor(); domRoot = document.createElement( 'div' ); domRoot.innerHTML = '
'; document.body.appendChild( domRoot ); diff --git a/tests/view/observer/observer.js b/tests/view/observer/observer.js index 662f911c6..45c584dd1 100644 --- a/tests/view/observer/observer.js +++ b/tests/view/observer/observer.js @@ -10,7 +10,7 @@ import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'Observer', () => { let stylesProcessor; - before( () => { + beforeEach( () => { stylesProcessor = new StylesProcessor(); } ); diff --git a/tests/view/range.js b/tests/view/range.js index 79419f228..e952357a6 100644 --- a/tests/view/range.js +++ b/tests/view/range.js @@ -23,11 +23,8 @@ function getRange( view, options = {} ) { describe( 'Range', () => { let document, stylesProcessor; - before( () => { - stylesProcessor = new StylesProcessor(); - } ); - beforeEach( () => { + stylesProcessor = new StylesProcessor(); document = new Document( stylesProcessor ); } ); diff --git a/tests/view/selection.js b/tests/view/selection.js index 34700a6dd..de14911c5 100644 --- a/tests/view/selection.js +++ b/tests/view/selection.js @@ -24,11 +24,8 @@ describe( 'Selection', () => { testUtils.createSinonSandbox(); - before( () => { - stylesProcessor = new StylesProcessor(); - } ); - beforeEach( () => { + stylesProcessor = new StylesProcessor(); viewDocument = new Document( stylesProcessor ); const text = new Text( viewDocument, 'xxxxxxxxxxxxxxxxxxxx' ); diff --git a/tests/view/styles/background.js b/tests/view/styles/background.js index bb8c3aa6a..61ab6e4d3 100644 --- a/tests/view/styles/background.js +++ b/tests/view/styles/background.js @@ -9,12 +9,9 @@ import { addBackgroundRules } from '../../../src/view/styles/background'; describe( 'Background styles normalization', () => { let styles, stylesProcessor; - before( () => { + beforeEach( () => { stylesProcessor = new StylesProcessor(); addBackgroundRules( stylesProcessor ); - } ); - - beforeEach( () => { styles = new StylesMap( stylesProcessor ); } ); diff --git a/tests/view/styles/border.js b/tests/view/styles/border.js index b8ff58f2f..f5ae65351 100644 --- a/tests/view/styles/border.js +++ b/tests/view/styles/border.js @@ -9,12 +9,9 @@ import { addBorderRules } from '../../../src/view/styles/border'; describe( 'Border styles normalization', () => { let styles, stylesProcessor; - before( () => { + beforeEach( () => { stylesProcessor = new StylesProcessor(); addBorderRules( stylesProcessor ); - } ); - - beforeEach( () => { styles = new StylesMap( stylesProcessor ); } ); diff --git a/tests/view/styles/margin.js b/tests/view/styles/margin.js index e60d52d91..75939e732 100644 --- a/tests/view/styles/margin.js +++ b/tests/view/styles/margin.js @@ -9,12 +9,9 @@ import { addMarginRules } from '../../../src/view/styles/margin'; describe( 'Margin styles normalizer', () => { let styles, stylesProcessor; - before( () => { + beforeEach( () => { stylesProcessor = new StylesProcessor(); addMarginRules( stylesProcessor ); - } ); - - beforeEach( () => { styles = new StylesMap( stylesProcessor ); } ); diff --git a/tests/view/styles/padding.js b/tests/view/styles/padding.js index 76baa9823..3d2138ba3 100644 --- a/tests/view/styles/padding.js +++ b/tests/view/styles/padding.js @@ -9,12 +9,9 @@ import { addPaddingRules } from '../../../src/view/styles/padding'; describe( 'Padding styles normalization', () => { let styles, stylesProcessor; - before( () => { + beforeEach( () => { stylesProcessor = new StylesProcessor(); addPaddingRules( stylesProcessor ); - } ); - - beforeEach( () => { styles = new StylesMap( stylesProcessor ); } ); diff --git a/tests/view/text.js b/tests/view/text.js index e9850b016..09c1da6af 100644 --- a/tests/view/text.js +++ b/tests/view/text.js @@ -11,11 +11,8 @@ import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'Text', () => { let document, stylesProcessor; - before( () => { - stylesProcessor = new StylesProcessor(); - } ); - beforeEach( () => { + stylesProcessor = new StylesProcessor(); document = new Document( stylesProcessor ); } ); diff --git a/tests/view/textproxy.js b/tests/view/textproxy.js index 3521e614e..c8aa3bf28 100644 --- a/tests/view/textproxy.js +++ b/tests/view/textproxy.js @@ -15,14 +15,10 @@ import Document from '../../src/view/document'; import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'TextProxy', () => { - let text, parent, wrapper, textProxy, document; - let stylesProcessor; - - before( () => { - stylesProcessor = new StylesProcessor(); - } ); + let text, parent, wrapper, textProxy, document, stylesProcessor; beforeEach( () => { + stylesProcessor = new StylesProcessor(); document = new Document( stylesProcessor ); text = new Text( document, 'abcdefgh' ); parent = new ContainerElement( document, 'p', [], [ text ] ); diff --git a/tests/view/treewalker.js b/tests/view/treewalker.js index b926988cf..958488d84 100644 --- a/tests/view/treewalker.js +++ b/tests/view/treewalker.js @@ -16,8 +16,7 @@ import { expectToThrowCKEditorError } from '@ckeditor/ckeditor5-utils/tests/_uti import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'TreeWalker', () => { - let doc, root, img1, paragraph, bold, textAbcd, charY, img2, charX, rootBeginning, rootEnding; - let stylesProcessor; + let doc, root, img1, paragraph, bold, textAbcd, charY, img2, charX, rootBeginning, rootEnding, stylesProcessor; before( () => { stylesProcessor = new StylesProcessor(); diff --git a/tests/view/uielement.js b/tests/view/uielement.js index 538555331..ce47abdb4 100644 --- a/tests/view/uielement.js +++ b/tests/view/uielement.js @@ -14,11 +14,8 @@ import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'UIElement', () => { let uiElement, doc, stylesProcessor; - before( () => { - stylesProcessor = new StylesProcessor(); - } ); - beforeEach( () => { + stylesProcessor = new StylesProcessor(); doc = new Document( stylesProcessor ); uiElement = new UIElement( doc, 'span', { diff --git a/tests/view/utils-tests/createroot.js b/tests/view/utils-tests/createroot.js index 92dd655d9..9095e49e1 100644 --- a/tests/view/utils-tests/createroot.js +++ b/tests/view/utils-tests/createroot.js @@ -11,11 +11,8 @@ import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'createRoot', () => { let viewDoc, stylesProcessor; - before( () => { - stylesProcessor = new StylesProcessor(); - } ); - beforeEach( () => { + stylesProcessor = new StylesProcessor(); viewDoc = new Document( stylesProcessor ); } ); diff --git a/tests/view/view/jumpoverinlinefiller.js b/tests/view/view/jumpoverinlinefiller.js index 64c88ae35..80a0f2432 100644 --- a/tests/view/view/jumpoverinlinefiller.js +++ b/tests/view/view/jumpoverinlinefiller.js @@ -16,14 +16,11 @@ import { parse, setData } from '../../../src/dev-utils/view'; import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'View', () => { - let view, viewDocument, domRoot; - let stylesProcessor; + let view, viewDocument, domRoot, stylesProcessor; - before( () => { + beforeEach( () => { stylesProcessor = new StylesProcessor(); - } ); - beforeEach( () => { domRoot = createElement( document, 'div', { contenteditable: 'true' } ); diff --git a/tests/view/view/jumpoveruielement.js b/tests/view/view/jumpoveruielement.js index 284d501d9..cf413d61e 100644 --- a/tests/view/view/jumpoveruielement.js +++ b/tests/view/view/jumpoveruielement.js @@ -19,8 +19,7 @@ import testUtils from '@ckeditor/ckeditor5-core/tests/_utils/utils'; import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'View', () => { - let view, viewDocument, domRoot, domSelection, viewRoot, foo, bar, ui, ui2; - let stylesProcessor; + let view, viewDocument, domRoot, domSelection, viewRoot, foo, bar, ui, ui2, stylesProcessor; function createUIElement( name, contents ) { const element = new UIElement( viewDocument, name ); @@ -35,11 +34,9 @@ describe( 'View', () => { return element; } - before( () => { + beforeEach( () => { stylesProcessor = new StylesProcessor(); - } ); - beforeEach( () => { domRoot = createElement( document, 'div', { contenteditable: 'true' } ); diff --git a/tests/view/view/view.js b/tests/view/view/view.js index cba26f6e9..7e7a5fa55 100644 --- a/tests/view/view/view.js +++ b/tests/view/view/view.js @@ -30,15 +30,11 @@ import CKEditorError from '@ckeditor/ckeditor5-utils/src/ckeditorerror'; describe( 'view', () => { const DEFAULT_OBSERVERS_COUNT = 6; - let domRoot, view, viewDocument, ObserverMock, instantiated, enabled, ObserverMockGlobalCount; + let domRoot, view, viewDocument, ObserverMock, instantiated, enabled, ObserverMockGlobalCount, stylesProcessor; - let stylesProcessor; - - before( () => { + beforeEach( () => { stylesProcessor = new StylesProcessor(); - } ); - beforeEach( () => { domRoot = createElement( document, 'div', { id: 'editor', contenteditable: 'true' From 6b9ac715721a021942f1edfb6afce4d5f256149b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Maciej=20Go=C5=82aszewski?= Date: Fri, 21 Feb 2020 09:55:01 +0100 Subject: [PATCH 25/34] Remove empty before. --- tests/conversion/viewconsumable.js | 4 ---- 1 file changed, 4 deletions(-) diff --git a/tests/conversion/viewconsumable.js b/tests/conversion/viewconsumable.js index c3d6f2be3..5b7ad8481 100644 --- a/tests/conversion/viewconsumable.js +++ b/tests/conversion/viewconsumable.js @@ -563,10 +563,6 @@ describe( 'ViewConsumable', () => { } ); describe( 'style shorthands handling', () => { - before( () => { - - } ); - describe( 'add', () => { it( 'should add padding shorthands', () => { viewConsumable.add( el, { styles: [ 'margin' ] } ); From cd0f3b6dedf4c7e6d52df461be6666ff58ee3cab Mon Sep 17 00:00:00 2001 From: Kamil Piechaczek Date: Tue, 25 Feb 2020 11:21:34 +0100 Subject: [PATCH 26/34] Reverted changes in Renderer class. --- src/view/renderer.js | 17 +++++------------ src/view/view.js | 2 +- tests/view/renderer.js | 17 ++++++++--------- 3 files changed, 14 insertions(+), 22 deletions(-) diff --git a/src/view/renderer.js b/src/view/renderer.js index 8f7ceebc8..49b2ad61a 100644 --- a/src/view/renderer.js +++ b/src/view/renderer.js @@ -41,9 +41,10 @@ export default class Renderer { /** * Creates a renderer instance. * - * @param {module:engine/view/view~View} view View editing controller. + * @param {module:engine/view/domconverter~DomConverter} domConverter Converter instance. + * @param {module:engine/view/documentselection~DocumentSelection} selection View selection. */ - constructor( view ) { + constructor( domConverter, selection ) { /** * Set of DOM Documents instances. * @@ -58,7 +59,7 @@ export default class Renderer { * @readonly * @member {module:engine/view/domconverter~DomConverter} */ - this.domConverter = view.domConverter; + this.domConverter = domConverter; /** * Set of nodes which attributes changed and may need to be rendered. @@ -90,7 +91,7 @@ export default class Renderer { * @readonly * @member {module:engine/view/documentselection~DocumentSelection} */ - this.selection = view.document.selection; + this.selection = selection; /** * Indicates if the view document is focused and selection can be rendered. Selection will not be rendered if @@ -115,14 +116,6 @@ export default class Renderer { * @type {null|HTMLElement} */ this._fakeSelectionContainer = null; - - /** - * Reference to the {@link module:engine/view/view~View#document}. - * - * @private - * @member {module:engine/view/document~Document} - */ - this._viewDocument = view.document; } /** diff --git a/src/view/view.js b/src/view/view.js index d57993c8b..93f648a38 100644 --- a/src/view/view.js +++ b/src/view/view.js @@ -106,7 +106,7 @@ export default class View { * @protected * @type {module:engine/view/renderer~Renderer} */ - this._renderer = new Renderer( this ); + this._renderer = new Renderer( this.domConverter, this.document.selection ); this._renderer.bind( 'isFocused' ).to( this.document ); /** diff --git a/tests/view/renderer.js b/tests/view/renderer.js index 86185826d..5ef61e566 100644 --- a/tests/view/renderer.js +++ b/tests/view/renderer.js @@ -14,8 +14,11 @@ import ViewText from '../../src/view/text'; import ViewRange from '../../src/view/range'; import ViewPosition from '../../src/view/position'; import UIElement from '../../src/view/uielement'; +import DocumentSelection from '../../src/view/documentselection'; +import DomConverter from '../../src/view/domconverter'; import Renderer from '../../src/view/renderer'; import DocumentFragment from '../../src/view/documentfragment'; +import ViewDocument from '../../src/view/document'; import DowncastWriter from '../../src/view/downcastwriter'; import { parse, stringify, setData as setViewData, getData as getViewData } from '../../src/dev-utils/view'; @@ -29,21 +32,17 @@ import { expectToThrowCKEditorError } from '@ckeditor/ckeditor5-utils/tests/_uti import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'Renderer', () => { - let view, selection, domConverter, renderer, viewDocument; + let selection, domConverter, renderer, viewDocument; let stylesProcessor; testUtils.createSinonSandbox(); beforeEach( () => { stylesProcessor = new StylesProcessor(); - - view = new View( stylesProcessor ); - viewDocument = view.document; - - renderer = new Renderer( view ); - domConverter = renderer.domConverter; - selection = renderer.selection; - + viewDocument = new ViewDocument( stylesProcessor ); + selection = new DocumentSelection(); + domConverter = new DomConverter( viewDocument ); + renderer = new Renderer( domConverter, selection ); renderer.domDocuments.add( document ); } ); From 3c3e9028ae754f67101b0e6293e472f65622ea3e Mon Sep 17 00:00:00 2001 From: Kamil Piechaczek Date: Tue, 25 Feb 2020 13:53:00 +0100 Subject: [PATCH 27/34] "This should be inlined." --- tests/controller/datacontroller.js | 9 +++-- tests/controller/editingcontroller.js | 14 ++----- tests/conversion/conversion.js | 8 ++-- tests/conversion/downcastdispatcher.js | 5 +-- tests/conversion/downcasthelpers.js | 21 ++++------ tests/conversion/mapper.js | 5 +-- tests/conversion/upcastdispatcher.js | 5 +-- tests/conversion/upcasthelpers.js | 16 ++------ tests/conversion/viewconsumable.js | 4 +- tests/dataprocessor/htmldataprocessor.js | 5 +-- tests/dataprocessor/xmldataprocessor.js | 5 +-- tests/dev-utils/view.js | 18 +++------ tests/tickets/1323.js | 5 +-- tests/view/attributeelement.js | 23 +++++------ tests/view/containerelement.js | 5 +-- tests/view/document.js | 6 +-- tests/view/documentfragment.js | 5 +-- tests/view/documentselection.js | 6 +-- tests/view/domconverter/binding.js | 9 ++--- tests/view/domconverter/dom-to-view.js | 5 +-- tests/view/domconverter/domconverter.js | 9 ++--- tests/view/domconverter/uielement.js | 5 +-- tests/view/domconverter/view-to-dom.js | 5 +-- tests/view/downcastwriter/breakattributes.js | 8 +--- tests/view/downcastwriter/breakcontainer.js | 8 +--- tests/view/downcastwriter/clear.js | 8 +--- tests/view/downcastwriter/insert.js | 8 +--- tests/view/downcastwriter/mergeattributes.js | 8 +--- tests/view/downcastwriter/mergecontainers.js | 8 +--- tests/view/downcastwriter/move.js | 8 +--- tests/view/downcastwriter/remove.js | 8 +--- tests/view/downcastwriter/rename.js | 8 +--- tests/view/downcastwriter/unwrap.js | 8 +--- tests/view/downcastwriter/wrap.js | 10 +---- tests/view/downcastwriter/writer.js | 7 +--- tests/view/editableelement.js | 8 +--- tests/view/element.js | 7 ++-- tests/view/emptyelement.js | 5 +-- tests/view/matcher.js | 5 +-- tests/view/node.js | 6 +-- tests/view/observer/clickobserver.js | 5 +-- tests/view/observer/compositionobserver.js | 5 +-- tests/view/observer/domeventdata.js | 5 +-- tests/view/observer/domeventobserver.js | 5 +-- tests/view/observer/fakeselectionobserver.js | 6 +-- tests/view/observer/focusobserver.js | 7 ++-- tests/view/observer/inputobserver.js | 5 +-- tests/view/observer/keyobserver.js | 5 +-- tests/view/observer/mouseobserver.js | 5 +-- tests/view/observer/mutationobserver.js | 42 +++++++++----------- tests/view/observer/observer.js | 8 +--- tests/view/observer/selectionobserver.js | 7 +--- tests/view/placeholder.js | 9 +---- tests/view/position.js | 7 +--- tests/view/range.js | 5 +-- tests/view/renderer.js | 8 ++-- tests/view/selection.js | 4 +- tests/view/styles/background.js | 4 +- tests/view/styles/border.js | 4 +- tests/view/styles/margin.js | 4 +- tests/view/styles/padding.js | 4 +- tests/view/stylesmap.js | 4 +- tests/view/text.js | 5 +-- tests/view/textproxy.js | 5 +-- tests/view/treewalker.js | 5 +-- tests/view/uielement.js | 5 +-- tests/view/upcastwriter.js | 5 +-- tests/view/utils-tests/createroot.js | 5 +-- tests/view/view/jumpoverinlinefiller.js | 6 +-- tests/view/view/jumpoveruielement.js | 6 +-- tests/view/view/view.js | 18 ++++----- 71 files changed, 184 insertions(+), 360 deletions(-) diff --git a/tests/controller/datacontroller.js b/tests/controller/datacontroller.js index 419c0c778..993e9d845 100644 --- a/tests/controller/datacontroller.js +++ b/tests/controller/datacontroller.js @@ -24,10 +24,10 @@ import { expectToThrowCKEditorError } from '@ckeditor/ckeditor5-utils/tests/_uti import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'DataController', () => { - let model, modelDocument, htmlDataProcessor, data, schema, upcastHelpers, downcastHelpers, viewDocument, stylesProcessor; + let model, modelDocument, htmlDataProcessor, data, schema, upcastHelpers, downcastHelpers, viewDocument; beforeEach( () => { - stylesProcessor = new StylesProcessor(); + const stylesProcessor = new StylesProcessor(); model = new Model(); schema = model.schema; @@ -49,7 +49,7 @@ describe( 'DataController', () => { describe( 'constructor()', () => { it( 'works without data processor', () => { - const data = new DataController( stylesProcessor, model ); + const data = new DataController( new StylesProcessor(), model ); expect( data.processor ).to.be.undefined; } ); @@ -576,6 +576,9 @@ describe( 'DataController', () => { describe( 'addStyleProcessorRules()', () => { it( 'should execute callback with an instance of StyleProcessor as the first argument', () => { + const stylesProcessor = new StylesProcessor(); + const data = new DataController( stylesProcessor, model, htmlDataProcessor ); + const spy = sinon.spy(); data.addStyleProcessorRules( spy ); diff --git a/tests/controller/editingcontroller.js b/tests/controller/editingcontroller.js index fc2e7aa50..467e05087 100644 --- a/tests/controller/editingcontroller.js +++ b/tests/controller/editingcontroller.js @@ -25,18 +25,12 @@ import { getData as getViewData } from '../../src/dev-utils/view'; import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'EditingController', () => { - let stylesProcessor; - - beforeEach( () => { - stylesProcessor = new StylesProcessor(); - } ); - describe( 'constructor()', () => { let model, editing; beforeEach( () => { model = new Model(); - editing = new EditingController( model, stylesProcessor ); + editing = new EditingController( model, new StylesProcessor() ); } ); afterEach( () => { @@ -84,7 +78,7 @@ describe( 'EditingController', () => { model = new Model(); modelRoot = model.document.createRoot(); - editing = new EditingController( model, stylesProcessor ); + editing = new EditingController( model, new StylesProcessor() ); domRoot = document.createElement( 'div' ); domRoot.contentEditable = true; @@ -484,7 +478,7 @@ describe( 'EditingController', () => { model.document.createRoot(); model.schema.register( 'paragraph', { inheritAllFrom: '$block' } ); - const editing = new EditingController( model, stylesProcessor ); + const editing = new EditingController( model, new StylesProcessor() ); const spy = sinon.spy(); @@ -508,7 +502,7 @@ describe( 'EditingController', () => { model.document.createRoot(); model.schema.register( 'paragraph', { inheritAllFrom: '$block' } ); - const editing = new EditingController( model, stylesProcessor ); + const editing = new EditingController( model, new StylesProcessor() ); const spy = sinon.spy( editing.view, 'destroy' ); diff --git a/tests/conversion/conversion.js b/tests/conversion/conversion.js index e95a104cd..4b8f61f77 100644 --- a/tests/conversion/conversion.js +++ b/tests/conversion/conversion.js @@ -21,11 +21,9 @@ import { expectToThrowCKEditorError } from '@ckeditor/ckeditor5-utils/tests/_uti import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'Conversion', () => { - let conversion, downcastDispA, upcastDispaA, downcastDispB, stylesProcessor; + let conversion, downcastDispA, upcastDispaA, downcastDispB; beforeEach( () => { - stylesProcessor = new StylesProcessor(); - // Placeholders. Will be used only to see if their were given as attribute for a spy function. downcastDispA = Symbol( 'downA' ); downcastDispB = Symbol( 'downB' ); @@ -124,7 +122,7 @@ describe( 'Conversion', () => { beforeEach( () => { model = new Model(); - const controller = new EditingController( model, stylesProcessor ); + const controller = new EditingController( model, new StylesProcessor() ); const modelDoc = model.document; modelRoot = modelDoc.createRoot(); @@ -722,7 +720,7 @@ describe( 'Conversion', () => { } function loadData( input ) { - const parsedView = viewParse( input, { stylesProcessor } ); + const parsedView = viewParse( input ); let convertedModel; model.change( writer => { diff --git a/tests/conversion/downcastdispatcher.js b/tests/conversion/downcastdispatcher.js index 51acfe16f..ba88b70cf 100644 --- a/tests/conversion/downcastdispatcher.js +++ b/tests/conversion/downcastdispatcher.js @@ -16,12 +16,11 @@ import ViewContainerElement from '../../src/view/containerelement'; import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'DowncastDispatcher', () => { - let dispatcher, doc, root, differStub, model, view, mapper, stylesProcessor; + let dispatcher, doc, root, differStub, model, view, mapper; beforeEach( () => { - stylesProcessor = new StylesProcessor(); model = new Model(); - view = new View( stylesProcessor ); + view = new View( new StylesProcessor() ); doc = model.document; mapper = new Mapper(); dispatcher = new DowncastDispatcher( { mapper } ); diff --git a/tests/conversion/downcasthelpers.js b/tests/conversion/downcasthelpers.js index 9ceb85634..2986cd09a 100644 --- a/tests/conversion/downcasthelpers.js +++ b/tests/conversion/downcasthelpers.js @@ -39,16 +39,14 @@ import { StylesProcessor } from '../../src/view/stylesmap'; import DowncastWriter from '../../src/view/downcastwriter'; describe( 'DowncastHelpers', () => { - let model, modelRoot, viewRoot, downcastHelpers, controller, modelRootStart, stylesProcessor; + let model, modelRoot, viewRoot, downcastHelpers, controller, modelRootStart; beforeEach( () => { - stylesProcessor = new StylesProcessor(); - model = new Model(); const modelDoc = model.document; modelRoot = modelDoc.createRoot(); - controller = new EditingController( model, stylesProcessor ); + controller = new EditingController( model, new StylesProcessor() ); // Set name of view root the same as dom root. // This is a mock of attaching view root to dom root. @@ -1325,7 +1323,7 @@ describe( 'DowncastHelpers', () => { let markerRange, viewDocument; beforeEach( () => { - viewDocument = new ViewDocument( stylesProcessor ); + viewDocument = new ViewDocument( new StylesProcessor() ); downcastHelpers.elementToElement( { model: 'div', @@ -1451,15 +1449,14 @@ describe( 'DowncastHelpers', () => { } ); describe( 'downcast converters', () => { - let dispatcher, modelDoc, modelRoot, viewRoot, controller, modelRootStart, model, stylesProcessor; + let dispatcher, modelDoc, modelRoot, viewRoot, controller, modelRootStart, model; beforeEach( () => { - stylesProcessor = new StylesProcessor(); model = new Model(); modelDoc = model.document; modelRoot = modelDoc.createRoot(); - controller = new EditingController( model, stylesProcessor ); + controller = new EditingController( model, new StylesProcessor() ); viewRoot = controller.view.document.getRoot(); // Set name of view root the same as dom root. @@ -1508,7 +1505,7 @@ describe( 'downcast converters', () => { let viewDocument; beforeEach( () => { - viewDocument = new ViewDocument( stylesProcessor ); + viewDocument = new ViewDocument( new StylesProcessor() ); } ); it( 'should remove items from view accordingly to changes in model #1', () => { @@ -1790,10 +1787,8 @@ describe( 'downcast converters', () => { describe( 'downcast selection converters', () => { let dispatcher, mapper, model, view, modelDoc, modelRoot, docSelection, viewDoc, viewRoot, viewSelection, downcastHelpers; - let stylesProcessor; beforeEach( () => { - stylesProcessor = new StylesProcessor(); model = new Model(); modelDoc = model.document; modelRoot = modelDoc.createRoot(); @@ -1801,7 +1796,7 @@ describe( 'downcast selection converters', () => { model.schema.extend( '$text', { allowIn: '$root' } ); - view = new View( stylesProcessor ); + view = new View( new StylesProcessor() ); viewDoc = view.document; viewRoot = createViewRoot( viewDoc ); viewSelection = viewDoc.selection; @@ -1931,7 +1926,7 @@ describe( 'downcast selection converters', () => { let marker, viewDocument; beforeEach( () => { - viewDocument = new ViewDocument( stylesProcessor ); + viewDocument = new ViewDocument( new StylesProcessor() ); } ); it( 'in container', () => { diff --git a/tests/conversion/mapper.js b/tests/conversion/mapper.js index 94c848136..2ddea3ad1 100644 --- a/tests/conversion/mapper.js +++ b/tests/conversion/mapper.js @@ -20,11 +20,10 @@ import ViewRange from '../../src/view/range'; import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'Mapper', () => { - let viewDocument, stylesProcessor; + let viewDocument; beforeEach( () => { - stylesProcessor = new StylesProcessor(); - viewDocument = new ViewDocument( stylesProcessor ); + viewDocument = new ViewDocument( new StylesProcessor() ); } ); describe( 'clearBindings', () => { diff --git a/tests/conversion/upcastdispatcher.js b/tests/conversion/upcastdispatcher.js index 008a68cf1..d40dae0ca 100644 --- a/tests/conversion/upcastdispatcher.js +++ b/tests/conversion/upcastdispatcher.js @@ -24,12 +24,11 @@ import { expectToThrowCKEditorError } from '@ckeditor/ckeditor5-utils/tests/_uti import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'UpcastDispatcher', () => { - let model, viewDocument, stylesProcessor; + let model, viewDocument; beforeEach( () => { model = new Model(); - stylesProcessor = new StylesProcessor(); - viewDocument = new ViewDocument( stylesProcessor ); + viewDocument = new ViewDocument( new StylesProcessor() ); } ); describe( 'constructor()', () => { diff --git a/tests/conversion/upcasthelpers.js b/tests/conversion/upcasthelpers.js index 3e30a8925..8b3f6499d 100644 --- a/tests/conversion/upcasthelpers.js +++ b/tests/conversion/upcasthelpers.js @@ -33,15 +33,9 @@ import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'UpcastHelpers', () => { let upcastDispatcher, model, schema, upcastHelpers, viewDocument; - let stylesProcessor; - - before( () => { - stylesProcessor = new StylesProcessor(); - } ); - beforeEach( () => { model = new Model(); - viewDocument = new ViewDocument( stylesProcessor ); + viewDocument = new ViewDocument( new StylesProcessor() ); schema = model.schema; @@ -705,13 +699,11 @@ describe( 'UpcastHelpers', () => { } ); describe( 'upcast-converters', () => { - let dispatcher, schema, context, model, viewDocument, stylesProcessor; + let dispatcher, schema, context, model, viewDocument; beforeEach( () => { - stylesProcessor = new StylesProcessor(); - model = new Model(); - viewDocument = new ViewDocument( stylesProcessor ); + viewDocument = new ViewDocument( new StylesProcessor() ); schema = model.schema; schema.register( 'paragraph', { inheritAllFrom: '$block' } ); @@ -885,7 +877,7 @@ describe( 'upcast-converters', () => { modelSetData( model, 'foobar' ); - view = new View( stylesProcessor ); + view = new View( new StylesProcessor() ); viewDocument = view.document; viewRoot = createViewRoot( viewDocument, 'div', 'main' ); diff --git a/tests/conversion/viewconsumable.js b/tests/conversion/viewconsumable.js index c3d6f2be3..9d168ccc7 100644 --- a/tests/conversion/viewconsumable.js +++ b/tests/conversion/viewconsumable.js @@ -14,10 +14,10 @@ import { addPaddingRules } from '../../src/view/styles/padding'; import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'ViewConsumable', () => { - let viewConsumable, el, viewDocument, stylesProcessor; + let viewConsumable, el, viewDocument; beforeEach( () => { - stylesProcessor = new StylesProcessor(); + const stylesProcessor = new StylesProcessor(); viewDocument = new ViewDocument( stylesProcessor ); addBorderRules( stylesProcessor ); diff --git a/tests/dataprocessor/htmldataprocessor.js b/tests/dataprocessor/htmldataprocessor.js index 475babd9e..644b8f6d4 100644 --- a/tests/dataprocessor/htmldataprocessor.js +++ b/tests/dataprocessor/htmldataprocessor.js @@ -13,11 +13,10 @@ import { StylesProcessor } from '../../src/view/stylesmap'; import ViewDocument from '../../src/view/document'; describe( 'HtmlDataProcessor', () => { - let stylesProcessor, dataProcessor, viewDocument; + let dataProcessor, viewDocument; beforeEach( () => { - stylesProcessor = new StylesProcessor(); - viewDocument = new ViewDocument( stylesProcessor ); + viewDocument = new ViewDocument( new StylesProcessor() ); dataProcessor = new HtmlDataProcessor( viewDocument ); } ); diff --git a/tests/dataprocessor/xmldataprocessor.js b/tests/dataprocessor/xmldataprocessor.js index 18764bc08..b262eb4b8 100644 --- a/tests/dataprocessor/xmldataprocessor.js +++ b/tests/dataprocessor/xmldataprocessor.js @@ -13,11 +13,10 @@ import { stringify, parse } from '../../src/dev-utils/view'; import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'XmlDataProcessor', () => { - let stylesProcessor, dataProcessor, viewDocument; + let dataProcessor, viewDocument; beforeEach( () => { - stylesProcessor = new StylesProcessor(); - viewDocument = new ViewDocument( stylesProcessor ); + viewDocument = new ViewDocument( new StylesProcessor() ); dataProcessor = new XmlDataProcessor( viewDocument ); } ); diff --git a/tests/dev-utils/view.js b/tests/dev-utils/view.js index 2d7e1a584..27ee96320 100644 --- a/tests/dev-utils/view.js +++ b/tests/dev-utils/view.js @@ -23,12 +23,6 @@ import createViewRoot from '../view/_utils/createroot'; import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'view test utils', () => { - let stylesProcessor; - - beforeEach( () => { - stylesProcessor = new StylesProcessor(); - } ); - describe( 'getData, setData', () => { afterEach( () => { sinon.restore(); @@ -38,7 +32,7 @@ describe( 'view test utils', () => { it( 'should use stringify method', () => { const element = document.createElement( 'div' ); const stringifySpy = sinon.spy( getData, '_stringify' ); - const view = new View( stylesProcessor ); + const view = new View( new StylesProcessor() ); const viewDocument = view.document; const options = { showType: false, @@ -65,7 +59,7 @@ describe( 'view test utils', () => { it( 'should use stringify method with selection', () => { const element = document.createElement( 'div' ); const stringifySpy = sinon.spy( getData, '_stringify' ); - const view = new View( stylesProcessor ); + const view = new View( new StylesProcessor() ); const viewDocument = view.document; const options = { showType: false, showPriority: false }; const root = createAttachedRoot( viewDocument, element ); @@ -96,7 +90,7 @@ describe( 'view test utils', () => { describe( 'setData', () => { it( 'should use parse method', () => { - const view = new View( stylesProcessor ); + const view = new View( new StylesProcessor() ); const viewDocument = view.document; const data = 'foobarbaz'; const parseSpy = sinon.spy( setData, '_parse' ); @@ -115,7 +109,7 @@ describe( 'view test utils', () => { } ); it( 'should use parse method with selection', () => { - const view = new View( stylesProcessor ); + const view = new View( new StylesProcessor() ); const viewDocument = view.document; const data = '[baz]'; const parseSpy = sinon.spy( setData, '_parse' ); @@ -144,7 +138,7 @@ describe( 'view test utils', () => { let viewDocument; beforeEach( () => { - viewDocument = new ViewDocument( stylesProcessor ); + viewDocument = new ViewDocument( new StylesProcessor() ); } ); it( 'should write text', () => { @@ -433,7 +427,7 @@ describe( 'view test utils', () => { let viewDocument; beforeEach( () => { - viewDocument = new ViewDocument( stylesProcessor ); + viewDocument = new ViewDocument( new StylesProcessor() ); } ); it( 'should return empty DocumentFragment for empty string', () => { diff --git a/tests/tickets/1323.js b/tests/tickets/1323.js index f0f10dbad..de86e04f1 100644 --- a/tests/tickets/1323.js +++ b/tests/tickets/1323.js @@ -13,12 +13,11 @@ import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'Bug ckeditor5-engine@1323', () => { describe( 'constructor()', () => { - let model, editing, root, range, stylesProcessor; + let model, editing, root, range; beforeEach( () => { - stylesProcessor = new StylesProcessor(); model = new Model(); - editing = new EditingController( model, stylesProcessor ); + editing = new EditingController( model, new StylesProcessor() ); root = model.document.createRoot(); root._appendChild( new ModelText( 'foo' ) ); range = model.createRange( model.createPositionAt( root, 0 ), model.createPositionAt( root, 0 ) ); diff --git a/tests/view/attributeelement.js b/tests/view/attributeelement.js index f0bcf58b3..d565c9272 100644 --- a/tests/view/attributeelement.js +++ b/tests/view/attributeelement.js @@ -12,11 +12,9 @@ import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'AttributeElement', () => { let document; - let stylesProcessor; beforeEach( () => { - stylesProcessor = new StylesProcessor(); - document = new Document( stylesProcessor ); + document = new Document( new StylesProcessor() ); } ); describe( 'constructor()', () => { @@ -154,7 +152,7 @@ describe( 'AttributeElement', () => { describe( 'getFillerOffset', () => { it( 'should return position 0 if it is the only element in the container', () => { - const { selection } = parse( '[]', { stylesProcessor } ); + const { selection } = parse( '[]' ); const attribute = selection.getFirstPosition().parent; expect( attribute.getFillerOffset() ).to.equals( 0 ); @@ -162,26 +160,26 @@ describe( 'AttributeElement', () => { it( 'should return position 0 if it is the only nested element in the container', () => { const { selection } = parse( - '[]', { stylesProcessor } ); + '[]' ); const attribute = selection.getFirstPosition().parent; expect( attribute.getFillerOffset() ).to.equals( 0 ); } ); it( 'should return null if element contains another element', () => { - const attribute = parse( '', { stylesProcessor } ); + const attribute = parse( '' ); expect( attribute.getFillerOffset() ).to.be.null; } ); it( 'should return null if element contains text', () => { - const attribute = parse( 'text', { stylesProcessor } ); + const attribute = parse( 'text' ); expect( attribute.getFillerOffset() ).to.be.null; } ); it( 'should return null if container element contains text', () => { - const { selection } = parse( '[]foo', { stylesProcessor } ); + const { selection } = parse( '[]foo' ); const attribute = selection.getFirstPosition().parent; expect( attribute.getFillerOffset() ).to.be.null; @@ -189,14 +187,14 @@ describe( 'AttributeElement', () => { it( 'should return null if it is the parent contains text', () => { const { selection } = parse( - '[]foo', { stylesProcessor } ); + '[]foo' ); const attribute = selection.getFirstPosition().parent; expect( attribute.getFillerOffset() ).to.be.null; } ); it( 'should return null if there is no parent container element', () => { - const { selection } = parse( '[]foo', { stylesProcessor } ); + const { selection } = parse( '[]foo' ); const attribute = selection.getFirstPosition().parent; expect( attribute.getFillerOffset() ).to.be.null; @@ -210,8 +208,7 @@ describe( 'AttributeElement', () => { it( 'should return offset after all children if it is the only nested element in the container and has UIElement inside', () => { const { selection } = parse( - '[]', - { stylesProcessor } + '[]' ); const attribute = selection.getFirstPosition().parent; @@ -219,7 +216,7 @@ describe( 'AttributeElement', () => { } ); it( 'should return offset after all children if there is no parent container element and has UIElement inside', () => { - const { selection } = parse( '[]', { stylesProcessor } ); + const { selection } = parse( '[]' ); const attribute = selection.getFirstPosition().parent; expect( attribute.getFillerOffset() ).to.equal( 2 ); diff --git a/tests/view/containerelement.js b/tests/view/containerelement.js index fba18c798..419a6be9f 100644 --- a/tests/view/containerelement.js +++ b/tests/view/containerelement.js @@ -10,11 +10,10 @@ import { parse } from '../../src/dev-utils/view'; import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'ContainerElement', () => { - let document, stylesProcessor; + let document; beforeEach( () => { - stylesProcessor = new StylesProcessor(); - document = new Document( stylesProcessor ); + document = new Document( new StylesProcessor() ); } ); describe( 'constructor()', () => { diff --git a/tests/view/document.js b/tests/view/document.js index 9d02eb6fc..5e42a0cbd 100644 --- a/tests/view/document.js +++ b/tests/view/document.js @@ -13,20 +13,18 @@ import createViewRoot from './_utils/createroot'; import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'Document', () => { - let domRoot, viewDocument, stylesProcessor; + let domRoot, viewDocument; testUtils.createSinonSandbox(); beforeEach( () => { - stylesProcessor = new StylesProcessor(); - domRoot = createElement( document, 'div', { id: 'editor', contenteditable: 'true' } ); document.body.appendChild( domRoot ); - viewDocument = new Document( stylesProcessor ); + viewDocument = new Document( new StylesProcessor() ); } ); afterEach( () => { diff --git a/tests/view/documentfragment.js b/tests/view/documentfragment.js index 4be51880d..7e86b3c39 100644 --- a/tests/view/documentfragment.js +++ b/tests/view/documentfragment.js @@ -12,11 +12,10 @@ import Document from '../../src/view/document'; import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'DocumentFragment', () => { - let document, stylesProcessor; + let document; beforeEach( () => { - stylesProcessor = new StylesProcessor(); - document = new Document( stylesProcessor ); + document = new Document( new StylesProcessor() ); } ); describe( 'constructor()', () => { diff --git a/tests/view/documentselection.js b/tests/view/documentselection.js index 2988c6047..24dd0e03a 100644 --- a/tests/view/documentselection.js +++ b/tests/view/documentselection.js @@ -19,13 +19,11 @@ import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'DocumentSelection', () => { let documentSelection, el, range1, range2, range3, document; - let stylesProcessor; testUtils.createSinonSandbox(); beforeEach( () => { - stylesProcessor = new StylesProcessor(); - document = new Document( stylesProcessor ); + document = new Document( new StylesProcessor() ); const text = new Text( document, 'xxxxxxxxxxxxxxxxxxxx' ); el = new Element( document, 'p', null, text ); @@ -1088,7 +1086,7 @@ describe( 'DocumentSelection', () => { } ); it( 'should return EditableElement when selection is placed inside', () => { - const viewDocument = new Document( stylesProcessor ); + const viewDocument = new Document( new StylesProcessor() ); documentSelection._setTo( viewDocument.selection ); const root = createViewRoot( viewDocument, 'div', 'main' ); const element = new Element( document, 'p' ); diff --git a/tests/view/domconverter/binding.js b/tests/view/domconverter/binding.js index d5094e89c..999d1b8d8 100644 --- a/tests/view/domconverter/binding.js +++ b/tests/view/domconverter/binding.js @@ -18,11 +18,10 @@ import createElement from '@ckeditor/ckeditor5-utils/src/dom/createelement'; import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'DomConverter', () => { - let converter, viewDocument, stylesProcessor; + let converter, viewDocument; beforeEach( () => { - stylesProcessor = new StylesProcessor(); - viewDocument = new ViewDocument( stylesProcessor ); + viewDocument = new ViewDocument( new StylesProcessor() ); converter = new DomConverter( viewDocument ); } ); @@ -151,7 +150,7 @@ describe( 'DomConverter', () => { const domText = document.createTextNode( 'x' ); const domP = createElement( document, 'p', null, [ domB, domText, domI ] ); - const viewP = parse( '

', { stylesProcessor } ); + const viewP = parse( '

' ); const viewB = viewP.getChild( 0 ); const viewI = viewP.getChild( 1 ); @@ -166,7 +165,7 @@ describe( 'DomConverter', () => { const domText = document.createTextNode( 'x' ); const domP = createElement( document, 'p', null, domText ); - const viewP = parse( '

', { stylesProcessor } ); + const viewP = parse( '

' ); converter.bindElements( domP, viewP ); diff --git a/tests/view/domconverter/dom-to-view.js b/tests/view/domconverter/dom-to-view.js index 43c57178b..2e2b942bf 100644 --- a/tests/view/domconverter/dom-to-view.js +++ b/tests/view/domconverter/dom-to-view.js @@ -18,11 +18,10 @@ import count from '@ckeditor/ckeditor5-utils/src/count'; import createElement from '@ckeditor/ckeditor5-utils/src/dom/createelement'; describe( 'DomConverter', () => { - let converter, viewDocument, stylesProcessor; + let converter, viewDocument; before( () => { - stylesProcessor = new StylesProcessor(); - viewDocument = new ViewDocument( stylesProcessor ); + viewDocument = new ViewDocument( new StylesProcessor() ); converter = new DomConverter( viewDocument ); } ); diff --git a/tests/view/domconverter/domconverter.js b/tests/view/domconverter/domconverter.js index c3c62dee9..fa72f72fd 100644 --- a/tests/view/domconverter/domconverter.js +++ b/tests/view/domconverter/domconverter.js @@ -16,13 +16,12 @@ import global from '@ckeditor/ckeditor5-utils/src/dom/global'; import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'DomConverter', () => { - let converter, stylesProcessor, viewDocument; + let converter, viewDocument; testUtils.createSinonSandbox(); beforeEach( () => { - stylesProcessor = new StylesProcessor(); - viewDocument = new ViewDocument( stylesProcessor ); + viewDocument = new ViewDocument( new StylesProcessor() ); converter = new DomConverter( viewDocument ); } ); @@ -41,7 +40,7 @@ describe( 'DomConverter', () => { let viewEditable, domEditable, domEditableParent, viewDocument; beforeEach( () => { - viewDocument = new ViewDocument( stylesProcessor ); + viewDocument = new ViewDocument( new StylesProcessor() ); viewEditable = new ViewEditable( viewDocument, 'div' ); domEditable = document.createElement( 'div' ); @@ -205,7 +204,7 @@ describe( 'DomConverter', () => { domUiDeepSpan = document.createElement( 'span' ); domUiSpan.appendChild( domUiDeepSpan ); - viewDocument = new ViewDocument( stylesProcessor ); + viewDocument = new ViewDocument( new StylesProcessor() ); const viewUiSpan = new ViewUIElement( viewDocument, 'span' ); const viewElementSpan = new ViewContainerElement( viewDocument, 'span' ); diff --git a/tests/view/domconverter/uielement.js b/tests/view/domconverter/uielement.js index 353fe9ddc..90eec9c51 100644 --- a/tests/view/domconverter/uielement.js +++ b/tests/view/domconverter/uielement.js @@ -12,7 +12,7 @@ import ViewDocument from '../../../src/view/document'; import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'DOMConverter UIElement integration', () => { - let converter, viewDocument, stylesProcessor; + let converter, viewDocument; function createUIElement( name ) { const element = new ViewUIElement( viewDocument, name ); @@ -28,8 +28,7 @@ describe( 'DOMConverter UIElement integration', () => { } beforeEach( () => { - stylesProcessor = new StylesProcessor(); - viewDocument = new ViewDocument( stylesProcessor ); + viewDocument = new ViewDocument( new StylesProcessor() ); converter = new DomConverter( viewDocument ); } ); diff --git a/tests/view/domconverter/view-to-dom.js b/tests/view/domconverter/view-to-dom.js index 1ad1d924d..6f7e9d6f5 100644 --- a/tests/view/domconverter/view-to-dom.js +++ b/tests/view/domconverter/view-to-dom.js @@ -22,11 +22,10 @@ import createElement from '@ckeditor/ckeditor5-utils/src/dom/createelement'; import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'DomConverter', () => { - let converter, viewDocument, stylesProcessor; + let converter, viewDocument; beforeEach( () => { - stylesProcessor = new StylesProcessor(); - viewDocument = new ViewDocument( stylesProcessor ); + viewDocument = new ViewDocument( new StylesProcessor() ); converter = new DomConverter( viewDocument ); } ); diff --git a/tests/view/downcastwriter/breakattributes.js b/tests/view/downcastwriter/breakattributes.js index 5b97491cd..c6262b471 100644 --- a/tests/view/downcastwriter/breakattributes.js +++ b/tests/view/downcastwriter/breakattributes.js @@ -17,17 +17,11 @@ import { expectToThrowCKEditorError } from '@ckeditor/ckeditor5-utils/tests/_uti import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'DowncastWriter', () => { - let stylesProcessor; - - beforeEach( () => { - stylesProcessor = new StylesProcessor(); - } ); - describe( 'breakAttributes()', () => { let writer, document; beforeEach( () => { - document = new Document( stylesProcessor ); + document = new Document( new StylesProcessor() ); writer = new DowncastWriter( document ); } ); diff --git a/tests/view/downcastwriter/breakcontainer.js b/tests/view/downcastwriter/breakcontainer.js index af4fc9a69..4a2e5b095 100644 --- a/tests/view/downcastwriter/breakcontainer.js +++ b/tests/view/downcastwriter/breakcontainer.js @@ -13,12 +13,6 @@ import { expectToThrowCKEditorError } from '@ckeditor/ckeditor5-utils/tests/_uti import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'DowncastWriter', () => { - let stylesProcessor; - - beforeEach( () => { - stylesProcessor = new StylesProcessor(); - } ); - describe( 'breakContainer()', () => { let writer, document; @@ -35,7 +29,7 @@ describe( 'DowncastWriter', () => { } before( () => { - document = new Document( stylesProcessor ); + document = new Document( new StylesProcessor() ); writer = new DowncastWriter( document ); } ); diff --git a/tests/view/downcastwriter/clear.js b/tests/view/downcastwriter/clear.js index aca7ee629..403438140 100644 --- a/tests/view/downcastwriter/clear.js +++ b/tests/view/downcastwriter/clear.js @@ -16,12 +16,6 @@ import { expectToThrowCKEditorError } from '@ckeditor/ckeditor5-utils/tests/_uti import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'DowncastWriter', () => { - let stylesProcessor; - - beforeEach( () => { - stylesProcessor = new StylesProcessor(); - } ); - describe( 'clear()', () => { let writer, document; @@ -39,7 +33,7 @@ describe( 'DowncastWriter', () => { } beforeEach( () => { - document = new Document( stylesProcessor ); + document = new Document( new StylesProcessor() ); writer = new DowncastWriter( document ); } ); diff --git a/tests/view/downcastwriter/insert.js b/tests/view/downcastwriter/insert.js index e8a6b621f..f3957dd00 100644 --- a/tests/view/downcastwriter/insert.js +++ b/tests/view/downcastwriter/insert.js @@ -17,12 +17,6 @@ import { expectToThrowCKEditorError } from '@ckeditor/ckeditor5-utils/tests/_uti import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'DowncastWriter', () => { - let stylesProcessor; - - beforeEach( () => { - stylesProcessor = new StylesProcessor(); - } ); - describe( 'insert()', () => { let writer, document; @@ -41,7 +35,7 @@ describe( 'DowncastWriter', () => { } beforeEach( () => { - document = new Document( stylesProcessor ); + document = new Document( new StylesProcessor() ); writer = new DowncastWriter( document ); } ); diff --git a/tests/view/downcastwriter/mergeattributes.js b/tests/view/downcastwriter/mergeattributes.js index d727bbf42..5f55611ef 100644 --- a/tests/view/downcastwriter/mergeattributes.js +++ b/tests/view/downcastwriter/mergeattributes.js @@ -12,12 +12,6 @@ import Document from '../../../src/view/document'; import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'DowncastWriter', () => { - let stylesProcessor; - - beforeEach( () => { - stylesProcessor = new StylesProcessor(); - } ); - describe( 'mergeAttributes', () => { let writer, document; @@ -33,7 +27,7 @@ describe( 'DowncastWriter', () => { } before( () => { - document = new Document( stylesProcessor ); + document = new Document( new StylesProcessor() ); writer = new DowncastWriter( document ); } ); diff --git a/tests/view/downcastwriter/mergecontainers.js b/tests/view/downcastwriter/mergecontainers.js index 8441d2c5b..2a234927c 100644 --- a/tests/view/downcastwriter/mergecontainers.js +++ b/tests/view/downcastwriter/mergecontainers.js @@ -11,12 +11,6 @@ import { expectToThrowCKEditorError } from '@ckeditor/ckeditor5-utils/tests/_uti import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'DowncastWriter', () => { - let stylesProcessor; - - beforeEach( () => { - stylesProcessor = new StylesProcessor(); - } ); - describe( 'mergeContainers()', () => { let writer; @@ -33,7 +27,7 @@ describe( 'DowncastWriter', () => { } before( () => { - writer = new DowncastWriter( new Document( stylesProcessor ) ); + writer = new DowncastWriter( new Document( new StylesProcessor() ) ); } ); it( 'should merge two container elements - position between elements', () => { diff --git a/tests/view/downcastwriter/move.js b/tests/view/downcastwriter/move.js index 39e6dd926..5fc958290 100644 --- a/tests/view/downcastwriter/move.js +++ b/tests/view/downcastwriter/move.js @@ -19,12 +19,6 @@ import { expectToThrowCKEditorError } from '@ckeditor/ckeditor5-utils/tests/_uti import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'DowncastWriter', () => { - let stylesProcessor; - - beforeEach( () => { - stylesProcessor = new StylesProcessor(); - } ); - describe( 'move()', () => { let writer, document; @@ -45,7 +39,7 @@ describe( 'DowncastWriter', () => { } before( () => { - document = new Document( stylesProcessor ); + document = new Document( new StylesProcessor() ); writer = new DowncastWriter( document ); } ); diff --git a/tests/view/downcastwriter/remove.js b/tests/view/downcastwriter/remove.js index 6f04b5ec5..2452663f1 100644 --- a/tests/view/downcastwriter/remove.js +++ b/tests/view/downcastwriter/remove.js @@ -17,12 +17,6 @@ import { expectToThrowCKEditorError } from '@ckeditor/ckeditor5-utils/tests/_uti import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'DowncastWriter', () => { - let stylesProcessor; - - beforeEach( () => { - stylesProcessor = new StylesProcessor(); - } ); - describe( 'remove()', () => { let writer, document; @@ -45,7 +39,7 @@ describe( 'DowncastWriter', () => { } beforeEach( () => { - document = new Document( stylesProcessor ); + document = new Document( new StylesProcessor() ); writer = new DowncastWriter( document ); } ); diff --git a/tests/view/downcastwriter/rename.js b/tests/view/downcastwriter/rename.js index c378c1e7a..46b7e142d 100644 --- a/tests/view/downcastwriter/rename.js +++ b/tests/view/downcastwriter/rename.js @@ -9,17 +9,11 @@ import Document from '../../../src/view/document'; import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'DowncastWriter', () => { - let stylesProcessor; - - beforeEach( () => { - stylesProcessor = new StylesProcessor(); - } ); - describe( 'rename()', () => { let root, foo, writer; before( () => { - writer = new DowncastWriter( new Document( stylesProcessor ) ); + writer = new DowncastWriter( new Document( new StylesProcessor() ) ); } ); beforeEach( () => { diff --git a/tests/view/downcastwriter/unwrap.js b/tests/view/downcastwriter/unwrap.js index bb6084ad5..30e02baa4 100644 --- a/tests/view/downcastwriter/unwrap.js +++ b/tests/view/downcastwriter/unwrap.js @@ -19,12 +19,6 @@ import { expectToThrowCKEditorError } from '@ckeditor/ckeditor5-utils/tests/_uti import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'DowncastWriter', () => { - let stylesProcessor; - - beforeEach( () => { - stylesProcessor = new StylesProcessor(); - } ); - describe( 'unwrap()', () => { let writer, document; @@ -41,7 +35,7 @@ describe( 'DowncastWriter', () => { } beforeEach( () => { - document = new Document( stylesProcessor ); + document = new Document( new StylesProcessor() ); writer = new DowncastWriter( document ); } ); diff --git a/tests/view/downcastwriter/wrap.js b/tests/view/downcastwriter/wrap.js index 45ca7d949..f73a4c593 100644 --- a/tests/view/downcastwriter/wrap.js +++ b/tests/view/downcastwriter/wrap.js @@ -22,17 +22,11 @@ import { expectToThrowCKEditorError } from '@ckeditor/ckeditor5-utils/tests/_uti import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'DowncastWriter', () => { - let stylesProcessor; - - beforeEach( () => { - stylesProcessor = new StylesProcessor(); - } ); - describe( 'wrap()', () => { let writer, document; beforeEach( () => { - document = new Document( stylesProcessor ); + document = new Document( new StylesProcessor() ); writer = new DowncastWriter( document ); } ); @@ -527,7 +521,7 @@ describe( 'DowncastWriter', () => { let view, viewDocument, viewRoot; beforeEach( () => { - view = new View( stylesProcessor ); + view = new View( new StylesProcessor() ); viewDocument = view.document; viewRoot = createViewRoot( viewDocument ); } ); diff --git a/tests/view/downcastwriter/writer.js b/tests/view/downcastwriter/writer.js index 46e3e8060..971f1d428 100644 --- a/tests/view/downcastwriter/writer.js +++ b/tests/view/downcastwriter/writer.js @@ -15,15 +15,10 @@ import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'DowncastWriter', () => { let writer, attributes, root, doc; - let stylesProcessor; - - beforeEach( () => { - stylesProcessor = new StylesProcessor(); - } ); beforeEach( () => { attributes = { foo: 'bar', baz: 'quz' }; - doc = new Document( stylesProcessor ); + doc = new Document( new StylesProcessor() ); root = createViewRoot( doc ); writer = new DowncastWriter( doc ); } ); diff --git a/tests/view/editableelement.js b/tests/view/editableelement.js index 7aac2a705..b956dbf5c 100644 --- a/tests/view/editableelement.js +++ b/tests/view/editableelement.js @@ -11,17 +11,11 @@ import Document from '../../src/view/document'; import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'EditableElement', () => { - let stylesProcessor; - - before( () => { - stylesProcessor = new StylesProcessor(); - } ); - describe( 'is', () => { let el; before( () => { - el = new EditableElement( new Document( stylesProcessor ), 'div' ); + el = new EditableElement( new Document( new StylesProcessor() ), 'div' ); } ); it( 'should return true for containerElement/editable/element, also with correct name and element name', () => { diff --git a/tests/view/element.js b/tests/view/element.js index 82e02a181..1a4bbd498 100644 --- a/tests/view/element.js +++ b/tests/view/element.js @@ -12,11 +12,10 @@ import Document from '../../src/view/document'; import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'Element', () => { - let document, stylesProcessor; + let document; beforeEach( () => { - stylesProcessor = new StylesProcessor(); - document = new Document( stylesProcessor ); + document = new Document( new StylesProcessor() ); } ); describe( 'constructor()', () => { @@ -412,7 +411,7 @@ describe( 'Element', () => { } ); it( 'set proper #document on inserted children', () => { - const anotherDocument = new Document( stylesProcessor ); + const anotherDocument = new Document( new StylesProcessor() ); const anotherEl = new Element( anotherDocument, 'p' ); parent._insertChild( 0, anotherEl ); diff --git a/tests/view/emptyelement.js b/tests/view/emptyelement.js index 23448aa2d..e1696a5b2 100644 --- a/tests/view/emptyelement.js +++ b/tests/view/emptyelement.js @@ -11,11 +11,10 @@ import { expectToThrowCKEditorError } from '@ckeditor/ckeditor5-utils/tests/_uti import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'EmptyElement', () => { - let element, emptyElement, document, stylesProcessor; + let element, emptyElement, document; beforeEach( () => { - stylesProcessor = new StylesProcessor(); - document = new Document( stylesProcessor ); + document = new Document( new StylesProcessor() ); element = new Element( document, 'b' ); emptyElement = new EmptyElement( document, 'img', { alt: 'alternative text', diff --git a/tests/view/matcher.js b/tests/view/matcher.js index 1c620e51c..3b78b67db 100644 --- a/tests/view/matcher.js +++ b/tests/view/matcher.js @@ -9,11 +9,10 @@ import Document from '../../src/view/document'; import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'Matcher', () => { - let document, stylesProcessor; + let document; beforeEach( () => { - stylesProcessor = new StylesProcessor(); - document = new Document( stylesProcessor ); + document = new Document( new StylesProcessor() ); } ); describe( 'add', () => { diff --git a/tests/view/node.js b/tests/view/node.js index 62e791e46..53d81b16b 100644 --- a/tests/view/node.js +++ b/tests/view/node.js @@ -17,12 +17,10 @@ import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'Node', () => { let root, document, one, two, three, - charB, charA, charR, img, - stylesProcessor; + charB, charA, charR, img; before( () => { - stylesProcessor = new StylesProcessor(); - document = new Document( stylesProcessor ); + document = new Document( new StylesProcessor() ); charB = new Text( document, 'b' ); charA = new Text( document, 'a' ); diff --git a/tests/view/observer/clickobserver.js b/tests/view/observer/clickobserver.js index 1efb9cabd..baf7a18d0 100644 --- a/tests/view/observer/clickobserver.js +++ b/tests/view/observer/clickobserver.js @@ -10,11 +10,10 @@ import View from '../../../src/view/view'; import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'ClickObserver', () => { - let view, viewDocument, observer, stylesProcessor; + let view, viewDocument, observer; beforeEach( () => { - stylesProcessor = new StylesProcessor(); - view = new View( stylesProcessor ); + view = new View( new StylesProcessor() ); viewDocument = view.document; observer = view.addObserver( ClickObserver ); } ); diff --git a/tests/view/observer/compositionobserver.js b/tests/view/observer/compositionobserver.js index 2eb11a0dd..1d2ed1e2f 100644 --- a/tests/view/observer/compositionobserver.js +++ b/tests/view/observer/compositionobserver.js @@ -9,11 +9,10 @@ import View from '../../../src/view/view'; import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'CompositionObserver', () => { - let view, viewDocument, observer, stylesProcessor; + let view, viewDocument, observer; beforeEach( () => { - stylesProcessor = new StylesProcessor(); - view = new View( stylesProcessor ); + view = new View( new StylesProcessor() ); viewDocument = view.document; observer = view.getObserver( CompositionObserver ); } ); diff --git a/tests/view/observer/domeventdata.js b/tests/view/observer/domeventdata.js index 8c17e7b5a..7b7f2a390 100644 --- a/tests/view/observer/domeventdata.js +++ b/tests/view/observer/domeventdata.js @@ -10,11 +10,10 @@ import View from '../../../src/view/view'; import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'DomEventData', () => { - let view, viewDocument, viewBody, domRoot, stylesProcessor; + let view, viewDocument, viewBody, domRoot; beforeEach( () => { - stylesProcessor = new StylesProcessor(); - view = new View( stylesProcessor ); + view = new View( new StylesProcessor() ); viewDocument = view.document; domRoot = document.createElement( 'div' ); diff --git a/tests/view/observer/domeventobserver.js b/tests/view/observer/domeventobserver.js index 1041733f0..a7c05bbe4 100644 --- a/tests/view/observer/domeventobserver.js +++ b/tests/view/observer/domeventobserver.js @@ -45,11 +45,10 @@ class ClickCapturingObserver extends ClickObserver { } describe( 'DomEventObserver', () => { - let view, viewDocument, stylesProcessor; + let view, viewDocument; beforeEach( () => { - stylesProcessor = new StylesProcessor(); - view = new View( stylesProcessor ); + view = new View( new StylesProcessor() ); viewDocument = view.document; } ); diff --git a/tests/view/observer/fakeselectionobserver.js b/tests/view/observer/fakeselectionobserver.js index 4b1d2723d..223f6fc7c 100644 --- a/tests/view/observer/fakeselectionobserver.js +++ b/tests/view/observer/fakeselectionobserver.js @@ -16,12 +16,10 @@ import testUtils from '@ckeditor/ckeditor5-core/tests/_utils/utils'; import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'FakeSelectionObserver', () => { - let observer, view, viewDocument, root, domRoot, stylesProcessor; + let observer, view, viewDocument, root, domRoot; testUtils.createSinonSandbox(); before( () => { - stylesProcessor = new StylesProcessor(); - domRoot = createElement( document, 'div', { contenteditable: 'true' } ); @@ -33,7 +31,7 @@ describe( 'FakeSelectionObserver', () => { } ); beforeEach( () => { - view = new View( stylesProcessor ); + view = new View( new StylesProcessor() ); viewDocument = view.document; root = createViewRoot( viewDocument ); view.attachDomRoot( domRoot ); diff --git a/tests/view/observer/focusobserver.js b/tests/view/observer/focusobserver.js index 330d60ce9..62c81d77e 100644 --- a/tests/view/observer/focusobserver.js +++ b/tests/view/observer/focusobserver.js @@ -11,11 +11,10 @@ import { setData } from '../../../src/dev-utils/view'; import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'FocusObserver', () => { - let view, viewDocument, observer, stylesProcessor; + let view, viewDocument, observer; beforeEach( () => { - stylesProcessor = new StylesProcessor(); - view = new View( stylesProcessor ); + view = new View( new StylesProcessor() ); viewDocument = view.document; observer = view.getObserver( FocusObserver ); } ); @@ -159,7 +158,7 @@ describe( 'FocusObserver', () => { domRoot = document.createElement( 'div' ); document.body.appendChild( domRoot ); - view = new View( stylesProcessor ); + view = new View( new StylesProcessor() ); viewDocument = view.document; createViewRoot( viewDocument ); view.attachDomRoot( domRoot ); diff --git a/tests/view/observer/inputobserver.js b/tests/view/observer/inputobserver.js index cea6b0eab..f007a811e 100644 --- a/tests/view/observer/inputobserver.js +++ b/tests/view/observer/inputobserver.js @@ -11,15 +11,14 @@ import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'InputObserver', () => { const oldEnvIsAndroid = env.isAndroid; - let view, viewDocument, observer, stylesProcessor; + let view, viewDocument, observer; before( () => { env.isAndroid = true; } ); beforeEach( () => { - stylesProcessor = new StylesProcessor(); - view = new View( stylesProcessor ); + view = new View( new StylesProcessor() ); viewDocument = view.document; observer = view.getObserver( InputObserver ); } ); diff --git a/tests/view/observer/keyobserver.js b/tests/view/observer/keyobserver.js index 3e85e5990..a564e43a8 100644 --- a/tests/view/observer/keyobserver.js +++ b/tests/view/observer/keyobserver.js @@ -11,11 +11,10 @@ import { getCode } from '@ckeditor/ckeditor5-utils/src/keyboard'; import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'KeyObserver', () => { - let view, viewDocument, observer, stylesProcessor; + let view, viewDocument, observer; beforeEach( () => { - stylesProcessor = new StylesProcessor(); - view = new View( stylesProcessor ); + view = new View( new StylesProcessor() ); viewDocument = view.document; observer = view.getObserver( KeyObserver ); } ); diff --git a/tests/view/observer/mouseobserver.js b/tests/view/observer/mouseobserver.js index f313086ab..9db6d4516 100644 --- a/tests/view/observer/mouseobserver.js +++ b/tests/view/observer/mouseobserver.js @@ -10,11 +10,10 @@ import View from '../../../src/view/view'; import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'MouseObserver', () => { - let view, viewDocument, observer, stylesProcessor; + let view, viewDocument, observer; beforeEach( () => { - stylesProcessor = new StylesProcessor(); - view = new View( stylesProcessor ); + view = new View( new StylesProcessor() ); viewDocument = view.document; observer = view.addObserver( MouseObserver ); } ); diff --git a/tests/view/observer/mutationobserver.js b/tests/view/observer/mutationobserver.js index f1da5c947..e5df359b0 100644 --- a/tests/view/observer/mutationobserver.js +++ b/tests/view/observer/mutationobserver.js @@ -13,15 +13,14 @@ import { parse } from '../../../src/dev-utils/view'; import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'MutationObserver', () => { - let view, domEditor, viewDocument, viewRoot, mutationObserver, lastMutations, domRoot, stylesProcessor; + let view, domEditor, viewDocument, viewRoot, mutationObserver, lastMutations, domRoot; beforeEach( () => { - stylesProcessor = new StylesProcessor(); domRoot = document.createElement( 'div' ); domRoot.innerHTML = '
'; document.body.appendChild( domRoot ); - view = new View( stylesProcessor ); + view = new View( new StylesProcessor() ); viewDocument = view.document; domEditor = document.getElementById( 'main' ); lastMutations = null; @@ -39,7 +38,7 @@ describe( 'MutationObserver', () => { viewRoot = viewDocument.getRoot(); - viewRoot._appendChild( parse( 'foobar', { stylesProcessor } ) ); + viewRoot._appendChild( parse( 'foobar' ) ); view.forceRender(); } ); @@ -99,7 +98,7 @@ describe( 'MutationObserver', () => { it( 'should handle unbold', () => { viewRoot._removeChildren( 0, viewRoot.childCount ); - viewRoot._appendChild( parse( 'foo', { stylesProcessor } ) ); + viewRoot._appendChild( parse( 'foo' ) ); view.forceRender(); const domP = domEditor.childNodes[ 0 ]; @@ -206,7 +205,7 @@ describe( 'MutationObserver', () => { view.attachDomRoot( domAdditionalEditor, 'additional' ); viewDocument.getRoot( 'additional' )._appendChild( - parse( 'foobar', { stylesProcessor } ) ); + parse( 'foobar' ) ); // Render AdditionalEditor (first editor has been rendered in the beforeEach function) view.forceRender(); @@ -228,7 +227,7 @@ describe( 'MutationObserver', () => { it( 'should fire children mutation if the mutation occurred in the inline filler', () => { const { view: viewContainer, selection } = parse( - 'foo[]bar', { stylesProcessor } + 'foo[]bar' ); view.change( writer => { @@ -248,7 +247,7 @@ describe( 'MutationObserver', () => { it( 'should have no inline filler in mutation', () => { const { view: viewContainer, selection } = parse( - 'foo[]bar', { stylesProcessor } + 'foo[]bar' ); view.change( writer => { @@ -260,7 +259,7 @@ describe( 'MutationObserver', () => { inlineFiller.data += 'x'; view.change( () => { - viewContainer.getChild( 1 )._appendChild( parse( 'x', { stylesProcessor } ) ); + viewContainer.getChild( 1 )._appendChild( parse( 'x' ) ); mutationObserver.flush(); } ); @@ -281,8 +280,7 @@ describe( 'MutationObserver', () => { '' + 'foo' + '[]' + - '', - { stylesProcessor } + '' ); view.change( writer => { @@ -314,8 +312,7 @@ describe( 'MutationObserver', () => { 'foo' + 'bar' + '[]' + - '', - { stylesProcessor } + '' ); view.change( writer => { @@ -358,8 +355,7 @@ describe( 'MutationObserver', () => { '' + '[]' + 'foo' + - '', - { stylesProcessor } + '' ); view.change( writer => { @@ -385,7 +381,7 @@ describe( 'MutationObserver', () => { } ); it( 'should have no block filler in mutation', () => { - viewRoot._appendChild( parse( '', { stylesProcessor } ) ); + viewRoot._appendChild( parse( '' ) ); view.forceRender(); @@ -404,7 +400,7 @@ describe( 'MutationObserver', () => { } ); it( 'should ignore mutation with bogus br inserted on the end of the empty paragraph', () => { - viewRoot._appendChild( parse( '', { stylesProcessor } ) ); + viewRoot._appendChild( parse( '' ) ); view.forceRender(); @@ -417,7 +413,7 @@ describe( 'MutationObserver', () => { } ); it( 'should ignore mutation with bogus br inserted on the end of the paragraph with text', () => { - viewRoot._appendChild( parse( 'foo', { stylesProcessor } ) ); + viewRoot._appendChild( parse( 'foo' ) ); view.forceRender(); @@ -430,7 +426,7 @@ describe( 'MutationObserver', () => { } ); it( 'should ignore mutation with bogus br inserted on the end of the paragraph while processing text mutations', () => { - viewRoot._appendChild( parse( 'foo', { stylesProcessor } ) ); + viewRoot._appendChild( parse( 'foo' ) ); view.forceRender(); @@ -447,7 +443,7 @@ describe( 'MutationObserver', () => { } ); it( 'should ignore child mutations which resulted in no changes – when element contains elements', () => { - viewRoot._appendChild( parse( '', { stylesProcessor } ) ); + viewRoot._appendChild( parse( '' ) ); view.forceRender(); @@ -481,7 +477,7 @@ describe( 'MutationObserver', () => { } ); it( 'should not ignore mutation with br inserted not on the end of the paragraph', () => { - viewRoot._appendChild( parse( 'foo', { stylesProcessor } ) ); + viewRoot._appendChild( parse( 'foo' ) ); view.forceRender(); @@ -500,7 +496,7 @@ describe( 'MutationObserver', () => { } ); it( 'should not ignore mutation inserting element different than br on the end of the empty paragraph', () => { - viewRoot._appendChild( parse( '', { stylesProcessor } ) ); + viewRoot._appendChild( parse( '' ) ); view.forceRender(); @@ -518,7 +514,7 @@ describe( 'MutationObserver', () => { } ); it( 'should not ignore mutation inserting element different than br on the end of the paragraph with text', () => { - viewRoot._appendChild( parse( 'foo', { stylesProcessor } ) ); + viewRoot._appendChild( parse( 'foo' ) ); view.forceRender(); diff --git a/tests/view/observer/observer.js b/tests/view/observer/observer.js index 45c584dd1..234347600 100644 --- a/tests/view/observer/observer.js +++ b/tests/view/observer/observer.js @@ -8,15 +8,9 @@ import View from '../../../src/view/view'; import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'Observer', () => { - let stylesProcessor; - - beforeEach( () => { - stylesProcessor = new StylesProcessor(); - } ); - describe( 'constructor()', () => { it( 'should create Observer with properties', () => { - const view = new View( stylesProcessor ); + const view = new View( new StylesProcessor() ); const observer = new Observer( view ); expect( observer ).to.be.an.instanceof( Observer ); diff --git a/tests/view/observer/selectionobserver.js b/tests/view/observer/selectionobserver.js index aa83e6eb6..d049607b0 100644 --- a/tests/view/observer/selectionobserver.js +++ b/tests/view/observer/selectionobserver.js @@ -17,11 +17,6 @@ import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'SelectionObserver', () => { let view, viewDocument, viewRoot, selectionObserver, domRoot, domMain, domDocument; - let stylesProcessor; - - before( () => { - stylesProcessor = new StylesProcessor(); - } ); beforeEach( done => { domDocument = document; @@ -30,7 +25,7 @@ describe( 'SelectionObserver', () => { domMain = domRoot.childNodes[ 0 ]; domDocument.body.appendChild( domRoot ); - view = new View( stylesProcessor ); + view = new View( new StylesProcessor() ); viewDocument = view.document; createViewRoot( viewDocument ); view.attachDomRoot( domMain ); diff --git a/tests/view/placeholder.js b/tests/view/placeholder.js index 1bf19b6ab..f02781999 100644 --- a/tests/view/placeholder.js +++ b/tests/view/placeholder.js @@ -18,14 +18,9 @@ import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'placeholder', () => { let view, viewDocument, viewRoot; - let stylesProcessor; - - before( () => { - stylesProcessor = new StylesProcessor(); - } ); beforeEach( () => { - view = new View( stylesProcessor ); + view = new View( new StylesProcessor() ); viewDocument = view.document; viewRoot = createViewRoot( viewDocument ); viewDocument.isFocused = true; @@ -178,7 +173,7 @@ describe( 'placeholder', () => { setData( view, '
{another div}
' ); const element = viewRoot.getChild( 0 ); - const secondView = new View( stylesProcessor ); + const secondView = new View( new StylesProcessor() ); const secondDocument = secondView.document; secondDocument.isFocused = true; const secondRoot = createViewRoot( secondDocument ); diff --git a/tests/view/position.js b/tests/view/position.js index cd388cfcc..63b6500df 100644 --- a/tests/view/position.js +++ b/tests/view/position.js @@ -24,11 +24,8 @@ describe( 'Position', () => { const parentMock = {}; let document; - let stylesProcessor; - before( () => { - stylesProcessor = new StylesProcessor(); - document = new Document( stylesProcessor ); + document = new Document( new StylesProcessor() ); } ); describe( 'constructor()', () => { @@ -648,7 +645,7 @@ describe( 'Position', () => { let root; beforeEach( () => { - const doc = new Document( stylesProcessor ); + const doc = new Document( new StylesProcessor() ); root = createViewRoot( doc ); diff --git a/tests/view/range.js b/tests/view/range.js index e952357a6..66decaf53 100644 --- a/tests/view/range.js +++ b/tests/view/range.js @@ -21,11 +21,10 @@ function getRange( view, options = {} ) { } describe( 'Range', () => { - let document, stylesProcessor; + let document; beforeEach( () => { - stylesProcessor = new StylesProcessor(); - document = new Document( stylesProcessor ); + document = new Document( new StylesProcessor() ); } ); describe( 'constructor()', () => { diff --git a/tests/view/renderer.js b/tests/view/renderer.js index 5ef61e566..241303383 100644 --- a/tests/view/renderer.js +++ b/tests/view/renderer.js @@ -33,13 +33,11 @@ import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'Renderer', () => { let selection, domConverter, renderer, viewDocument; - let stylesProcessor; testUtils.createSinonSandbox(); beforeEach( () => { - stylesProcessor = new StylesProcessor(); - viewDocument = new ViewDocument( stylesProcessor ); + viewDocument = new ViewDocument( new StylesProcessor() ); selection = new DocumentSelection(); domConverter = new DomConverter( viewDocument ); renderer = new Renderer( domConverter, selection ); @@ -3132,7 +3130,7 @@ describe( 'Renderer', () => { '' + '
'; - viewRoot._appendChild( parse( view, { stylesProcessor } ) ); + viewRoot._appendChild( parse( view ) ); renderer.markToSync( 'children', viewRoot ); renderer.render(); @@ -3726,7 +3724,7 @@ describe( 'Renderer', () => { let view, viewDoc, viewRoot, domRoot, converter; beforeEach( () => { - view = new View( stylesProcessor ); + view = new View( new StylesProcessor() ); viewDoc = view.document; domRoot = document.createElement( 'div' ); document.body.appendChild( domRoot ); diff --git a/tests/view/selection.js b/tests/view/selection.js index de14911c5..a0fd243cf 100644 --- a/tests/view/selection.js +++ b/tests/view/selection.js @@ -20,13 +20,11 @@ import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'Selection', () => { let selection, el, range1, range2, range3, viewDocument; - let stylesProcessor; testUtils.createSinonSandbox(); beforeEach( () => { - stylesProcessor = new StylesProcessor(); - viewDocument = new Document( stylesProcessor ); + viewDocument = new Document( new StylesProcessor() ); const text = new Text( viewDocument, 'xxxxxxxxxxxxxxxxxxxx' ); el = new Element( viewDocument, 'p', null, text ); diff --git a/tests/view/styles/background.js b/tests/view/styles/background.js index 61ab6e4d3..db956e1ba 100644 --- a/tests/view/styles/background.js +++ b/tests/view/styles/background.js @@ -7,10 +7,10 @@ import StylesMap, { StylesProcessor } from '../../../src/view/stylesmap'; import { addBackgroundRules } from '../../../src/view/styles/background'; describe( 'Background styles normalization', () => { - let styles, stylesProcessor; + let styles; beforeEach( () => { - stylesProcessor = new StylesProcessor(); + const stylesProcessor = new StylesProcessor(); addBackgroundRules( stylesProcessor ); styles = new StylesMap( stylesProcessor ); } ); diff --git a/tests/view/styles/border.js b/tests/view/styles/border.js index f5ae65351..6b11453da 100644 --- a/tests/view/styles/border.js +++ b/tests/view/styles/border.js @@ -7,10 +7,10 @@ import StylesMap, { StylesProcessor } from '../../../src/view/stylesmap'; import { addBorderRules } from '../../../src/view/styles/border'; describe( 'Border styles normalization', () => { - let styles, stylesProcessor; + let styles; beforeEach( () => { - stylesProcessor = new StylesProcessor(); + const stylesProcessor = new StylesProcessor(); addBorderRules( stylesProcessor ); styles = new StylesMap( stylesProcessor ); } ); diff --git a/tests/view/styles/margin.js b/tests/view/styles/margin.js index 75939e732..8bce19f17 100644 --- a/tests/view/styles/margin.js +++ b/tests/view/styles/margin.js @@ -7,10 +7,10 @@ import StylesMap, { StylesProcessor } from '../../../src/view/stylesmap'; import { addMarginRules } from '../../../src/view/styles/margin'; describe( 'Margin styles normalizer', () => { - let styles, stylesProcessor; + let styles; beforeEach( () => { - stylesProcessor = new StylesProcessor(); + const stylesProcessor = new StylesProcessor(); addMarginRules( stylesProcessor ); styles = new StylesMap( stylesProcessor ); } ); diff --git a/tests/view/styles/padding.js b/tests/view/styles/padding.js index 3d2138ba3..ccea8f3c6 100644 --- a/tests/view/styles/padding.js +++ b/tests/view/styles/padding.js @@ -7,10 +7,10 @@ import StylesMap, { StylesProcessor } from '../../../src/view/stylesmap'; import { addPaddingRules } from '../../../src/view/styles/padding'; describe( 'Padding styles normalization', () => { - let styles, stylesProcessor; + let styles; beforeEach( () => { - stylesProcessor = new StylesProcessor(); + const stylesProcessor = new StylesProcessor(); addPaddingRules( stylesProcessor ); styles = new StylesMap( stylesProcessor ); } ); diff --git a/tests/view/stylesmap.js b/tests/view/stylesmap.js index 8a004c698..10f661d5d 100644 --- a/tests/view/stylesmap.js +++ b/tests/view/stylesmap.js @@ -9,10 +9,10 @@ import { addMarginRules } from '../../src/view/styles/margin'; import { getBoxSidesValueReducer } from '../../src/view/styles/utils'; describe( 'StylesMap', () => { - let stylesMap, stylesProcessor; + let stylesMap; beforeEach( () => { - stylesProcessor = new StylesProcessor(); + const stylesProcessor = new StylesProcessor(); // Define simple "foo" shorthand normalizers, similar to the "margin" shorthand normalizers, for testing purposes. stylesProcessor.setNormalizer( 'foo', value => ( { diff --git a/tests/view/text.js b/tests/view/text.js index 09c1da6af..f6f19d748 100644 --- a/tests/view/text.js +++ b/tests/view/text.js @@ -9,11 +9,10 @@ import Document from '../../src/view/document'; import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'Text', () => { - let document, stylesProcessor; + let document; beforeEach( () => { - stylesProcessor = new StylesProcessor(); - document = new Document( stylesProcessor ); + document = new Document( new StylesProcessor() ); } ); describe( 'constructor()', () => { diff --git a/tests/view/textproxy.js b/tests/view/textproxy.js index c8aa3bf28..9d78fe6b1 100644 --- a/tests/view/textproxy.js +++ b/tests/view/textproxy.js @@ -15,11 +15,10 @@ import Document from '../../src/view/document'; import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'TextProxy', () => { - let text, parent, wrapper, textProxy, document, stylesProcessor; + let text, parent, wrapper, textProxy, document; beforeEach( () => { - stylesProcessor = new StylesProcessor(); - document = new Document( stylesProcessor ); + document = new Document( new StylesProcessor() ); text = new Text( document, 'abcdefgh' ); parent = new ContainerElement( document, 'p', [], [ text ] ); wrapper = new ContainerElement( document, 'div', [], parent ); diff --git a/tests/view/treewalker.js b/tests/view/treewalker.js index 958488d84..b9ae249e6 100644 --- a/tests/view/treewalker.js +++ b/tests/view/treewalker.js @@ -16,11 +16,10 @@ import { expectToThrowCKEditorError } from '@ckeditor/ckeditor5-utils/tests/_uti import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'TreeWalker', () => { - let doc, root, img1, paragraph, bold, textAbcd, charY, img2, charX, rootBeginning, rootEnding, stylesProcessor; + let doc, root, img1, paragraph, bold, textAbcd, charY, img2, charX, rootBeginning, rootEnding; before( () => { - stylesProcessor = new StylesProcessor(); - doc = new Document( stylesProcessor ); + doc = new Document( new StylesProcessor() ); root = createViewRoot( doc ); // root diff --git a/tests/view/uielement.js b/tests/view/uielement.js index ce47abdb4..7bb4439f8 100644 --- a/tests/view/uielement.js +++ b/tests/view/uielement.js @@ -12,11 +12,10 @@ import { expectToThrowCKEditorError } from '@ckeditor/ckeditor5-utils/tests/_uti import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'UIElement', () => { - let uiElement, doc, stylesProcessor; + let uiElement, doc; beforeEach( () => { - stylesProcessor = new StylesProcessor(); - doc = new Document( stylesProcessor ); + doc = new Document( new StylesProcessor() ); uiElement = new UIElement( doc, 'span', { foo: 'bar', diff --git a/tests/view/upcastwriter.js b/tests/view/upcastwriter.js index f5bf6703a..1d19e1106 100644 --- a/tests/view/upcastwriter.js +++ b/tests/view/upcastwriter.js @@ -15,11 +15,10 @@ import Document from '../../src/view/document'; import { StylesProcessor } from '../../src/view/stylesmap'; describe( 'UpcastWriter', () => { - let writer, view, dataprocessor, document, stylesProcessor; + let writer, view, dataprocessor, document; beforeEach( () => { - stylesProcessor = new StylesProcessor(); - document = new Document( stylesProcessor ); + document = new Document( new StylesProcessor() ); writer = new UpcastWriter( document ); dataprocessor = new HtmlDataProcessor( document ); diff --git a/tests/view/utils-tests/createroot.js b/tests/view/utils-tests/createroot.js index 9095e49e1..2e98efbd0 100644 --- a/tests/view/utils-tests/createroot.js +++ b/tests/view/utils-tests/createroot.js @@ -9,11 +9,10 @@ import createRoot from '../_utils/createroot.js'; import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'createRoot', () => { - let viewDoc, stylesProcessor; + let viewDoc; beforeEach( () => { - stylesProcessor = new StylesProcessor(); - viewDoc = new Document( stylesProcessor ); + viewDoc = new Document( new StylesProcessor() ); } ); it( 'should create view root element with given data', () => { diff --git a/tests/view/view/jumpoverinlinefiller.js b/tests/view/view/jumpoverinlinefiller.js index 80a0f2432..f82d2d941 100644 --- a/tests/view/view/jumpoverinlinefiller.js +++ b/tests/view/view/jumpoverinlinefiller.js @@ -16,17 +16,15 @@ import { parse, setData } from '../../../src/dev-utils/view'; import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'View', () => { - let view, viewDocument, domRoot, stylesProcessor; + let view, viewDocument, domRoot; beforeEach( () => { - stylesProcessor = new StylesProcessor(); - domRoot = createElement( document, 'div', { contenteditable: 'true' } ); document.body.appendChild( domRoot ); - view = new View( stylesProcessor ); + view = new View( new StylesProcessor() ); viewDocument = view.document; createViewRoot( viewDocument ); view.attachDomRoot( domRoot ); diff --git a/tests/view/view/jumpoveruielement.js b/tests/view/view/jumpoveruielement.js index cf413d61e..2218a5d6a 100644 --- a/tests/view/view/jumpoveruielement.js +++ b/tests/view/view/jumpoveruielement.js @@ -19,7 +19,7 @@ import testUtils from '@ckeditor/ckeditor5-core/tests/_utils/utils'; import { StylesProcessor } from '../../../src/view/stylesmap'; describe( 'View', () => { - let view, viewDocument, domRoot, domSelection, viewRoot, foo, bar, ui, ui2, stylesProcessor; + let view, viewDocument, domRoot, domSelection, viewRoot, foo, bar, ui, ui2; function createUIElement( name, contents ) { const element = new UIElement( viewDocument, name ); @@ -35,14 +35,12 @@ describe( 'View', () => { } beforeEach( () => { - stylesProcessor = new StylesProcessor(); - domRoot = createElement( document, 'div', { contenteditable: 'true' } ); document.body.appendChild( domRoot ); - view = new View( stylesProcessor ); + view = new View( new StylesProcessor() ); viewDocument = view.document; viewRoot = createViewRoot( viewDocument ); view.attachDomRoot( domRoot ); diff --git a/tests/view/view/view.js b/tests/view/view/view.js index 7e7a5fa55..c2a28d534 100644 --- a/tests/view/view/view.js +++ b/tests/view/view/view.js @@ -30,11 +30,9 @@ import CKEditorError from '@ckeditor/ckeditor5-utils/src/ckeditorerror'; describe( 'view', () => { const DEFAULT_OBSERVERS_COUNT = 6; - let domRoot, view, viewDocument, ObserverMock, instantiated, enabled, ObserverMockGlobalCount, stylesProcessor; + let domRoot, view, viewDocument, ObserverMock, instantiated, enabled, ObserverMockGlobalCount; beforeEach( () => { - stylesProcessor = new StylesProcessor(); - domRoot = createElement( document, 'div', { id: 'editor', contenteditable: 'true' @@ -42,7 +40,7 @@ describe( 'view', () => { document.body.appendChild( domRoot ); - view = new View( stylesProcessor ); + view = new View( new StylesProcessor() ); viewDocument = view.document; ObserverMock = class extends Observer { @@ -93,7 +91,7 @@ describe( 'view', () => { const oldEnvIsAndroid = env.isAndroid; env.isAndroid = true; - const newView = new View( stylesProcessor ); + const newView = new View( new StylesProcessor() ); expect( newView.getObserver( InputObserver ) ).to.be.instanceof( InputObserver ); env.isAndroid = oldEnvIsAndroid; @@ -162,7 +160,7 @@ describe( 'view', () => { // The variable will be overwritten. view.destroy(); - view = new View( stylesProcessor ); + view = new View( new StylesProcessor() ); viewDocument = view.document; view._renderer.render = sinon.spy(); @@ -272,7 +270,7 @@ describe( 'view', () => { // The variable will be overwritten. view.destroy(); - view = new View( stylesProcessor ); + view = new View( new StylesProcessor() ); viewDocument = view.document; view._renderer.render = sinon.spy(); } ); @@ -561,7 +559,7 @@ describe( 'view', () => { createElement( document, 'p' ) ] ); - const view = new View( stylesProcessor ); + const view = new View( new StylesProcessor() ); const viewDocument = view.document; createViewRoot( viewDocument, 'div', 'main' ); @@ -578,7 +576,7 @@ describe( 'view', () => { it( 'should render changes in the Document', () => { const domDiv = document.createElement( 'div' ); - const view = new View( stylesProcessor ); + const view = new View( new StylesProcessor() ); const viewDocument = view.document; createViewRoot( viewDocument, 'div', 'main' ); view.attachDomRoot( domDiv ); @@ -595,7 +593,7 @@ describe( 'view', () => { it( 'should render attribute changes', () => { const domRoot = document.createElement( 'div' ); - const view = new View( stylesProcessor ); + const view = new View( new StylesProcessor() ); const viewDocument = view.document; const viewRoot = createViewRoot( viewDocument, 'div', 'main' ); From 21390a93bde53517bec3e82fedc9cb1ea77d5187 Mon Sep 17 00:00:00 2001 From: Kamil Piechaczek Date: Thu, 27 Feb 2020 11:56:05 +0100 Subject: [PATCH 28/34] Removed the 'model.Node#document.' property. --- src/model/node.js | 17 ----------------- src/model/selection.js | 11 ++++++++--- src/model/textproxy.js | 11 ----------- tests/model/node.js | 19 ------------------- tests/model/textproxy.js | 5 ----- 5 files changed, 8 insertions(+), 55 deletions(-) diff --git a/src/model/node.js b/src/model/node.js index 3795350b1..5c5800139 100644 --- a/src/model/node.js +++ b/src/model/node.js @@ -188,23 +188,6 @@ export default class Node { return root; } - /** - * {@link module:engine/model/document~Document Document} that owns this node or `null` if the node has no parent or is inside - * a {@link module:engine/model/documentfragment~DocumentFragment DocumentFragment}. - * - * @readonly - * @type {module:engine/model/document~Document|null} - */ - get document() { - // This is a top element of a sub-tree. - if ( this.root == this ) { - return null; - } - - // Root may be `DocumentFragment` which does not have document property. - return this.root.document || null; - } - /** * Gets path to the node. The path is an array containing starting offsets of consecutive ancestors of this node, * beginning from {@link module:engine/model/node~Node#root root}, down to this node's starting offset. The path can be used to diff --git a/src/model/selection.js b/src/model/selection.js index be1fe8682..1ec167eae 100644 --- a/src/model/selection.js +++ b/src/model/selection.js @@ -829,7 +829,9 @@ function isUnvisitedBlock( element, visited ) { visited.add( element ); - return element.document.model.schema.isBlock( element ) && element.parent; + const document = element.is( 'rootElement' ) ? element.document : element.root.document; + + return document.model.schema.isBlock( element ) && element.parent; } // Checks if the given element is a $block was not previously visited and is a top block in a range. @@ -841,7 +843,9 @@ function isUnvisitedTopBlock( element, visited, range ) { // It will search until first ancestor that is a limit element. // Marks all ancestors as already visited to not include any of them later on. function getParentBlock( position, visited ) { - const schema = position.parent.document.model.schema; + const element = position.parent; + const document = element.is( 'rootElement' ) ? element.document : element.root.document; + const schema = document.model.schema; const ancestors = position.parent.getAncestors( { parentFirst: true, includeSelf: true } ); @@ -887,7 +891,8 @@ function isTopBlockInRange( block, range ) { // @param {module:engine/model/node~Node} node // @returns {module:engine/model/node~Node|undefined} function findAncestorBlock( node ) { - const schema = node.document.model.schema; + const document = node.is( 'rootElement' ) ? node.document : node.root.document; + const schema = document.model.schema; let parent = node.parent; diff --git a/src/model/textproxy.js b/src/model/textproxy.js index 1d4a0a9cf..f3946f8c4 100644 --- a/src/model/textproxy.js +++ b/src/model/textproxy.js @@ -163,17 +163,6 @@ export default class TextProxy { return this.textNode.root; } - /** - * {@link module:engine/model/document~Document Document} that owns text node represented by this text proxy or `null` if the text node - * has no parent or is inside a {@link module:engine/model/documentfragment~DocumentFragment DocumentFragment}. - * - * @readonly - * @type {module:engine/model/document~Document|null} - */ - get document() { - return this.textNode.document; - } - /** * Checks whether this object is of the given. * diff --git a/tests/model/node.js b/tests/model/node.js index 4284c5ecb..f684fdfc9 100644 --- a/tests/model/node.js +++ b/tests/model/node.js @@ -75,25 +75,6 @@ describe( 'Node', () => { expect( node ).to.have.property( 'previousSibling' ).that.is.null; } ); - - it( 'document', () => { - expect( root ).to.have.property( 'document' ).that.equals( doc ); - - expect( one ).to.have.property( 'document' ).that.equals( doc ); - expect( two ).to.have.property( 'document' ).that.equals( doc ); - expect( three ).to.have.property( 'document' ).that.equals( doc ); - - expect( textBA ).to.have.property( 'document' ).that.equals( doc ); - expect( img ).to.have.property( 'document' ).that.equals( doc ); - expect( textR ).to.have.property( 'document' ).that.equals( doc ); - - expect( node ).to.have.property( 'document' ).that.is.null; - - // DocumentFragment does not have document property, so node's document property should be null. - const docFrag = new DocumentFragment(); - docFrag._appendChild( node ); - expect( node ).to.have.property( 'document' ).that.is.null; - } ); } ); describe( 'constructor()', () => { diff --git a/tests/model/textproxy.js b/tests/model/textproxy.js index c5c8938d6..294ea2b85 100644 --- a/tests/model/textproxy.js +++ b/tests/model/textproxy.js @@ -38,11 +38,6 @@ describe( 'TextProxy', () => { expect( textProxyNoParent ).to.have.property( 'root' ).that.equals( textNoParent ); } ); - it( 'should have document property', () => { - expect( textProxy ).to.have.property( 'document' ).that.equals( doc ); - expect( textProxyNoParent ).to.have.property( 'document' ).that.equals( null ); - } ); - it( 'should have parent property', () => { expect( textProxy ).to.have.property( 'parent' ).that.equals( element ); expect( textProxyNoParent ).to.have.property( 'parent' ).that.equals( null ); From 8039a8d4ce86eadcab13ec9d5ffb74d4f700e09a Mon Sep 17 00:00:00 2001 From: Kamil Piechaczek Date: Fri, 28 Feb 2020 13:00:16 +0100 Subject: [PATCH 29/34] Added a new method (#isAttached()) to both (view and model) Nodes classes. --- src/conversion/downcasthelpers.js | 2 +- src/model/node.js | 9 ++++++ src/view/element.js | 4 --- src/view/node.js | 9 ++++++ tests/model/node.js | 51 +++++++++++++++++++++++++++++++ tests/view/node.js | 43 +++++++++++++++++++------- tests/view/position.js | 1 - 7 files changed, 102 insertions(+), 17 deletions(-) diff --git a/src/conversion/downcasthelpers.js b/src/conversion/downcasthelpers.js index d80e1a4ee..9ed599f93 100644 --- a/src/conversion/downcasthelpers.js +++ b/src/conversion/downcasthelpers.js @@ -544,7 +544,7 @@ export function clearAttributes() { // Not collapsed selection should not have artifacts. if ( range.isCollapsed ) { // Position might be in the node removed by the view writer. - if ( range.end.parent.parent ) { + if ( range.end.parent.isAttached() ) { conversionApi.writer.mergeAttributes( range.start ); } } diff --git a/src/model/node.js b/src/model/node.js index 5c5800139..24485f5ee 100644 --- a/src/model/node.js +++ b/src/model/node.js @@ -188,6 +188,15 @@ export default class Node { return root; } + /** + * Returns true if a node is in a tree rooted in an element of the root type. + * + * @returns {Boolean} + */ + isAttached() { + return this.root.is( 'rootElement' ); + } + /** * Gets path to the node. The path is an array containing starting offsets of consecutive ancestors of this node, * beginning from {@link module:engine/model/node~Node#root root}, down to this node's starting offset. The path can be used to diff --git a/src/view/element.js b/src/view/element.js index 7443b1ac6..a15dbe7c8 100644 --- a/src/view/element.js +++ b/src/view/element.js @@ -667,10 +667,6 @@ export default class Element extends Node { if ( key == 'class' ) { parseClasses( this._classes, value ); } else if ( key == 'style' ) { - // if (!this._styles ) { - // debugger; - // } - this._styles.setTo( value ); } else { this._attrs.set( key, value ); diff --git a/src/view/node.js b/src/view/node.js index c4b7a4300..f33f5461a 100644 --- a/src/view/node.js +++ b/src/view/node.js @@ -117,6 +117,15 @@ export default class Node { return root; } + /** + * Returns true if a node is in a tree rooted in an element of the root type. + * + * @returns {Boolean} + */ + isAttached() { + return this.root.is( 'rootElement' ); + } + /** * Gets a path to the node. The path is an array containing indices of consecutive ancestors of this node, * beginning from {@link module:engine/view/node~Node#root root}, down to this node's index. diff --git a/tests/model/node.js b/tests/model/node.js index f684fdfc9..965df900b 100644 --- a/tests/model/node.js +++ b/tests/model/node.js @@ -8,8 +8,10 @@ import DocumentFragment from '../../src/model/documentfragment'; import Node from '../../src/model/node'; import Element from '../../src/model/element'; import Text from '../../src/model/text'; +import RootElement from '../../src/model/rootelement'; import count from '@ckeditor/ckeditor5-utils/src/count'; import { expectToThrowCKEditorError } from '@ckeditor/ckeditor5-utils/tests/_utils/utils'; +import ModelTestEditor from '@ckeditor/ckeditor5-core/tests/_utils/modeltesteditor'; describe( 'Node', () => { let doc, root, node, @@ -386,6 +388,55 @@ describe( 'Node', () => { } ); } ); + describe( 'isAttached()', () => { + it( 'returns false for a fresh node', () => { + const char = new Text( 'x' ); + const el = new Element( 'one' ); + + expect( char.isAttached() ).to.equal( false ); + expect( el.isAttached() ).to.equal( false ); + } ); + + it( 'returns true for the root element', () => { + const model = new Model(); + const root = new RootElement( model.document, 'root' ); + + expect( root.isAttached() ).to.equal( true ); + } ); + + it( 'returns false for a node attached to a document fragment', () => { + const foo = new Text( 'foo' ); + new DocumentFragment( [ foo ] ); // eslint-disable-line no-new + + expect( foo.isAttached() ).to.equal( false ); + } ); + + it( 'returns true for a node moved to graveyard', () => { + return ModelTestEditor.create() + .then( editor => { + const model = editor.model; + const root = model.document.getRoot(); + + // Allow "paragraph" element to be added as a child in block elements. + model.schema.register( 'paragraph', { inheritAllFrom: '$block' } ); + + const node = model.change( writer => writer.createElement( 'paragraph' ) ); + + expect( node.isAttached() ).to.equal( false ); + + model.change( writer => writer.append( node, root ) ); + + expect( node.isAttached() ).to.equal( true ); + + model.change( writer => writer.remove( node ) ); + + expect( node.isAttached() ).to.equal( true ); + + return editor.destroy(); + } ); + } ); + } ); + describe( 'attributes interface', () => { const node = new Node( { foo: 'bar' } ); diff --git a/tests/view/node.js b/tests/view/node.js index 53d81b16b..465abffed 100644 --- a/tests/view/node.js +++ b/tests/view/node.js @@ -9,7 +9,6 @@ import Node from '../../src/view/node'; import DocumentFragment from '../../src/view/documentfragment'; import RootEditableElement from '../../src/view/rooteditableelement'; -import createDocumentMock from '../../tests/view/_utils/createdocumentmock'; import { expectToThrowCKEditorError } from '@ckeditor/ckeditor5-utils/tests/_utils/utils'; import Document from '../../src/view/document'; import { StylesProcessor } from '../../src/view/stylesmap'; @@ -180,9 +179,9 @@ describe( 'Node', () => { } ); it( 'should return proper element for nodes in different branches and on different levels', () => { - const foo = new Text( 'foo' ); - const bar = new Text( 'bar' ); - const bom = new Text( 'bom' ); + const foo = new Text( document, 'foo' ); + const bar = new Text( document, 'bar' ); + const bom = new Text( document, 'bom' ); const d = new Element( document, 'd', null, [ bar ] ); const c = new Element( document, 'c', null, [ foo, d ] ); const b = new Element( document, 'b', null, [ c ] ); @@ -207,8 +206,8 @@ describe( 'Node', () => { } ); it( 'should return document fragment', () => { - const foo = new Text( 'foo' ); - const bar = new Text( 'bar' ); + const foo = new Text( document, 'foo' ); + const bar = new Text( document, 'bar' ); const df = new DocumentFragment( document, [ foo, bar ] ); expect( foo.getCommonAncestor( bar ) ).to.equal( df ); @@ -232,7 +231,7 @@ describe( 'Node', () => { } ); it( 'should throw an error if parent does not contain element', () => { - const f = new Text( 'f' ); + const f = new Text( document, 'f' ); const bar = new Element( document, 'bar', [], [] ); f.parent = bar; @@ -266,7 +265,6 @@ describe( 'Node', () => { it( 'should return root element', () => { const parent = new RootEditableElement( document, 'div' ); - parent._document = createDocumentMock(); const child = new Element( document, 'p' ); child.parent = parent; @@ -352,9 +350,32 @@ describe( 'Node', () => { } ); } ); + describe( 'isAttached()', () => { + it( 'returns false for a fresh node', () => { + const char = new Text( document, 'x' ); + const el = new Element( document, 'one' ); + + expect( char.isAttached() ).to.equal( false ); + expect( el.isAttached() ).to.equal( false ); + } ); + + it( 'returns true for the root element', () => { + const root = new RootEditableElement( document, 'div' ); + + expect( root.isAttached() ).to.equal( true ); + } ); + + it( 'returns false for a node attached to a document fragment', () => { + const foo = new Text( document, 'foo' ); + new DocumentFragment( document, [ foo ] ); // eslint-disable-line no-new + + expect( foo.isAttached() ).to.equal( false ); + } ); + } ); + describe( '_remove()', () => { it( 'should remove node from its parent', () => { - const char = new Text( 'a' ); + const char = new Text( document, 'a' ); const parent = new Element( document, 'p', null, [ char ] ); char._remove(); @@ -362,7 +383,7 @@ describe( 'Node', () => { } ); it( 'uses parent._removeChildren method', () => { - const char = new Text( 'a' ); + const char = new Text( document, 'a' ); const parent = new Element( document, 'p', null, [ char ] ); const _removeChildrenSpy = sinon.spy( parent, '_removeChildren' ); const index = char.index; @@ -399,7 +420,7 @@ describe( 'Node', () => { } ); beforeEach( () => { - text = new Text( 'foo' ); + text = new Text( document, 'foo' ); img = new Element( document, 'img', { 'src': 'img.png' } ); root = new Element( document, 'p', { renderer: { markToSync: rootChangeSpy } } ); diff --git a/tests/view/position.js b/tests/view/position.js index 9e5807fdd..1bd715959 100644 --- a/tests/view/position.js +++ b/tests/view/position.js @@ -546,7 +546,6 @@ describe( 'Position', () => { it( 'should return EditableElement when position is placed inside', () => { const p = new Element( document, 'p' ); const editable = new EditableElement( document, 'div', null, p ); - editable._document = document; const position = new Position( p, 0 ); expect( position.editableElement ).to.equal( editable ); From b21a4158fe61bc4b618076238bdedc91cd4b8e4a Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Piotrek=20Koszuli=C5=84ski?= Date: Tue, 3 Mar 2020 12:31:40 +0100 Subject: [PATCH 30/34] Removed the dataProcessor argument, as it was never used in practice. --- src/controller/datacontroller.js | 13 +++++-------- tests/controller/datacontroller.js | 13 ++++++++----- 2 files changed, 13 insertions(+), 13 deletions(-) diff --git a/src/controller/datacontroller.js b/src/controller/datacontroller.js index d7b2c2199..37e041aa1 100644 --- a/src/controller/datacontroller.js +++ b/src/controller/datacontroller.js @@ -46,12 +46,10 @@ export default class DataController { /** * Creates a data controller instance. * - * @param {module:engine/view/stylesmap~StylesProcessor} stylesProcessor Styles processor. * @param {module:engine/model/model~Model} model Data model. - * @param {module:engine/dataprocessor/dataprocessor~DataProcessor} [dataProcessor] Data processor that should be used - * by the controller. + * @param {module:engine/view/stylesmap~StylesProcessor} stylesProcessor Styles processor. */ - constructor( stylesProcessor, model, dataProcessor ) { + constructor( model, stylesProcessor ) { /** * Data model. * @@ -61,7 +59,7 @@ export default class DataController { this.model = model; /** - * StylesProcessor is responsible for writing and reading a normalized styles object. + * Styles processor used during the conversion. * * @readonly * @member {module:engine/view/stylesmap~StylesProcessor} @@ -71,10 +69,9 @@ export default class DataController { /** * Data processor used during the conversion. * - * @readonly - * @member {module:engine/dataprocessor/dataprocessor~DataProcessor} + * @member {module:engine/dataprocessor/dataprocessor~DataProcessor} #processor */ - this.processor = dataProcessor; + this.processor; /** * Mapper used for the conversion. It has no permanent bindings, because they are created when getting data and diff --git a/tests/controller/datacontroller.js b/tests/controller/datacontroller.js index 993e9d845..3fad2844d 100644 --- a/tests/controller/datacontroller.js +++ b/tests/controller/datacontroller.js @@ -41,17 +41,20 @@ describe( 'DataController', () => { viewDocument = new ViewDocument( stylesProcessor ); htmlDataProcessor = new HtmlDataProcessor( viewDocument ); - data = new DataController( stylesProcessor, model, htmlDataProcessor ); + data = new DataController( model, stylesProcessor ); + data.processor = htmlDataProcessor; upcastHelpers = new UpcastHelpers( [ data.upcastDispatcher ] ); downcastHelpers = new DowncastHelpers( [ data.downcastDispatcher ] ); } ); describe( 'constructor()', () => { - it( 'works without data processor', () => { - const data = new DataController( new StylesProcessor(), model ); + it( 'sets the model and styles processor properties', () => { + const stylesProcessor = new StylesProcessor(); + const data = new DataController( model, stylesProcessor ); - expect( data.processor ).to.be.undefined; + expect( data.model ).to.equal( model ); + expect( data.stylesProcessor ).to.equal( stylesProcessor ); } ); } ); @@ -577,7 +580,7 @@ describe( 'DataController', () => { describe( 'addStyleProcessorRules()', () => { it( 'should execute callback with an instance of StyleProcessor as the first argument', () => { const stylesProcessor = new StylesProcessor(); - const data = new DataController( stylesProcessor, model, htmlDataProcessor ); + const data = new DataController( model, stylesProcessor ); const spy = sinon.spy(); From 054d8a2d54a4da5a3c959b1bc908df1fb9aa2cdb Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Piotrek=20Koszuli=C5=84ski?= Date: Tue, 3 Mar 2020 12:45:54 +0100 Subject: [PATCH 31/34] Docs. --- src/controller/datacontroller.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/controller/datacontroller.js b/src/controller/datacontroller.js index 37e041aa1..ce9880a40 100644 --- a/src/controller/datacontroller.js +++ b/src/controller/datacontroller.js @@ -381,7 +381,7 @@ export default class DataController { /** * Adds a style processor normalization rules. * - * The available style processors: + * You can implement your own rules as well as use one of the available processor rules: * * * background: {@link module:engine/view/styles/background~addBackgroundRules} * * border: {@link module:engine/view/styles/border~addBorderRules} From 13dd24c39e006800a7bac55241d3fb391e720511 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Piotrek=20Koszuli=C5=84ski?= Date: Tue, 3 Mar 2020 13:12:37 +0100 Subject: [PATCH 32/34] Docs and code simplification. --- src/dataprocessor/htmldataprocessor.js | 2 +- src/dataprocessor/xmldataprocessor.js | 2 +- src/model/node.js | 2 +- src/model/rootelement.js | 10 ++++------ src/model/selection.js | 10 +++------- 5 files changed, 10 insertions(+), 16 deletions(-) diff --git a/src/dataprocessor/htmldataprocessor.js b/src/dataprocessor/htmldataprocessor.js index 88bb69710..1b8efa6de 100644 --- a/src/dataprocessor/htmldataprocessor.js +++ b/src/dataprocessor/htmldataprocessor.js @@ -22,7 +22,7 @@ export default class HtmlDataProcessor { /** * Creates a new instance of the HTML data processor class. * - * @param {module:engine/view/document~Document} document + * @param {module:engine/view/document~Document} document The view document instance. */ constructor( document ) { /** diff --git a/src/dataprocessor/xmldataprocessor.js b/src/dataprocessor/xmldataprocessor.js index 63e0dca22..8f0c03cd4 100644 --- a/src/dataprocessor/xmldataprocessor.js +++ b/src/dataprocessor/xmldataprocessor.js @@ -24,7 +24,7 @@ export default class XmlDataProcessor { /** * Creates a new instance of the XML data processor class. * - * @param {module:engine/view/document~Document} document + * @param {module:engine/view/document~Document} document The view document instance. * @param {Object} options Configuration options. * @param {Array} [options.namespaces=[]] A list of namespaces allowed to use in the XML input. */ diff --git a/src/model/node.js b/src/model/node.js index 24485f5ee..d85bb8055 100644 --- a/src/model/node.js +++ b/src/model/node.js @@ -189,7 +189,7 @@ export default class Node { } /** - * Returns true if a node is in a tree rooted in an element of the root type. + * Returns true if the node is in a tree rooted in the document (is a descendant of one of its roots). * * @returns {Boolean} */ diff --git a/src/model/rootelement.js b/src/model/rootelement.js index 77fe0f2c8..2d29cac2d 100644 --- a/src/model/rootelement.js +++ b/src/model/rootelement.js @@ -17,12 +17,12 @@ export default class RootElement extends Element { /** * Creates root element. * - * @param {module:engine/model/document~Document} doc Document that is an owner of this root. + * @param {module:engine/model/document~Document} document Document that is an owner of this root. * @param {String} name Node name. * @param {String} [rootName='main'] Unique root name used to identify this root * element by {@link module:engine/model/document~Document}. */ - constructor( doc, name, rootName = 'main' ) { + constructor( document, name, rootName = 'main' ) { super( name ); /** @@ -31,7 +31,7 @@ export default class RootElement extends Element { * @private * @member {module:engine/model/document~Document} */ - this._doc = doc; + this._document = document; /** * Unique root name used to identify this root element by {@link module:engine/model/document~Document}. @@ -45,13 +45,11 @@ export default class RootElement extends Element { /** * {@link module:engine/model/document~Document Document} that owns this root element. * - * In contrary, to {@link module:engine/model/node~Node node}, root element always have a `document`. - * * @readonly * @type {module:engine/model/document~Document|null} */ get document() { - return this._doc; + return this._document; } /** diff --git a/src/model/selection.js b/src/model/selection.js index 1ec167eae..aad3538c3 100644 --- a/src/model/selection.js +++ b/src/model/selection.js @@ -829,9 +829,7 @@ function isUnvisitedBlock( element, visited ) { visited.add( element ); - const document = element.is( 'rootElement' ) ? element.document : element.root.document; - - return document.model.schema.isBlock( element ) && element.parent; + return element.root.document.model.schema.isBlock( element ) && element.parent; } // Checks if the given element is a $block was not previously visited and is a top block in a range. @@ -844,8 +842,7 @@ function isUnvisitedTopBlock( element, visited, range ) { // Marks all ancestors as already visited to not include any of them later on. function getParentBlock( position, visited ) { const element = position.parent; - const document = element.is( 'rootElement' ) ? element.document : element.root.document; - const schema = document.model.schema; + const schema = element.root.document.model.schema; const ancestors = position.parent.getAncestors( { parentFirst: true, includeSelf: true } ); @@ -891,8 +888,7 @@ function isTopBlockInRange( block, range ) { // @param {module:engine/model/node~Node} node // @returns {module:engine/model/node~Node|undefined} function findAncestorBlock( node ) { - const document = node.is( 'rootElement' ) ? node.document : node.root.document; - const schema = document.model.schema; + const schema = node.root.document.model.schema; let parent = node.parent; From 16301a194da3e2806a7b5e8ce00557e7c839315c Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Piotrek=20Koszuli=C5=84ski?= Date: Tue, 3 Mar 2020 13:49:00 +0100 Subject: [PATCH 33/34] Docs and other improvements. --- src/controller/datacontroller.js | 2 +- src/controller/editingcontroller.js | 2 +- src/view/attributeelement.js | 2 +- src/view/containerelement.js | 2 +- src/view/document.js | 4 ++-- src/view/documentfragment.js | 5 +++-- src/view/domconverter.js | 2 +- src/view/downcastwriter.js | 8 +++++--- src/view/element.js | 2 +- src/view/emptyelement.js | 2 +- src/view/node.js | 1 + src/view/rooteditableelement.js | 2 +- src/view/uielement.js | 2 +- src/view/view.js | 2 +- 14 files changed, 21 insertions(+), 17 deletions(-) diff --git a/src/controller/datacontroller.js b/src/controller/datacontroller.js index ce9880a40..7a1a06a22 100644 --- a/src/controller/datacontroller.js +++ b/src/controller/datacontroller.js @@ -47,7 +47,7 @@ export default class DataController { * Creates a data controller instance. * * @param {module:engine/model/model~Model} model Data model. - * @param {module:engine/view/stylesmap~StylesProcessor} stylesProcessor Styles processor. + * @param {module:engine/view/stylesmap~StylesProcessor} stylesProcessor The styles processor instance.. */ constructor( model, stylesProcessor ) { /** diff --git a/src/controller/editingcontroller.js b/src/controller/editingcontroller.js index a8a4c673e..412f5ebf5 100644 --- a/src/controller/editingcontroller.js +++ b/src/controller/editingcontroller.js @@ -31,7 +31,7 @@ export default class EditingController { * Creates an editing controller instance. * * @param {module:engine/model/model~Model} model Editing model. - * @param {module:engine/view/stylesmap~StylesProcessor} stylesProcessor Styles processor. + * @param {module:engine/view/stylesmap~StylesProcessor} stylesProcessor The styles processor instance.. */ constructor( model, stylesProcessor ) { /** diff --git a/src/view/attributeelement.js b/src/view/attributeelement.js index 52e981f11..626e470d1 100644 --- a/src/view/attributeelement.js +++ b/src/view/attributeelement.js @@ -33,7 +33,7 @@ export default class AttributeElement extends Element { * @see module:engine/view/downcastwriter~DowncastWriter#createAttributeElement * @see module:engine/view/element~Element * @protected - * @param {module:engine/view/document~Document} document A document where the element belongs to. + * @param {module:engine/view/document~Document} document The document instance to which this element belongs. * @param {String} name Node name. * @param {Object|Iterable} [attrs] Collection of attributes. * @param {module:engine/view/node~Node|Iterable.} [children] diff --git a/src/view/containerelement.js b/src/view/containerelement.js index ab501d0a9..753b71867 100644 --- a/src/view/containerelement.js +++ b/src/view/containerelement.js @@ -37,7 +37,7 @@ export default class ContainerElement extends Element { * @see module:engine/view/downcastwriter~DowncastWriter#createContainerElement * @see module:engine/view/element~Element * @protected - * @param {module:engine/view/document~Document} document A document where the element belongs to. + * @param {module:engine/view/document~Document} document The document instance to which this element belongs. * @param {String} name Node name. * @param {Object|Iterable} [attrs] Collection of attributes. * @param {module:engine/view/node~Node|Iterable.} [children] diff --git a/src/view/document.js b/src/view/document.js index 975ab1a30..c79b1a271 100644 --- a/src/view/document.js +++ b/src/view/document.js @@ -24,7 +24,7 @@ export default class Document { /** * Creates a Document instance. * - * @param {module:engine/view/stylesmap~StylesProcessor} stylesProcessor Styles processor. + * @param {module:engine/view/stylesmap~StylesProcessor} stylesProcessor The styles processor instance.. */ constructor( stylesProcessor ) { /** @@ -49,7 +49,7 @@ export default class Document { this.roots = new Collection( { idProperty: 'rootName' } ); /** - * StylesProcessor is responsible for writing and reading a normalized styles object. + * The styles processor instance used by this document when normalizing styles. * * @readonly * @member {module:engine/view/stylesmap~StylesProcessor} diff --git a/src/view/documentfragment.js b/src/view/documentfragment.js index 1ff1bab52..1bda12313 100644 --- a/src/view/documentfragment.js +++ b/src/view/documentfragment.js @@ -25,14 +25,15 @@ export default class DocumentFragment { * Creates new DocumentFragment instance. * * @protected - * @param {module:engine/view/document~Document} document A document where the document fragment belongs to. + * @param {module:engine/view/document~Document} document The document to which this document fragment belongs. * @param {module:engine/view/node~Node|Iterable.} [children] * A list of nodes to be inserted into the created document fragment. */ constructor( document, children ) { /** - * A document where the document fragment belongs to. + * The document to which this document fragment belongs. * + * @readonly * @member {module:engine/view/document~Document} */ this.document = document; diff --git a/src/view/domconverter.js b/src/view/domconverter.js index 51656ff92..c8564a552 100644 --- a/src/view/domconverter.js +++ b/src/view/domconverter.js @@ -44,7 +44,7 @@ export default class DomConverter { /** * Creates DOM converter. * - * @param {module:engine/view/document~Document} document + * @param {module:engine/view/document~Document} document The view document instance. * @param {Object} options Object with configuration options. * @param {module:engine/view/filler~BlockFillerMode} [options.blockFillerMode='br'] The type of the block filler to use. */ diff --git a/src/view/downcastwriter.js b/src/view/downcastwriter.js index d8db67105..9f9d3e0b7 100644 --- a/src/view/downcastwriter.js +++ b/src/view/downcastwriter.js @@ -38,10 +38,12 @@ import { isPlainObject } from 'lodash-es'; */ export default class DowncastWriter { /** - * @param {module:engine/view/document~Document} document + * @param {module:engine/view/document~Document} document The view document instance. */ constructor( document ) { /** + * The view document instance in which this writer operates. + * * @readonly * @type {module:engine/view/document~Document} */ @@ -988,7 +990,7 @@ export default class DowncastWriter { /** * Creates a range spanning from `start` position to `end` position. * - * **Note:** This factory method creates it's own {@link module:engine/view/position~Position} instances basing on passed values. + * **Note:** This factory method creates its own {@link module:engine/view/position~Position} instances basing on passed values. * * @param {module:engine/view/position~Position} start Start position. * @param {module:engine/view/position~Position} [end] End position. If not set, range will be collapsed at `start` position. @@ -1810,7 +1812,7 @@ function breakTextNode( position ) { position.parent._data = position.parent.data.slice( 0, position.offset ); // Insert new text node after position's parent text node. - position.parent.parent._insertChild( position.parent.index + 1, new Text( position.parent.document, textToMove ) ); + position.parent.parent._insertChild( position.parent.index + 1, new Text( position.root.document, textToMove ) ); // Return new position between two newly created text nodes. return new Position( position.parent.parent, position.parent.index + 1 ); diff --git a/src/view/element.js b/src/view/element.js index a15dbe7c8..078c5e9f6 100644 --- a/src/view/element.js +++ b/src/view/element.js @@ -53,7 +53,7 @@ export default class Element extends Node { * new Element( 'div', mapOfAttributes ); // map * * @protected - * @param {module:engine/view/document~Document} document A document where the element belongs to. + * @param {module:engine/view/document~Document} document The document instance to which this element belongs. * @param {String} name Node name. * @param {Object|Iterable} [attrs] Collection of attributes. * @param {module:engine/view/node~Node|Iterable.} [children] diff --git a/src/view/emptyelement.js b/src/view/emptyelement.js index b6af5ae99..39182de91 100644 --- a/src/view/emptyelement.js +++ b/src/view/emptyelement.js @@ -28,7 +28,7 @@ export default class EmptyElement extends Element { * * @see module:engine/view/downcastwriter~DowncastWriter#createEmptyElement * @protected - * @param {module:engine/view/document~Document} document A document where the element belongs to. + * @param {module:engine/view/document~Document} document The document instance to which this element belongs. * @param {String} name Node name. * @param {Object|Iterable} [attrs] Collection of attributes. * @param {module:engine/view/node~Node|Iterable.} [children] diff --git a/src/view/node.js b/src/view/node.js index f33f5461a..3538ddc47 100644 --- a/src/view/node.js +++ b/src/view/node.js @@ -35,6 +35,7 @@ export default class Node { /** * A document where the node belongs to. * + * @readonly * @member {module:engine/view/document~Document} */ this.document = document; diff --git a/src/view/rooteditableelement.js b/src/view/rooteditableelement.js index 2ca25e7fe..75337cb21 100644 --- a/src/view/rooteditableelement.js +++ b/src/view/rooteditableelement.js @@ -22,7 +22,7 @@ export default class RootEditableElement extends EditableElement { /** * Creates root editable element. * - * @param {module:engine/view/document~Document} document A document where the element belongs to. + * @param {module:engine/view/document~Document} document The document instance to which this element belongs. * @param {String} name Node name. */ constructor( document, name ) { diff --git a/src/view/uielement.js b/src/view/uielement.js index a4c5e40f2..c2f2a0718 100644 --- a/src/view/uielement.js +++ b/src/view/uielement.js @@ -41,7 +41,7 @@ export default class UIElement extends Element { * * @see module:engine/view/downcastwriter~DowncastWriter#createUIElement * @protected - * @param {module:engine/view/document~Document} document A document where the element belongs to. + * @param {module:engine/view/document~Document} document The document instance to which this element belongs. * @param {String} name Node name. * @param {Object|Iterable} [attributes] Collection of attributes. * @param {module:engine/view/node~Node|Iterable.} [children] diff --git a/src/view/view.js b/src/view/view.js index 93f648a38..4ccb04881 100644 --- a/src/view/view.js +++ b/src/view/view.js @@ -63,7 +63,7 @@ import env from '@ckeditor/ckeditor5-utils/src/env'; */ export default class View { /** - * @param {module:engine/view/stylesmap~StylesProcessor} stylesProcessor Styles processor. + * @param {module:engine/view/stylesmap~StylesProcessor} stylesProcessor The styles processor instance.. */ constructor( stylesProcessor ) { /** From fb8e77ac8df1308da392c4c3e7958d7a86284816 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Piotrek=20Koszuli=C5=84ski?= Date: Tue, 3 Mar 2020 14:04:52 +0100 Subject: [PATCH 34/34] Docs and other improvements. --- src/controller/datacontroller.js | 2 +- src/controller/editingcontroller.js | 2 +- src/view/document.js | 2 +- src/view/element.js | 6 +++--- src/view/node.js | 13 +++++++------ src/view/placeholder.js | 13 ++++++------- src/view/text.js | 4 ++-- src/view/upcastwriter.js | 4 +++- src/view/view.js | 2 +- 9 files changed, 25 insertions(+), 23 deletions(-) diff --git a/src/controller/datacontroller.js b/src/controller/datacontroller.js index 7a1a06a22..848444769 100644 --- a/src/controller/datacontroller.js +++ b/src/controller/datacontroller.js @@ -47,7 +47,7 @@ export default class DataController { * Creates a data controller instance. * * @param {module:engine/model/model~Model} model Data model. - * @param {module:engine/view/stylesmap~StylesProcessor} stylesProcessor The styles processor instance.. + * @param {module:engine/view/stylesmap~StylesProcessor} stylesProcessor The styles processor instance. */ constructor( model, stylesProcessor ) { /** diff --git a/src/controller/editingcontroller.js b/src/controller/editingcontroller.js index 412f5ebf5..145ce7795 100644 --- a/src/controller/editingcontroller.js +++ b/src/controller/editingcontroller.js @@ -31,7 +31,7 @@ export default class EditingController { * Creates an editing controller instance. * * @param {module:engine/model/model~Model} model Editing model. - * @param {module:engine/view/stylesmap~StylesProcessor} stylesProcessor The styles processor instance.. + * @param {module:engine/view/stylesmap~StylesProcessor} stylesProcessor The styles processor instance. */ constructor( model, stylesProcessor ) { /** diff --git a/src/view/document.js b/src/view/document.js index c79b1a271..2d1738541 100644 --- a/src/view/document.js +++ b/src/view/document.js @@ -24,7 +24,7 @@ export default class Document { /** * Creates a Document instance. * - * @param {module:engine/view/stylesmap~StylesProcessor} stylesProcessor The styles processor instance.. + * @param {module:engine/view/stylesmap~StylesProcessor} stylesProcessor The styles processor instance. */ constructor( stylesProcessor ) { /** diff --git a/src/view/element.js b/src/view/element.js index 078c5e9f6..9bd3efebb 100644 --- a/src/view/element.js +++ b/src/view/element.js @@ -48,9 +48,9 @@ export default class Element extends Node { * * Attributes can be passed in various formats: * - * new Element( 'div', { class: 'editor', contentEditable: 'true' } ); // object - * new Element( 'div', [ [ 'class', 'editor' ], [ 'contentEditable', 'true' ] ] ); // map-like iterator - * new Element( 'div', mapOfAttributes ); // map + * new Element( viewDocument, 'div', { class: 'editor', contentEditable: 'true' } ); // object + * new Element( viewDocument, 'div', [ [ 'class', 'editor' ], [ 'contentEditable', 'true' ] ] ); // map-like iterator + * new Element( viewDocument, 'div', mapOfAttributes ); // map * * @protected * @param {module:engine/view/document~Document} document The document instance to which this element belongs. diff --git a/src/view/node.js b/src/view/node.js index 3538ddc47..719120930 100644 --- a/src/view/node.js +++ b/src/view/node.js @@ -17,11 +17,11 @@ import { clone } from 'lodash-es'; import '@ckeditor/ckeditor5-utils/src/version'; /** - * Abstract tree view node class. + * Abstract view node class. * * This is an abstract class. Its constructor should not be used directly. - * Use the {@link module:engine/view/element~Element} class to create view elements - * or {@link module:engine/view/text~Text} class to create view text nodes. + * Use the {@link module:engine/view/downcastwriter~DowncastWriter} or {@link module:engine/view/upcastwriter~UpcastWriter} + * to create new instances of view nodes. * * @abstract */ @@ -29,11 +29,12 @@ export default class Node { /** * Creates a tree view node. * - * @param {module:engine/view/document~Document} document A document where the node belongs to. + * @protected + * @param {module:engine/view/document~Document} document The document instance to which this node belongs. */ constructor( document ) { /** - * A document where the node belongs to. + * The document instance to which this node belongs. * * @readonly * @member {module:engine/view/document~Document} @@ -119,7 +120,7 @@ export default class Node { } /** - * Returns true if a node is in a tree rooted in an element of the root type. + * Returns true if the node is in a tree rooted in the document (is a descendant of one of its roots). * * @returns {Boolean} */ diff --git a/src/view/placeholder.js b/src/view/placeholder.js index 806383056..b8fc3c9a4 100644 --- a/src/view/placeholder.js +++ b/src/view/placeholder.js @@ -140,20 +140,19 @@ export function hidePlaceholder( writer, element ) { * {@link module:engine/view/placeholder~enablePlaceholder `enablePlaceholder()`} in that case or make * sure the correct element is passed to the helper. * - * @param {module:engine/view/element~Element|module:engine/view/documentfragment~DocumentFragment} elementOrDocumentFragment + * @param {module:engine/view/element~Element} element * @returns {Boolean} */ -export function needsPlaceholder( elementOrDocumentFragment ) { - // TODO: How to check whether the element was removed from the document? - if ( elementOrDocumentFragment.root.is( 'documentFragment' ) ) { +export function needsPlaceholder( element ) { + if ( !element.isAttached() ) { return false; } // The element is empty only as long as it contains nothing but uiElements. - const isEmptyish = !Array.from( elementOrDocumentFragment.getChildren() ) + const isEmptyish = !Array.from( element.getChildren() ) .some( element => !element.is( 'uiElement' ) ); - const doc = elementOrDocumentFragment.document; + const doc = element.document; // If the element is empty and the document is blurred. if ( !doc.isFocused && isEmptyish ) { @@ -164,7 +163,7 @@ export function needsPlaceholder( elementOrDocumentFragment ) { const selectionAnchor = viewSelection.anchor; // If document is focused and the element is empty but the selection is not anchored inside it. - if ( isEmptyish && selectionAnchor && selectionAnchor.parent !== elementOrDocumentFragment ) { + if ( isEmptyish && selectionAnchor && selectionAnchor.parent !== element ) { return true; } diff --git a/src/view/text.js b/src/view/text.js index 86b4ab3c7..27636d59f 100644 --- a/src/view/text.js +++ b/src/view/text.js @@ -12,7 +12,7 @@ import Node from './node'; /** * Tree view text node. * - * The constructor of this class shouldn't be used directly. To create new Text instances + * The constructor of this class should not be used directly. To create a new text node instance * use the {@link module:engine/view/downcastwriter~DowncastWriter#createText `DowncastWriter#createText()`} * method when working on data downcasted from the model or the * {@link module:engine/view/upcastwriter~UpcastWriter#createText `UpcastWriter#createText()`} @@ -25,7 +25,7 @@ export default class Text extends Node { * Creates a tree view text node. * * @protected - * @param {module:engine/view/document~Document} document A document where the text belongs to. + * @param {module:engine/view/document~Document} document The document instance to which this text node belongs. * @param {String} data The text's data. */ constructor( document, data ) { diff --git a/src/view/upcastwriter.js b/src/view/upcastwriter.js index 251a8c214..973e81846 100644 --- a/src/view/upcastwriter.js +++ b/src/view/upcastwriter.js @@ -36,10 +36,12 @@ import Selection from './selection'; */ export default class UpcastWriter { /** - * @param {module:engine/view/document~Document} document + * @param {module:engine/view/document~Document} document The view document instance in which this upcast writer operates. */ constructor( document ) { /** + * The view document instance in which this upcast writer operates. + * * @readonly * @type {module:engine/view/document~Document} */ diff --git a/src/view/view.js b/src/view/view.js index 4ccb04881..379092a32 100644 --- a/src/view/view.js +++ b/src/view/view.js @@ -63,7 +63,7 @@ import env from '@ckeditor/ckeditor5-utils/src/env'; */ export default class View { /** - * @param {module:engine/view/stylesmap~StylesProcessor} stylesProcessor The styles processor instance.. + * @param {module:engine/view/stylesmap~StylesProcessor} stylesProcessor The styles processor instance. */ constructor( stylesProcessor ) { /**