浏览代码

Make findAttributeRange code less Link-specific.

Tomek Wytrębowicz 5 年之前
父节点
当前提交
49276bc799

+ 1 - 1
packages/ckeditor5-link/src/linkcommand.js

@@ -160,7 +160,7 @@ export default class LinkCommand extends Command {
 				// When selection is inside text with `linkHref` attribute.
 				if ( selection.hasAttribute( 'linkHref' ) ) {
 					// Then update `linkHref` value.
-					const linkRange = findAttributeRange( position, selection.getAttribute( 'linkHref' ), model );
+					const linkRange = findAttributeRange( position, 'linkHref', selection.getAttribute( 'linkHref' ), model );
 
 					writer.setAttribute( 'linkHref', href, linkRange );
 

+ 1 - 1
packages/ckeditor5-link/src/linkediting.js

@@ -339,7 +339,7 @@ export default class LinkEditing extends Plugin {
 			}
 
 			const position = selection.getFirstPosition();
-			const linkRange = findAttributeRange( position, selection.getAttribute( 'linkHref' ), editor.model );
+			const linkRange = findAttributeRange( position, 'linkHref', selection.getAttribute( 'linkHref' ), editor.model );
 
 			// ...check whether clicked start/end boundary of the link.
 			// If so, remove the `linkHref` attribute.

+ 7 - 1
packages/ckeditor5-link/src/unlinkcommand.js

@@ -57,7 +57,13 @@ export default class UnlinkCommand extends Command {
 		model.change( writer => {
 			// Get ranges to unlink.
 			const rangesToUnlink = selection.isCollapsed ?
-				[ findAttributeRange( selection.getFirstPosition(), selection.getAttribute( 'linkHref' ), model ) ] : selection.getRanges();
+				[ findAttributeRange(
+					selection.getFirstPosition(),
+					'linkHref',
+					selection.getAttribute( 'linkHref' ),
+					model
+				) ] :
+				selection.getRanges();
 
 			// Remove `linkHref` attribute from specified ranges.
 			for ( const range of rangesToUnlink ) {

+ 14 - 8
packages/ckeditor5-typing/src/utils/findattributerange.js

@@ -8,34 +8,40 @@
  */
 
 /**
- * Returns a range containing the entire link in which the given `position` is placed.
+ * Returns a range containing the entire {@link module:engine/view/attributeelement~AttributeElement#childCount attribute element}
+ * in which the given `position` is placed.
  *
  * It can be used e.g. to get the entire range on which the `linkHref` attribute needs to be changed when having a
  * selection inside a link.
  *
  * @param {module:engine/model/position~Position} position The start position.
- * @param {String} value The `linkHref` attribute value.
+ * @param {String} attributeName The attribute name.
+ * @param {String} value The attribute value.
  * @returns {module:engine/model/range~Range} The link range.
  */
-export default function findAttributeRange( position, value, model ) {
-	return model.createRange( _findBound( position, value, true, model ), _findBound( position, value, false, model ) );
+export default function findAttributeRange( position, attributeName, value, model ) {
+	return model.createRange(
+		_findBound( position, attributeName, value, true, model ),
+		_findBound( position, attributeName, value, false, model )
+	);
 }
 
-// Walks forward or backward (depends on the `lookBack` flag), node by node, as long as they have the same `linkHref` attribute value
+// Walks forward or backward (depends on the `lookBack` flag), node by node, as long as they have the same attribute value
 // and returns a position just before or after (depends on the `lookBack` flag) the last matched node.
 //
 // @param {module:engine/model/position~Position} position The start position.
-// @param {String} value The `linkHref` attribute value.
+// @param {String} attributeName The attribute name.
+// @param {String} value The attribute value.
 // @param {Boolean} lookBack Whether the walk direction is forward (`false`) or backward (`true`).
 // @returns {module:engine/model/position~Position} The position just before the last matched node.
-function _findBound( position, value, lookBack, model ) {
+function _findBound( position, attributeName, value, lookBack, model ) {
 	// Get node before or after position (depends on `lookBack` flag).
 	// When position is inside text node then start searching from text node.
 	let node = position.textNode || ( lookBack ? position.nodeBefore : position.nodeAfter );
 
 	let lastNode = null;
 
-	while ( node && node.getAttribute( 'linkHref' ) == value ) {
+	while ( node && node.getAttribute( attributeName ) == value ) {
 		lastNode = node;
 		node = lookBack ? node.previousSibling : node.nextSibling;
 	}

+ 6 - 1
packages/ckeditor5-typing/src/utils/inlinehighlight.js

@@ -33,7 +33,12 @@ export default function setupLinkHighlight( editor, className ) {
 		let changed = false;
 
 		if ( selection.hasAttribute( 'linkHref' ) ) {
-			const modelRange = findAttributeRange( selection.getFirstPosition(), selection.getAttribute( 'linkHref' ), editor.model );
+			const modelRange = findAttributeRange(
+				selection.getFirstPosition(),
+				'linkHref',
+				selection.getAttribute( 'linkHref' ),
+				editor.model
+			);
 			const viewRange = editor.editing.mapper.toViewRange( modelRange );
 
 			// There might be multiple `a` elements in the `viewRange`, for example, when the `a` element is

+ 10 - 10
packages/ckeditor5-typing/tests/utils/findattributerange.js

@@ -23,7 +23,7 @@ describe( 'findAttributeRange', () => {
 		setData( model, '<$text linkHref="url">foobar</$text>' );
 
 		const startPosition = model.createPositionAt( root, [ 3 ] );
-		const result = findAttributeRange( startPosition, 'url', model );
+		const result = findAttributeRange( startPosition, 'linkHref', 'url', model );
 
 		expect( result ).to.instanceOf( Range );
 		expect( result.isEqual( model.createRange( model.createPositionAt( root, 0 ), model.createPositionAt( root, 6 ) ) ) ).to.true;
@@ -33,7 +33,7 @@ describe( 'findAttributeRange', () => {
 		setData( model, 'abc <$text linkHref="url">foobar</$text> abc' );
 
 		const startPosition = model.createPositionAt( root, [ 7 ] );
-		const result = findAttributeRange( startPosition, 'url', model );
+		const result = findAttributeRange( startPosition, 'linkHref', 'url', model );
 
 		expect( result ).to.instanceOf( Range );
 		expect( result.isEqual( model.createRange( model.createPositionAt( root, 4 ), model.createPositionAt( root, 10 ) ) ) ).to.true;
@@ -43,7 +43,7 @@ describe( 'findAttributeRange', () => {
 		setData( model, '<$text linkHref="url">foobar</$text>' );
 
 		const startPosition = model.createPositionAt( root, [ 0 ] );
-		const result = findAttributeRange( startPosition, 'url', model );
+		const result = findAttributeRange( startPosition, 'linkHref', 'url', model );
 
 		expect( result ).to.instanceOf( Range );
 		expect( result.isEqual( model.createRange( model.createPositionAt( root, 0 ), model.createPositionAt( root, 6 ) ) ) ).to.true;
@@ -53,7 +53,7 @@ describe( 'findAttributeRange', () => {
 		setData( model, 'abc <$text linkHref="url">foobar</$text> abc' );
 
 		const startPosition = model.createPositionAt( root, [ 4 ] );
-		const result = findAttributeRange( startPosition, 'url', model );
+		const result = findAttributeRange( startPosition, 'linkHref', 'url', model );
 
 		expect( result ).to.instanceOf( Range );
 		expect( result.isEqual( model.createRange( model.createPositionAt( root, 4 ), model.createPositionAt( root, 10 ) ) ) ).to.true;
@@ -63,7 +63,7 @@ describe( 'findAttributeRange', () => {
 		setData( model, '<$text linkHref="url">foobar</$text>' );
 
 		const startPosition = model.createPositionAt( root, [ 6 ] );
-		const result = findAttributeRange( startPosition, 'url', model );
+		const result = findAttributeRange( startPosition, 'linkHref', 'url', model );
 
 		expect( result ).to.instanceOf( Range );
 		expect( result.isEqual( model.createRange( model.createPositionAt( root, 0 ), model.createPositionAt( root, 6 ) ) ) ).to.true;
@@ -73,7 +73,7 @@ describe( 'findAttributeRange', () => {
 		setData( model, 'abc <$text linkHref="url">foobar</$text> abc' );
 
 		const startPosition = model.createPositionAt( root, [ 10 ] );
-		const result = findAttributeRange( startPosition, 'url', model );
+		const result = findAttributeRange( startPosition, 'linkHref', 'url', model );
 
 		expect( result ).to.instanceOf( Range );
 		expect( result.isEqual( model.createRange( model.createPositionAt( root, 4 ), model.createPositionAt( root, 10 ) ) ) ).to.true;
@@ -83,7 +83,7 @@ describe( 'findAttributeRange', () => {
 		setData( model, '<$text linkHref="other">abc</$text><$text linkHref="url">foobar</$text><$text linkHref="other">abc</$text>' );
 
 		const startPosition = model.createPositionAt( root, [ 6 ] );
-		const result = findAttributeRange( startPosition, 'url', model );
+		const result = findAttributeRange( startPosition, 'linkHref', 'url', model );
 
 		expect( result ).to.instanceOf( Range );
 		expect( result.isEqual( model.createRange( model.createPositionAt( root, 3 ), model.createPositionAt( root, 9 ) ) ) ).to.true;
@@ -93,7 +93,7 @@ describe( 'findAttributeRange', () => {
 		setData( model, '<$text linkHref="other">abc</$text><$text linkHref="url">foobar</$text><$text linkHref="other">abc</$text>' );
 
 		const startPosition = model.createPositionAt( root, [ 3 ] );
-		const result = findAttributeRange( startPosition, 'url', model );
+		const result = findAttributeRange( startPosition, 'linkHref', 'url', model );
 
 		expect( result ).to.instanceOf( Range );
 		expect( result.isEqual( model.createRange( model.createPositionAt( root, 3 ), model.createPositionAt( root, 9 ) ) ) ).to.true;
@@ -103,7 +103,7 @@ describe( 'findAttributeRange', () => {
 		setData( model, '<$text linkHref="other">abc</$text><$text linkHref="url">foobar</$text><$text linkHref="other">abc</$text>' );
 
 		const startPosition = model.createPositionAt( root, [ 9 ] );
-		const result = findAttributeRange( startPosition, 'url', model );
+		const result = findAttributeRange( startPosition, 'linkHref', 'url', model );
 
 		expect( result ).to.instanceOf( Range );
 		expect( result.isEqual( model.createRange( model.createPositionAt( root, 3 ), model.createPositionAt( root, 9 ) ) ) ).to.true;
@@ -118,7 +118,7 @@ describe( 'findAttributeRange', () => {
 		);
 
 		const startPosition = model.createPositionAt( root.getNodeByPath( [ 1 ] ), 3 );
-		const result = findAttributeRange( startPosition, 'url', model );
+		const result = findAttributeRange( startPosition, 'linkHref', 'url', model );
 
 		expect( result ).to.instanceOf( Range );
 		const expectedRange = model.createRange(