Procházet zdrojové kódy

Merge pull request #28 from ckeditor/t/6

t/6: Basic DOM utils.
Piotrek Koszuliński před 9 roky
rodič
revize
15376187b3

+ 47 - 0
packages/ckeditor5-utils/src/dom/createelement.js

@@ -0,0 +1,47 @@
+/**
+ * @license Copyright (c) 2003-2015, CKSource - Frederico Knabben. All rights reserved.
+ * For licensing, see LICENSE.md.
+ */
+
+'use strict';
+
+import isString from '../lib/lodash/isString.js';
+import utils from '../utils.js';
+
+/**
+ * Creates element with attributes and children.
+ *
+ *		createElement( document, 'p' ); // <p>
+ *		createElement( document, 'p', { class: 'foo' } ); // <p class="foo">
+ *		createElement( document, 'p', null, 'foo' ); // <p>foo</p>
+ *		createElement( document, 'p', null, [ 'foo', createElement( document, 'img' ) ] ); // <p>foo<img></p>
+ *
+ * @method utils.dom.createElement
+ * @param {Document} doc Document used to create element.
+ * @param {String} name Name of the element.
+ * @param {Object} attributes Object keys will become attributes keys and object values will became attributes values.
+ * @param {Node|String|Array.<Node|String>} children Child or array of children. Strings will be automatically turned
+ * into Text nodes.
+ * @returns {Element} Created element.
+ */
+export default function createElement( doc, name, attributes = {}, children = [] ) {
+	const element = doc.createElement( name );
+
+	for ( let key in attributes ) {
+		element.setAttribute( key, attributes[ key ] );
+	}
+
+	if ( isString( children ) || !utils.isIterable( children ) ) {
+		children = [ children ];
+	}
+
+	for ( let child of children ) {
+		if ( isString( child ) ) {
+			child = doc.createTextNode( child );
+		}
+
+		element.appendChild( child );
+	}
+
+	return element;
+}

+ 24 - 0
packages/ckeditor5-utils/src/dom/indexof.js

@@ -0,0 +1,24 @@
+/**
+ * @license Copyright (c) 2003-2015, CKSource - Frederico Knabben. All rights reserved.
+ * For licensing, see LICENSE.md.
+ */
+
+'use strict';
+
+/**
+ * Returns index of the node in the parent element.
+ *
+ * @method utils.dom.indexOf
+ * @param {Node} node Node which index is tested.
+ * @returns {Number} Index of the node in the parent element. Returns 0 if node has no parent.
+ */
+export default function indexOf( node ) {
+	let index = 0;
+
+	while ( node.previousSibling ) {
+		node = node.previousSibling;
+		index++;
+	}
+
+	return index;
+}

+ 17 - 0
packages/ckeditor5-utils/src/dom/insertat.js

@@ -0,0 +1,17 @@
+/**
+ * @license Copyright (c) 2003-2015, CKSource - Frederico Knabben. All rights reserved.
+ * For licensing, see LICENSE.md.
+ */
+
+'use strict';
+
+/**
+ * Inserts node to the parent at given index.
+ *
+ * @param {Element} parentElement Parent element.
+ * @param {Number} index Insertions index.
+ * @param {Node} nodeToInsert Node to insert.
+ */
+export default function insertAt( parentElement, index, nodeToInsert ) {
+	parentElement.insertBefore( nodeToInsert, parentElement.childNodes[ index ] || null );
+}

+ 19 - 0
packages/ckeditor5-utils/src/dom/remove.js

@@ -0,0 +1,19 @@
+/**
+ * @license Copyright (c) 2003-2015, CKSource - Frederico Knabben. All rights reserved.
+ * For licensing, see LICENSE.md.
+ */
+
+'use strict';
+
+/**
+ * Removes given node from parent.
+ *
+ * @param {Node} node Node to remove.
+ */
+export default function remove( node ) {
+	const parent = node.parentNode;
+
+	if ( parent ) {
+		parent.removeChild( node );
+	}
+}

+ 44 - 0
packages/ckeditor5-utils/tests/dom/createelement.js

@@ -0,0 +1,44 @@
+/**
+ * @license Copyright (c) 2003-2015, CKSource - Frederico Knabben. All rights reserved.
+ * For licensing, see LICENSE.md.
+ */
+
+/* bender-tags: dom */
+
+'use strict';
+
+import createElement from '/ckeditor5/utils/dom/createelement.js';
+
+describe( 'createElement', () => {
+	it( 'should create element', () => {
+		const p = createElement( document, 'p' );
+
+		expect( p.tagName.toLowerCase() ).to.equal( 'p' );
+		expect( p.childNodes.length ).to.equal( 0 );
+	} );
+
+	it( 'should create element with attribute', () => {
+		const p = createElement( document, 'p', { class: 'foo' } );
+
+		expect( p.tagName.toLowerCase() ).to.equal( 'p' );
+		expect( p.childNodes.length ).to.equal( 0 );
+		expect( p.getAttribute( 'class' ) ).to.equal( 'foo' );
+	} );
+
+	it( 'should create element with child text node', () => {
+		const p = createElement( document, 'p', null, 'foo' );
+
+		expect( p.tagName.toLowerCase() ).to.equal( 'p' );
+		expect( p.childNodes.length ).to.equal( 1 );
+		expect( p.childNodes[ 0 ].data ).to.equal( 'foo' );
+	} );
+
+	it( 'should create ', () => {
+		const p = createElement( document, 'p', null, [ 'foo', createElement( document, 'img' ) ] );
+
+		expect( p.tagName.toLowerCase() ).to.equal( 'p' );
+		expect( p.childNodes.length ).to.equal( 2 );
+		expect( p.childNodes[ 0 ].data ).to.equal( 'foo' );
+		expect( p.childNodes[ 1 ].tagName.toLowerCase() ).to.equal( 'img' );
+	} );
+} );

+ 33 - 0
packages/ckeditor5-utils/tests/dom/indexof.js

@@ -0,0 +1,33 @@
+/**
+ * @license Copyright (c) 2003-2015, CKSource - Frederico Knabben. All rights reserved.
+ * For licensing, see LICENSE.md.
+ */
+
+/* bender-tags: dom */
+
+'use strict';
+
+import indexOf from '/ckeditor5/utils/dom/indexof.js';
+
+describe( 'indexOf', () => {
+	it( 'should return 0 if element has no parent', () => {
+		const p = document.createElement( 'p' );
+
+		expect( indexOf( p ) ).to.equal( 0 );
+	} );
+
+	it( 'should return index of the node in parent', () => {
+		const div = document.createElement( 'div' );
+		const p0 = document.createElement( 'p' );
+		const p1 = document.createElement( 'p' );
+		const p2 = document.createElement( 'p' );
+
+		div.appendChild( p0 );
+		div.appendChild( p1 );
+		div.appendChild( p2 );
+
+		expect( indexOf( p0 ) ).to.equal( 0 );
+		expect( indexOf( p1 ) ).to.equal( 1 );
+		expect( indexOf( p2 ) ).to.equal( 2 );
+	} );
+} );

+ 63 - 0
packages/ckeditor5-utils/tests/dom/insertat.js

@@ -0,0 +1,63 @@
+/**
+ * @license Copyright (c) 2003-2015, CKSource - Frederico Knabben. All rights reserved.
+ * For licensing, see LICENSE.md.
+ */
+
+/* bender-tags: dom */
+
+'use strict';
+
+import insertAt from '/ckeditor5/utils/dom/insertat.js';
+
+describe( 'insertAt', () => {
+	it( 'should insert at given position', () => {
+		const div = document.createElement( 'div' );
+		const p0 = document.createElement( 'p' );
+		const p1 = document.createElement( 'p' );
+		const p2 = document.createElement( 'p' );
+
+		div.appendChild( p0 );
+		div.appendChild( p2 );
+
+		insertAt( div, 1, p1 );
+
+		expect( div.childNodes.length ).to.equal( 3 );
+		expect( div.childNodes[ 0 ] ).to.equal( p0 );
+		expect( div.childNodes[ 1 ] ).to.equal( p1 );
+		expect( div.childNodes[ 2 ] ).to.equal( p2 );
+	} );
+
+	it( 'should insert at the beginning', () => {
+		const div = document.createElement( 'div' );
+		const p0 = document.createElement( 'p' );
+		const p1 = document.createElement( 'p' );
+		const p2 = document.createElement( 'p' );
+
+		div.appendChild( p1 );
+		div.appendChild( p2 );
+
+		insertAt( div, 0, p0 );
+
+		expect( div.childNodes.length ).to.equal( 3 );
+		expect( div.childNodes[ 0 ] ).to.equal( p0 );
+		expect( div.childNodes[ 1 ] ).to.equal( p1 );
+		expect( div.childNodes[ 2 ] ).to.equal( p2 );
+	} );
+
+	it( 'should insert at the end', () => {
+		const div = document.createElement( 'div' );
+		const p0 = document.createElement( 'p' );
+		const p1 = document.createElement( 'p' );
+		const p2 = document.createElement( 'p' );
+
+		div.appendChild( p0 );
+		div.appendChild( p1 );
+
+		insertAt( div, 2, p2 );
+
+		expect( div.childNodes.length ).to.equal( 3 );
+		expect( div.childNodes[ 0 ] ).to.equal( p0 );
+		expect( div.childNodes[ 1 ] ).to.equal( p1 );
+		expect( div.childNodes[ 2 ] ).to.equal( p2 );
+	} );
+} );

+ 36 - 0
packages/ckeditor5-utils/tests/dom/remove.js

@@ -0,0 +1,36 @@
+/**
+ * @license Copyright (c) 2003-2015, CKSource - Frederico Knabben. All rights reserved.
+ * For licensing, see LICENSE.md.
+ */
+
+/* bender-tags: dom */
+
+'use strict';
+
+import remove from '/ckeditor5/utils/dom/remove.js';
+
+describe( 'remove', () => {
+	it( 'should remove element form parent', () => {
+		const div = document.createElement( 'div' );
+		const p0 = document.createElement( 'p' );
+		const p1 = document.createElement( 'p' );
+		const p2 = document.createElement( 'p' );
+
+		div.appendChild( p0 );
+		div.appendChild( p1 );
+		div.appendChild( p2 );
+
+		remove( p1 );
+
+		expect( p1.parentNode ).to.be.null;
+		expect( div.childNodes.length ).to.equal( 2 );
+	} );
+
+	it( 'should do nothing if element has no parent', () => {
+		const div = document.createElement( 'div' );
+
+		remove( div );
+
+		expect( div.parentNode ).to.be.null;
+	} );
+} );