-
Notifications
You must be signed in to change notification settings - Fork 4.3k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
onAddBlock and onRemoveBlock event #41679
Comments
Agreed. Few months ago, i was working on one project where i had to detect the New Added/Removed blocks. Had used Block client id and subscribe method for continuous execution to find removed block. which was affected performance of editor. even though we couldn't find solution for new added block. This two methods will help a lot to handle Gutenberg actions for advance operations. |
I'm not opposing the suggested feature though I'd like to mention it seems the Example filter to fire callbacks for block addition and removal.(( {
compose: { createHigherOrderComponent },
element: { createElement: el, Fragment, useEffect, useRef },
hooks: { addFilter },
} ) => {
addFilter(
'editor.BlockEdit',
'no41679/with-presence',
createHigherOrderComponent( ( BlockEdit ) => ( props ) => {
const ref = useRef();
useEffect( () => {
const previewContainer = ref.current.closest(
'.block-editor-block-preview__content-iframe'
);
// Bails when the block is inside a preview container.
if ( previewContainer ) return;
const { name, attributes, clientId } = props;
console.log( 'block added' );
// onBlockAdded( { name, attributes, clientId } );
return () => {
console.log( 'block removed' );
// onBlockRemoved( { name, attributes, clientId } );
}
}, [] );
return el(
Fragment,
null,
el( BlockEdit, props ),
el( 'meta', { itemProp: 'present', ref } ),
);
}, 'withPresence' )
);
})( wp ); That example can be pasted into the console to test. It also seems like the example use case might be quite related to #29693. There's no solution there yet but it could be worth subscribing to in case it leads to some features that might support your use case. |
@stokesman Thanks, your codes are helping me a lot for my current project. Yet, I believe it would be great to have some simple callback to use.
|
Right. The blocks parsed from a saved post are added to the editor each page load. I'm not sure what would be the best approach to filter those out. |
What about adding a |
When Filter to fire added/removed callbacks only for blocks just inserted (and their innerBlocks)(( {
blockEditor: { store: blockEditorStore },
compose: { createHigherOrderComponent },
element: { createElement: el, useEffect },
data: { useSelect },
hooks: { addFilter },
} ) => {
const onBlockAdded = ( block ) => {
console.log( 'block added', block );
}
const onBlockRemoved = ( block ) => {
console.log( 'block removed', block );
}
// Tracks added blocks. Really only needed if the `onBlockRemoved` callback
// should only fire for blocks that were just inserted.
const addedBlocks = new WeakSet;
const addWithInnerBlocks = ( block ) => {
onBlockAdded( block );
addedBlocks.add( block );
for ( const innerBlock of block.innerBlocks )
addWithInnerBlocks( innerBlock );
}
addFilter(
'editor.BlockEdit',
'no41679/with-new-presence',
createHigherOrderComponent( ( BlockEdit ) => ( props ) => {
const { getBlock, wasBlockJustInserted } = useSelect( blockEditorStore );
useEffect( () => {
const { clientId } = props;
const self = getBlock( clientId );
if ( wasBlockJustInserted( clientId ) ) addWithInnerBlocks( self );
return () => {
if ( addedBlocks.has( self ) ) onBlockRemoved( self );
}
}, [] );
return el( BlockEdit, props );
}, 'withNewPresence' )
);
})( wp ); One neat thing about filtering to only blocks that have just been inserted is it also eliminates blocks inside preview containers which simplifies things in nice way (as compared to the original example I posted). |
Amazing solution! Helped out alot. Might be a good idea to add something like const blocks = getBlocks();
// Makes sure blocks in page are already counted
blocks.forEach((block: any) => {
addWithInnerBlocks(block);
}); to make sure blocks already present in the page are included |
What problem does this address?
When we add a block it should hit a
onAddBlock
event by using which we can do something globally like save something unique for this block to database. We should also useonRemoveBlock
to reverse that save when this block is deleted.Example use case
Suppose, like creating a new email address, I want one of my inspector control field to hold a unique name for every instance of my block. It will be a auto generated field (ex. My Block 1) but user can also choose their own. And during savings it will get the previous instance values from database to check if this new one is unique. If not it will suggest user to change the name a bit to make it unique.
Also by deleting this instance of block, we should have a remove functionality to delete associated field value from the database
What is your proposed solution?
TextControl
component to produce unique value by developer defined pattern. Ex. My Form 1, My Form 2onAddBlock
andonRemoveBlock
to enable developers to do some callback functionality. By this solution, they can do almost anything during those event, not only generate some unique field.The text was updated successfully, but these errors were encountered: