From 330c6dfd610163b017ea884367edb8212b804373 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Ella=20van=C2=A0Durpe?= Date: Thu, 12 Dec 2019 15:13:16 +0200 Subject: [PATCH] Convert to blocks: preserve alignment (#19097) * Raw handler: preserve alignment * Add heading support * Fix typo --- .../block-library/src/heading/transforms.js | 48 ++++++++++++------- .../block-library/src/paragraph/transforms.js | 27 ++++++++++- .../src/api/raw-handling/paste-handler.js | 2 +- packages/blocks/src/api/raw-handling/utils.js | 5 +- .../blocks-raw-handling.test.js.snap | 6 +++ test/integration/blocks-raw-handling.test.js | 5 ++ 6 files changed, 72 insertions(+), 21 deletions(-) diff --git a/packages/block-library/src/heading/transforms.js b/packages/block-library/src/heading/transforms.js index 70904e4b68e4ba..f4ad976e418411 100644 --- a/packages/block-library/src/heading/transforms.js +++ b/packages/block-library/src/heading/transforms.js @@ -10,6 +10,7 @@ import { * Internal dependencies */ import { getLevelFromHeadingNodeName } from './shared'; +import { name } from './block.json'; const transforms = { from: [ @@ -17,7 +18,7 @@ const transforms = { type: 'block', blocks: [ 'core/paragraph' ], transform: ( { content } ) => { - return createBlock( 'core/heading', { + return createBlock( name, { content, } ); }, @@ -25,29 +26,42 @@ const transforms = { { type: 'raw', selector: 'h1,h2,h3,h4,h5,h6', - schema: ( { phrasingContentSchema } ) => ( { - h1: { children: phrasingContentSchema }, - h2: { children: phrasingContentSchema }, - h3: { children: phrasingContentSchema }, - h4: { children: phrasingContentSchema }, - h5: { children: phrasingContentSchema }, - h6: { children: phrasingContentSchema }, - } ), + schema: ( { phrasingContentSchema, isPaste } ) => { + const schema = { + children: phrasingContentSchema, + attributes: isPaste ? [] : [ 'style' ], + }; + return { + h1: schema, + h2: schema, + h3: schema, + h4: schema, + h5: schema, + h6: schema, + }; + }, transform( node ) { - return createBlock( 'core/heading', { - ...getBlockAttributes( - 'core/heading', - node.outerHTML - ), - level: getLevelFromHeadingNodeName( node.nodeName ), - } ); + const attributes = getBlockAttributes( name, node.outerHTML ); + const { textAlign } = node.style; + + attributes.level = getLevelFromHeadingNodeName( node.nodeName ); + + if ( + textAlign === 'left' || + textAlign === 'center' || + textAlign === 'right' + ) { + attributes.align = textAlign; + } + + return createBlock( name, attributes ); }, }, ...[ 2, 3, 4, 5, 6 ].map( ( level ) => ( { type: 'prefix', prefix: Array( level + 1 ).join( '#' ), transform( content ) { - return createBlock( 'core/heading', { + return createBlock( name, { level, content, } ); diff --git a/packages/block-library/src/paragraph/transforms.js b/packages/block-library/src/paragraph/transforms.js index 98ef95b68cfefe..f319c59f9c07fb 100644 --- a/packages/block-library/src/paragraph/transforms.js +++ b/packages/block-library/src/paragraph/transforms.js @@ -1,3 +1,13 @@ +/** + * WordPress dependencies + */ +import { createBlock, getBlockAttributes } from '@wordpress/blocks'; + +/** + * Internal dependencies + */ +import { name } from './block.json'; + const transforms = { from: [ { @@ -5,11 +15,26 @@ const transforms = { // Paragraph is a fallback and should be matched last. priority: 20, selector: 'p', - schema: ( { phrasingContentSchema } ) => ( { + schema: ( { phrasingContentSchema, isPaste } ) => ( { p: { children: phrasingContentSchema, + attributes: isPaste ? [] : [ 'style' ], }, } ), + transform( node ) { + const attributes = getBlockAttributes( name, node.outerHTML ); + const { textAlign } = node.style; + + if ( + textAlign === 'left' || + textAlign === 'center' || + textAlign === 'right' + ) { + attributes.align = textAlign; + } + + return createBlock( name, attributes ); + }, }, ], }; diff --git a/packages/blocks/src/api/raw-handling/paste-handler.js b/packages/blocks/src/api/raw-handling/paste-handler.js index f126e050c15c08..d486328032ceef 100644 --- a/packages/blocks/src/api/raw-handling/paste-handler.js +++ b/packages/blocks/src/api/raw-handling/paste-handler.js @@ -197,7 +197,7 @@ export function pasteHandler( { HTML = '', plainText = '', mode = 'AUTO', tagNam const rawTransforms = getRawTransformations(); const phrasingContentSchema = getPhrasingContentSchema( 'paste' ); - const blockContentSchema = getBlockContentSchema( rawTransforms, phrasingContentSchema ); + const blockContentSchema = getBlockContentSchema( rawTransforms, phrasingContentSchema, true ); const blocks = compact( flatMap( pieces, ( piece ) => { // Already a block from shortcode. diff --git a/packages/blocks/src/api/raw-handling/utils.js b/packages/blocks/src/api/raw-handling/utils.js index 20ed5a1e9dec31..a70d78c3e34174 100644 --- a/packages/blocks/src/api/raw-handling/utils.js +++ b/packages/blocks/src/api/raw-handling/utils.js @@ -24,14 +24,15 @@ const { ELEMENT_NODE, TEXT_NODE } = window.Node; * * @param {Array} transforms Block transforms, of the `raw` type. * @param {Object} phrasingContentSchema The phrasing content schema. + * @param {Object} isPaste Whether the context is pasting or not. * * @return {Object} A complete block content schema. */ -export function getBlockContentSchema( transforms, phrasingContentSchema ) { +export function getBlockContentSchema( transforms, phrasingContentSchema, isPaste ) { const schemas = transforms.map( ( { isMatch, blockName, schema } ) => { const hasAnchorSupport = hasBlockSupport( blockName, 'anchor' ); - schema = isFunction( schema ) ? schema( { phrasingContentSchema } ) : schema; + schema = isFunction( schema ) ? schema( { phrasingContentSchema, isPaste } ) : schema; // If the block does not has anchor support and the transform does not // provides an isMatch we can return the schema right away. diff --git a/test/integration/__snapshots__/blocks-raw-handling.test.js.snap b/test/integration/__snapshots__/blocks-raw-handling.test.js.snap index 9cefe8bffb6fd9..efe2b7dba8f468 100644 --- a/test/integration/__snapshots__/blocks-raw-handling.test.js.snap +++ b/test/integration/__snapshots__/blocks-raw-handling.test.js.snap @@ -116,3 +116,9 @@ exports[`rawHandler should not strip any text-level elements 1`] = `

This is ncorect

" `; + +exports[`rawHandler should preserve alignment 1`] = ` +" +

center

+" +`; diff --git a/test/integration/blocks-raw-handling.test.js b/test/integration/blocks-raw-handling.test.js index d042702d37b0d2..d505a119fe9cfb 100644 --- a/test/integration/blocks-raw-handling.test.js +++ b/test/integration/blocks-raw-handling.test.js @@ -358,4 +358,9 @@ describe( 'rawHandler', () => { const HTML = '

This is ncorect

'; expect( serialize( rawHandler( { HTML } ) ) ).toMatchSnapshot(); } ); + + it( 'should preserve alignment', () => { + const HTML = '

center

'; + expect( serialize( rawHandler( { HTML } ) ) ).toMatchSnapshot(); + } ); } );