From 8bc2ad791c8acbf074731138a853da6f41f07ed7 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Ella=20van=C2=A0Durpe?= Date: Tue, 18 Oct 2022 16:01:52 +0200 Subject: [PATCH 1/4] List/quote: unwrap inner block when pressing Backspace at start --- .../src/components/block-list/block.js | 57 +++++++++++++++---- packages/block-library/src/list-item/index.js | 2 + .../block-library/src/list-item/transforms.js | 17 ++++++ packages/block-library/src/list/transforms.js | 11 ---- packages/blocks/README.md | 20 +++++-- packages/blocks/src/api/index.js | 1 + packages/blocks/src/api/utils.js | 37 ++++++------ 7 files changed, 101 insertions(+), 44 deletions(-) create mode 100644 packages/block-library/src/list-item/transforms.js diff --git a/packages/block-editor/src/components/block-list/block.js b/packages/block-editor/src/components/block-list/block.js index c32d929392d8d8..5b2c3747a68726 100644 --- a/packages/block-editor/src/components/block-list/block.js +++ b/packages/block-editor/src/components/block-list/block.js @@ -19,6 +19,8 @@ import { serializeRawBlock, switchToBlockType, store as blocksStore, + getDefaultBlockName, + isUnmodifiedBlock, } from '@wordpress/blocks'; import { withFilters } from '@wordpress/components'; import { @@ -311,7 +313,6 @@ const applyWithDispatch = withDispatch( ( dispatch, ownProps, registry ) => { __unstableMarkLastChangeAsPersistent, moveBlocksToPosition, removeBlock, - selectBlock, } = dispatch( blockEditorStore ); // Do not add new properties here, use `useDispatch` instead to avoid @@ -348,6 +349,9 @@ const applyWithDispatch = withDispatch( ( dispatch, ownProps, registry ) => { getBlockAttributes, getBlockName, getBlockOrder, + getBlockIndex, + getBlockRootClientId, + canInsertBlockType, } = registry.select( blockEditorStore ); // For `Delete` or forward merge, we should do the exact same thing @@ -453,17 +457,46 @@ const applyWithDispatch = withDispatch( ( dispatch, ownProps, registry ) => { } } - // Attempt to "unwrap" the block contents when there's no - // preceding block to merge with. - const replacement = switchToBlockType( - getBlock( rootClientId ), - '*' - ); - if ( replacement && replacement.length ) { - registry.batch( () => { - replaceBlocks( rootClientId, replacement ); - selectBlock( replacement[ 0 ].clientId, 0 ); - } ); + const targetRootClientId = + getBlockRootClientId( rootClientId ); + + if ( isUnmodifiedBlock( getBlock( clientId ) ) ) { + removeBlock( rootClientId ); + } else { + if ( + canInsertBlockType( + getBlockName( clientId ), + targetRootClientId + ) + ) { + moveBlocksToPosition( + [ clientId ], + rootClientId, + targetRootClientId, + getBlockIndex( rootClientId ) + ); + } else { + const replacement = switchToBlockType( + getBlock( clientId ), + getDefaultBlockName() + ); + + if ( replacement && replacement.length ) { + registry.batch( () => { + insertBlocks( + replacement, + getBlockIndex( rootClientId ), + targetRootClientId, + true + ); + removeBlock( clientId, false ); + } ); + } + } + + if ( ! getBlockOrder( rootClientId ).length ) { + removeBlock( rootClientId, false ); + } } } } diff --git a/packages/block-library/src/list-item/index.js b/packages/block-library/src/list-item/index.js index 61756019baf920..00adc1c2c40266 100644 --- a/packages/block-library/src/list-item/index.js +++ b/packages/block-library/src/list-item/index.js @@ -10,6 +10,7 @@ import initBlock from '../utils/init-block'; import metadata from './block.json'; import edit from './edit'; import save from './save'; +import transforms from './transforms'; const { name } = metadata; @@ -25,6 +26,7 @@ export const settings = { content: attributes.content + attributesToMerge.content, }; }, + transforms, }; export const init = () => initBlock( { name, metadata, settings } ); diff --git a/packages/block-library/src/list-item/transforms.js b/packages/block-library/src/list-item/transforms.js new file mode 100644 index 00000000000000..6e05f8501b5a3b --- /dev/null +++ b/packages/block-library/src/list-item/transforms.js @@ -0,0 +1,17 @@ +/** + * WordPress dependencies + */ +import { createBlock } from '@wordpress/blocks'; + +const transforms = { + to: [ + { + type: 'block', + blocks: [ 'core/paragraph' ], + transform: ( attributes ) => + createBlock( 'core/paragraph', attributes ), + }, + ], +}; + +export default transforms; diff --git a/packages/block-library/src/list/transforms.js b/packages/block-library/src/list/transforms.js index 2f11119768ef89..a6263d7ad639c7 100644 --- a/packages/block-library/src/list/transforms.js +++ b/packages/block-library/src/list/transforms.js @@ -114,17 +114,6 @@ const transforms = { ); }, } ) ), - { - type: 'block', - blocks: [ '*' ], - transform: ( _attributes, childBlocks ) => { - return getListContentFlat( childBlocks ).map( ( content ) => - createBlock( 'core/paragraph', { - content, - } ) - ); - }, - }, ], }; diff --git a/packages/blocks/README.md b/packages/blocks/README.md index f78783f7283392..a03fddf71fe1cc 100644 --- a/packages/blocks/README.md +++ b/packages/blocks/README.md @@ -529,10 +529,9 @@ _Returns_ - `boolean`: Whether the given block is a template part. -### isUnmodifiedDefaultBlock +### isUnmodifiedBlock -Determines whether the block is a default block -and its attributes are equal to the default attributes +Determines whether the block's attributes are equal to the default attributes which means the block is unmodified. _Parameters_ @@ -541,7 +540,20 @@ _Parameters_ _Returns_ -- `boolean`: Whether the block is an unmodified default block +- `boolean`: Whether the block is an unmodified block. + +### isUnmodifiedDefaultBlock + +Determines whether the block is a default block and its attributes are equal +to the default attributes which means the block is unmodified. + +_Parameters_ + +- _block_ `WPBlock`: Block Object + +_Returns_ + +- `boolean`: Whether the block is an unmodified default block. ### isValidBlockContent diff --git a/packages/blocks/src/api/index.js b/packages/blocks/src/api/index.js index afa11f82c6b6ba..2ddeb3a60f0abb 100644 --- a/packages/blocks/src/api/index.js +++ b/packages/blocks/src/api/index.js @@ -137,6 +137,7 @@ export { unregisterBlockVariation, } from './registration'; export { + isUnmodifiedBlock, isUnmodifiedDefaultBlock, normalizeIconObject, isValidIcon, diff --git a/packages/blocks/src/api/utils.js b/packages/blocks/src/api/utils.js index bc68ccd189537d..c43445c6272264 100644 --- a/packages/blocks/src/api/utils.js +++ b/packages/blocks/src/api/utils.js @@ -30,37 +30,40 @@ extend( [ namesPlugin, a11yPlugin ] ); const ICON_COLORS = [ '#191e23', '#f8f9f9' ]; /** - * Determines whether the block is a default block - * and its attributes are equal to the default attributes + * Determines whether the block's attributes are equal to the default attributes * which means the block is unmodified. * * @param {WPBlock} block Block Object * - * @return {boolean} Whether the block is an unmodified default block + * @return {boolean} Whether the block is an unmodified block. */ -export function isUnmodifiedDefaultBlock( block ) { - const defaultBlockName = getDefaultBlockName(); - if ( block.name !== defaultBlockName ) { - return false; - } - +export function isUnmodifiedBlock( block ) { // Cache a created default block if no cache exists or the default block // name changed. - if ( - ! isUnmodifiedDefaultBlock.block || - isUnmodifiedDefaultBlock.block.name !== defaultBlockName - ) { - isUnmodifiedDefaultBlock.block = createBlock( defaultBlockName ); + if ( ! isUnmodifiedBlock[ block.name ] ) { + isUnmodifiedBlock[ block.name ] = createBlock( block.name ); } - const newDefaultBlock = isUnmodifiedDefaultBlock.block; - const blockType = getBlockType( defaultBlockName ); + const newBlock = isUnmodifiedBlock[ block.name ]; + const blockType = getBlockType( block.name ); return Object.keys( blockType?.attributes ?? {} ).every( - ( key ) => newDefaultBlock.attributes[ key ] === block.attributes[ key ] + ( key ) => newBlock.attributes[ key ] === block.attributes[ key ] ); } +/** + * Determines whether the block is a default block and its attributes are equal + * to the default attributes which means the block is unmodified. + * + * @param {WPBlock} block Block Object + * + * @return {boolean} Whether the block is an unmodified default block. + */ +export function isUnmodifiedDefaultBlock( block ) { + return block.name === getDefaultBlockName() && isUnmodifiedBlock( block ); +} + /** * Function that checks if the parameter is a valid icon. * From 46526d808ce7d3d13d10a005adb0732b8beb94dd Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Ella=20van=C2=A0Durpe?= Date: Tue, 18 Oct 2022 21:02:35 +0200 Subject: [PATCH 2/4] Implement forward delete and fix tests --- .../src/components/block-list/block.js | 104 +++++++++--------- .../specs/editor/blocks/quote.test.js | 6 +- .../editor/various/block-switcher.test.js | 4 +- test/e2e/specs/editor/blocks/list.spec.js | 8 +- ...one-block-on-forward-delete-2-chromium.txt | 9 ++ ...one-block-on-forward-delete-1-chromium.txt | 14 ++- ...than-one-block-on-backspace-2-chromium.txt | 9 ++ ...than-one-block-on-backspace-1-chromium.txt | 10 +- .../editor/various/splitting-merging.spec.js | 10 +- 9 files changed, 109 insertions(+), 65 deletions(-) create mode 100644 test/e2e/specs/editor/various/__snapshots__/splitting-and-merging-blocks-test-restore-sele-18edb-roduces-more-than-one-block-on-forward-delete-2-chromium.txt create mode 100644 test/e2e/specs/editor/various/__snapshots__/splitting-and-merging-blocks-test-restore-sele-46dfa-rge-produces-more-than-one-block-on-backspace-2-chromium.txt diff --git a/packages/block-editor/src/components/block-list/block.js b/packages/block-editor/src/components/block-list/block.js index 5b2c3747a68726..517be2941570ed 100644 --- a/packages/block-editor/src/components/block-list/block.js +++ b/packages/block-editor/src/components/block-list/block.js @@ -354,6 +354,57 @@ const applyWithDispatch = withDispatch( ( dispatch, ownProps, registry ) => { canInsertBlockType, } = registry.select( blockEditorStore ); + function moveFirstItemUp( _clientId, changeSelection = true ) { + const targetRootClientId = getBlockRootClientId( _clientId ); + const blockOrder = getBlockOrder( _clientId ); + const [ firstClientId ] = blockOrder; + + if ( + blockOrder.length === 1 && + isUnmodifiedBlock( getBlock( firstClientId ) ) + ) { + removeBlock( _clientId ); + } else { + if ( + canInsertBlockType( + getBlockName( firstClientId ), + targetRootClientId + ) + ) { + moveBlocksToPosition( + [ firstClientId ], + _clientId, + targetRootClientId, + getBlockIndex( _clientId ) + ); + } else { + const replacement = switchToBlockType( + getBlock( firstClientId ), + getDefaultBlockName() + ); + + if ( replacement && replacement.length ) { + registry.batch( () => { + insertBlocks( + replacement, + getBlockIndex( _clientId ), + targetRootClientId, + changeSelection + ); + removeBlock( firstClientId, false ); + } ); + } + } + + if ( + ! getBlockOrder( _clientId ).length && + isUnmodifiedBlock( getBlock( _clientId ) ) + ) { + removeBlock( _clientId, false ); + } + } + } + // For `Delete` or forward merge, we should do the exact same thing // as `Backspace`, but from the other block. if ( forward ) { @@ -404,15 +455,8 @@ const applyWithDispatch = withDispatch( ( dispatch, ownProps, registry ) => { return; } - // Check if it's possibile to "unwrap" the following block - // before trying to merge. - const replacement = switchToBlockType( - getBlock( nextBlockClientId ), - '*' - ); - - if ( replacement && replacement.length ) { - replaceBlocks( nextBlockClientId, replacement ); + if ( getBlockOrder( nextBlockClientId ).length ) { + moveFirstItemUp( nextBlockClientId, false ); } else { mergeBlocks( clientId, nextBlockClientId ); } @@ -457,47 +501,7 @@ const applyWithDispatch = withDispatch( ( dispatch, ownProps, registry ) => { } } - const targetRootClientId = - getBlockRootClientId( rootClientId ); - - if ( isUnmodifiedBlock( getBlock( clientId ) ) ) { - removeBlock( rootClientId ); - } else { - if ( - canInsertBlockType( - getBlockName( clientId ), - targetRootClientId - ) - ) { - moveBlocksToPosition( - [ clientId ], - rootClientId, - targetRootClientId, - getBlockIndex( rootClientId ) - ); - } else { - const replacement = switchToBlockType( - getBlock( clientId ), - getDefaultBlockName() - ); - - if ( replacement && replacement.length ) { - registry.batch( () => { - insertBlocks( - replacement, - getBlockIndex( rootClientId ), - targetRootClientId, - true - ); - removeBlock( clientId, false ); - } ); - } - } - - if ( ! getBlockOrder( rootClientId ).length ) { - removeBlock( rootClientId, false ); - } - } + moveFirstItemUp( rootClientId ); } } }, diff --git a/packages/e2e-tests/specs/editor/blocks/quote.test.js b/packages/e2e-tests/specs/editor/blocks/quote.test.js index bb61fc7a5ee0a9..9b0a4bac546dd3 100644 --- a/packages/e2e-tests/specs/editor/blocks/quote.test.js +++ b/packages/e2e-tests/specs/editor/blocks/quote.test.js @@ -191,9 +191,9 @@ describe( 'Quote', () => {

1

- -

2

- " + +
2
+ " ` ); } ); } ); diff --git a/packages/e2e-tests/specs/editor/various/block-switcher.test.js b/packages/e2e-tests/specs/editor/various/block-switcher.test.js index eea665e688888e..6e5c192a758adc 100644 --- a/packages/e2e-tests/specs/editor/various/block-switcher.test.js +++ b/packages/e2e-tests/specs/editor/various/block-switcher.test.js @@ -82,9 +82,9 @@ describe( 'Block Switcher', () => { await pressKeyWithModifier( 'alt', 'F10' ); // Verify the block switcher exists. - expect( await hasBlockSwitcher() ).toBeTruthy(); + expect( await hasBlockSwitcher() ).toBeFalsy(); // Verify the correct block transforms appear. - expect( await getAvailableBlockTransforms() ).toHaveLength( 1 ); + expect( await getAvailableBlockTransforms() ).toHaveLength( 0 ); } ); describe( 'Conditional tranformation options', () => { diff --git a/test/e2e/specs/editor/blocks/list.spec.js b/test/e2e/specs/editor/blocks/list.spec.js index daa23241a4e8e9..0a1159f6d5d49d 100644 --- a/test/e2e/specs/editor/blocks/list.spec.js +++ b/test/e2e/specs/editor/blocks/list.spec.js @@ -1090,9 +1090,11 @@ test.describe( 'List', () => {

- -

2

-` + + +` ); } ); diff --git a/test/e2e/specs/editor/various/__snapshots__/splitting-and-merging-blocks-test-restore-sele-18edb-roduces-more-than-one-block-on-forward-delete-2-chromium.txt b/test/e2e/specs/editor/various/__snapshots__/splitting-and-merging-blocks-test-restore-sele-18edb-roduces-more-than-one-block-on-forward-delete-2-chromium.txt new file mode 100644 index 00000000000000..463d4ecae0e093 --- /dev/null +++ b/test/e2e/specs/editor/various/__snapshots__/splitting-and-merging-blocks-test-restore-sele-18edb-roduces-more-than-one-block-on-forward-delete-2-chromium.txt @@ -0,0 +1,9 @@ + +

hi-item 1

+ + + + + \ No newline at end of file diff --git a/test/e2e/specs/editor/various/__snapshots__/splitting-and-merging-blocks-test-restore-sele-2a1ee-roduces-more-than-one-block-on-forward-delete-1-chromium.txt b/test/e2e/specs/editor/various/__snapshots__/splitting-and-merging-blocks-test-restore-sele-2a1ee-roduces-more-than-one-block-on-forward-delete-1-chromium.txt index cb5b5fcf148b3c..04346aeb9e959c 100644 --- a/test/e2e/specs/editor/various/__snapshots__/splitting-and-merging-blocks-test-restore-sele-2a1ee-roduces-more-than-one-block-on-forward-delete-1-chromium.txt +++ b/test/e2e/specs/editor/various/__snapshots__/splitting-and-merging-blocks-test-restore-sele-2a1ee-roduces-more-than-one-block-on-forward-delete-1-chromium.txt @@ -1,3 +1,13 @@ -

hi-

- \ No newline at end of file +

hi

+ + + +

item 1

+ + + + + \ No newline at end of file diff --git a/test/e2e/specs/editor/various/__snapshots__/splitting-and-merging-blocks-test-restore-sele-46dfa-rge-produces-more-than-one-block-on-backspace-2-chromium.txt b/test/e2e/specs/editor/various/__snapshots__/splitting-and-merging-blocks-test-restore-sele-46dfa-rge-produces-more-than-one-block-on-backspace-2-chromium.txt new file mode 100644 index 00000000000000..463d4ecae0e093 --- /dev/null +++ b/test/e2e/specs/editor/various/__snapshots__/splitting-and-merging-blocks-test-restore-sele-46dfa-rge-produces-more-than-one-block-on-backspace-2-chromium.txt @@ -0,0 +1,9 @@ + +

hi-item 1

+ + + + + \ No newline at end of file diff --git a/test/e2e/specs/editor/various/__snapshots__/splitting-and-merging-blocks-test-restore-sele-92273-rge-produces-more-than-one-block-on-backspace-1-chromium.txt b/test/e2e/specs/editor/various/__snapshots__/splitting-and-merging-blocks-test-restore-sele-92273-rge-produces-more-than-one-block-on-backspace-1-chromium.txt index 33adf8bef295a9..04346aeb9e959c 100644 --- a/test/e2e/specs/editor/various/__snapshots__/splitting-and-merging-blocks-test-restore-sele-92273-rge-produces-more-than-one-block-on-backspace-1-chromium.txt +++ b/test/e2e/specs/editor/various/__snapshots__/splitting-and-merging-blocks-test-restore-sele-92273-rge-produces-more-than-one-block-on-backspace-1-chromium.txt @@ -3,9 +3,11 @@ -

-item 1

+

item 1

- -

item 2

- \ No newline at end of file + + + \ No newline at end of file diff --git a/test/e2e/specs/editor/various/splitting-merging.spec.js b/test/e2e/specs/editor/various/splitting-merging.spec.js index 45f4d9347edcc2..510c1cb46cf3b3 100644 --- a/test/e2e/specs/editor/various/splitting-merging.spec.js +++ b/test/e2e/specs/editor/various/splitting-merging.spec.js @@ -377,7 +377,11 @@ test.describe( 'splitting and merging blocks', () => { await page.keyboard.type( 'item 1' ); await page.keyboard.press( 'Enter' ); await page.keyboard.type( 'item 2' ); - await pageUtils.pressKeyTimes( 'ArrowUp', 2 ); + await pageUtils.pressKeyTimes( 'ArrowUp', 3 ); + await page.keyboard.press( 'Delete' ); + + expect( await editor.getEditedPostContent() ).toMatchSnapshot(); + await page.keyboard.press( 'Delete' ); // Carret should be in the first block and at the proper position. await page.keyboard.type( '-' ); @@ -395,6 +399,10 @@ test.describe( 'splitting and merging blocks', () => { await page.keyboard.type( 'item 2' ); await page.keyboard.press( 'ArrowUp' ); await pageUtils.pressKeyTimes( 'ArrowLeft', 6 ); + await page.keyboard.press( 'Backspace' ); + + expect( await editor.getEditedPostContent() ).toMatchSnapshot(); + await page.keyboard.press( 'Backspace' ); // Carret should be in the first block and at the proper position. await page.keyboard.type( '-' ); From 53c12099220c1c779588232d3fa83d435e84b4e9 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Ella=20van=C2=A0Durpe?= Date: Fri, 25 Nov 2022 14:11:07 +0100 Subject: [PATCH 3/4] Add comment --- packages/block-editor/src/components/block-list/block.js | 9 +++++++++ 1 file changed, 9 insertions(+) diff --git a/packages/block-editor/src/components/block-list/block.js b/packages/block-editor/src/components/block-list/block.js index 517be2941570ed..70456ac213fc3b 100644 --- a/packages/block-editor/src/components/block-list/block.js +++ b/packages/block-editor/src/components/block-list/block.js @@ -354,6 +354,15 @@ const applyWithDispatch = withDispatch( ( dispatch, ownProps, registry ) => { canInsertBlockType, } = registry.select( blockEditorStore ); + /** + * Moves the block with clientId up one level. If the block type + * cannot be inserted at the new location, it will be attempted to + * convert to the default block type. + * + * @param {string} _clientId The block to move. + * @param {boolean} changeSelection Whether to change the selection + * to the moved block. + */ function moveFirstItemUp( _clientId, changeSelection = true ) { const targetRootClientId = getBlockRootClientId( _clientId ); const blockOrder = getBlockOrder( _clientId ); From e1b346de12a75f0d0063f9f4d7c610bdbfd47561 Mon Sep 17 00:00:00 2001 From: Gerardo Pacheco Date: Wed, 30 Nov 2022 16:27:45 +0100 Subject: [PATCH 4/4] [Mobile] List/quote: Unwrap inner block when pressing Backspace at start (#46115) --- .../src/components/block-list/block.native.js | 90 ++++++++++++++----- .../src/list/test/edit.native.js | 14 +-- .../utils/transformation-categories.native.js | 1 + 3 files changed, 78 insertions(+), 27 deletions(-) diff --git a/packages/block-editor/src/components/block-list/block.native.js b/packages/block-editor/src/components/block-list/block.native.js index 91817675d6eed1..061ff216a1383f 100644 --- a/packages/block-editor/src/components/block-list/block.native.js +++ b/packages/block-editor/src/components/block-list/block.native.js @@ -20,6 +20,8 @@ import { getBlockType, __experimentalGetAccessibleBlockLabel as getAccessibleBlockLabel, switchToBlockType, + getDefaultBlockName, + isUnmodifiedBlock, } from '@wordpress/blocks'; import { useSetting } from '@wordpress/block-editor'; @@ -436,8 +438,72 @@ export default compose( [ getBlockAttributes, getBlockName, getBlockOrder, + getBlockIndex, + getBlockRootClientId, + canInsertBlockType, } = registry.select( blockEditorStore ); + /** + * Moves the block with clientId up one level. If the block type + * cannot be inserted at the new location, it will be attempted to + * convert to the default block type. + * + * @param {string} _clientId The block to move. + * @param {boolean} changeSelection Whether to change the selection + * to the moved block. + */ + function moveFirstItemUp( _clientId, changeSelection = true ) { + const targetRootClientId = + getBlockRootClientId( _clientId ); + const blockOrder = getBlockOrder( _clientId ); + const [ firstClientId ] = blockOrder; + + if ( + blockOrder.length === 1 && + isUnmodifiedBlock( getBlock( firstClientId ) ) + ) { + removeBlock( _clientId ); + } else { + if ( + canInsertBlockType( + getBlockName( firstClientId ), + targetRootClientId + ) + ) { + moveBlocksToPosition( + [ firstClientId ], + _clientId, + targetRootClientId, + getBlockIndex( _clientId ) + ); + } else { + const replacement = switchToBlockType( + getBlock( firstClientId ), + getDefaultBlockName() + ); + + if ( replacement && replacement.length ) { + registry.batch( () => { + insertBlocks( + replacement, + getBlockIndex( _clientId ), + targetRootClientId, + changeSelection + ); + removeBlock( firstClientId, false ); + } ); + } + } + + if ( + ! getBlockOrder( _clientId ).length && + isUnmodifiedBlock( getBlock( _clientId ) ) + ) { + removeBlock( _clientId, false ); + } + } + } + // For `Delete` or forward merge, we should do the exact same thing // as `Backspace`, but from the other block. if ( forward ) { @@ -488,15 +554,8 @@ export default compose( [ return; } - // Check if it's possibile to "unwrap" the following block - // before trying to merge. - const replacement = switchToBlockType( - getBlock( nextBlockClientId ), - '*' - ); - - if ( replacement && replacement.length ) { - replaceBlocks( nextBlockClientId, replacement ); + if ( getBlockOrder( nextBlockClientId ).length ) { + moveFirstItemUp( nextBlockClientId, false ); } else { mergeBlocks( clientId, nextBlockClientId ); } @@ -541,18 +600,7 @@ export default compose( [ } } - // Attempt to "unwrap" the block contents when there's no - // preceding block to merge with. - const replacement = switchToBlockType( - getBlock( rootClientId ), - '*' - ); - if ( replacement && replacement.length ) { - registry.batch( () => { - replaceBlocks( rootClientId, replacement ); - selectBlock( replacement[ 0 ].clientId, 0 ); - } ); - } + moveFirstItemUp( rootClientId ); } } }, diff --git a/packages/block-library/src/list/test/edit.native.js b/packages/block-library/src/list/test/edit.native.js index 9defa338782dbe..e661fbe3a626da 100644 --- a/packages/block-library/src/list/test/edit.native.js +++ b/packages/block-library/src/list/test/edit.native.js @@ -361,7 +361,7 @@ describe( 'List block', () => { ` ); } ); - it( 'unwraps list items when attempting to merge with non-list block', async () => { + it( 'unwraps first item when attempting to merge with non-list block', async () => { const initialHtml = `

A quick brown fox.

@@ -400,14 +400,16 @@ describe( 'List block', () => { "

A quick brown fox.

- +

One

- - -

Two

- " + + +
    +
  • Two
  • +
+ " ` ); } ); } ); diff --git a/packages/block-library/src/utils/transformation-categories.native.js b/packages/block-library/src/utils/transformation-categories.native.js index 3ddf60d2a4c227..e001f9b67c785d 100644 --- a/packages/block-library/src/utils/transformation-categories.native.js +++ b/packages/block-library/src/utils/transformation-categories.native.js @@ -3,6 +3,7 @@ const transformationCategories = { 'core/paragraph', 'core/heading', 'core/list', + 'core/list-item', 'core/quote', 'core/pullquote', 'core/preformatted',