浏览代码

Added: Conversion#attributeToAttribute should support free-value conversion.

Maciej Gołaszewski 7 年之前
父节点
当前提交
b983ff73cd

+ 8 - 1
packages/ckeditor5-engine/src/conversion/downcast-converters.js

@@ -427,7 +427,14 @@ function _normalizeToAttributeConfig( view ) {
 	if ( typeof view == 'string' ) {
 		return modelAttributeValue => ( { key: view, value: modelAttributeValue } );
 	} else if ( typeof view == 'object' ) {
-		return () => view;
+		// { key, value, ... }
+		if ( view.value ) {
+			return () => view;
+		}
+		// { key, ... }
+		else {
+			return modelAttributeValue => ( { key: view.key, value: modelAttributeValue } );
+		}
 	} else {
 		// function.
 		return view;

+ 5 - 1
packages/ckeditor5-engine/src/conversion/upcast-converters.js

@@ -430,7 +430,11 @@ function _normalizeModelAttributeConfig( config, viewAttributeKeyToCopy = null )
 	const defaultModelValue = viewAttributeKeyToCopy === null ? true : viewElement => viewElement.getAttribute( viewAttributeKeyToCopy );
 
 	const key = typeof config.model != 'object' ? config.model : config.model.key;
-	const value = typeof config.model != 'object' ? defaultModelValue : config.model.value;
+	let value = typeof config.model != 'object' ? defaultModelValue : config.model.value;
+
+	if ( typeof value == 'undefined' ) {
+		value = defaultModelValue;
+	}
 
 	config.model = { key, value };
 }

+ 19 - 0
packages/ckeditor5-engine/tests/conversion/conversion.js

@@ -585,6 +585,25 @@ describe( 'Conversion', () => {
 					'<p class="align-center">Foo</p>'
 				);
 			} );
+
+			it( 'config.view and config.model have name and key set', () => {
+				schema.extend( 'image', {
+					allowAttributes: [ 'source' ]
+				} );
+
+				conversion.attributeToAttribute( {
+					model: {
+						name: 'image',
+						key: 'source'
+					},
+					view: {
+						name: 'img',
+						key: 'src'
+					}
+				} );
+
+				test( '<img src="foo.jpg"></img>', '<image source="foo.jpg"></image>' );
+			} );
 		} );
 
 		function test( input, expectedModel, expectedView = null ) {

+ 35 - 0
packages/ckeditor5-engine/tests/conversion/downcast-converters.js

@@ -390,6 +390,41 @@ describe( 'downcast-helpers', () => {
 			expectResult( '<p></p>' );
 		} );
 
+		it( 'config.view is an object, only name and key are provided', () => {
+			conversion.for( 'downcast' ).add( downcastElementToElement( { model: 'paragraph', view: 'p' } ) );
+
+			const helper = downcastAttributeToAttribute( {
+				model: {
+					name: 'paragraph',
+					key: 'class'
+				},
+				view: {
+					name: 'paragraph',
+					key: 'class'
+				}
+			} );
+
+			conversion.for( 'downcast' ).add( helper );
+
+			model.change( writer => {
+				writer.insertElement( 'paragraph', { class: 'dark' }, modelRoot, 0 );
+			} );
+
+			expectResult( '<p class="dark"></p>' );
+
+			model.change( writer => {
+				writer.setAttribute( 'class', 'light', modelRoot.getChild( 0 ) );
+			} );
+
+			expectResult( '<p class="light"></p>' );
+
+			model.change( writer => {
+				writer.removeAttribute( 'class', modelRoot.getChild( 0 ) );
+			} );
+
+			expectResult( '<p></p>' );
+		} );
+
 		it( 'config.view is a function', () => {
 			const helper = downcastAttributeToAttribute( {
 				model: 'styled',

+ 15 - 0
packages/ckeditor5-engine/tests/conversion/upcast-converters.js

@@ -384,6 +384,21 @@ describe( 'upcast-helpers', () => {
 			);
 		} );
 
+		it( 'config.view has only key and name set', () => {
+			schema.extend( 'image', {
+				allowAttributes: [ 'source' ]
+			} );
+
+			const helper = upcastAttributeToAttribute( { view: { name: 'img', key: 'src' }, model: { name: 'image', key: 'source' } } );
+
+			conversion.for( 'upcast' ).add( helper );
+
+			expectResult(
+				new ViewAttributeElement( 'img', { src: 'foo.jpg' } ),
+				'<image source="foo.jpg"></image>'
+			);
+		} );
+
 		it( 'can be overwritten using priority', () => {
 			schema.extend( 'image', {
 				allowAttributes: [ 'src', 'source' ]