-
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
BlockList: Ensure element styles (and svg) are always appended at the end of the document #53859
BlockList: Ensure element styles (and svg) are always appended at the end of the document #53859
Conversation
Size Change: +7 B (0%) Total Size: 1.51 MB
ℹ️ View Unchanged
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This looks good to me but I'd like for @ellatrix to confirm here.
The other thing here is that, there's no a small chance that this extra div impacts CSS that is injected by the theme, things like last-child selectors... Maybe the percentage of themes this impacts is small?
Thanks for taking a look @youknowriad!
True — I think the likelihood is probably fairly minimal, and on balance I think the behaviour with this PR is probably preferable and keeps the injected styles and svgs in a consistent place at least. My main thinking here is that this extra div is now a sibling of
Agreed, it'd be good to get another pair of eyes on this if we can. Since this PR is a change that resolves a fairly subtle issue, and in turn could cause other fairly subtle issues, to be on the safe side I'll just give a wider ping to @WordPress/gutenberg-core in case there's anyone who has further thoughts about the markup here 🙂 |
0e81a9c
to
430b991
Compare
Just gave this a fresh rebase to fix a conflict after #53875 landed, so this should be good to review again now. |
There's also the #52888, which proposes a new system for outputting styles and SVGs. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Approving this cause overall it's seems like an improvement for the current way we do things. We can look at the further improvements separately.
Sure this is fine, but outputting extra divs. You all know how much I hate extra divs 😅 |
Thanks for the reviews and feedback, folks! I'll merge this in now since it fixes the immediate issue for the moment.
Agreed, let's take a closer look at #52888 for a better long-term solution 👍 |
What?
Fixes #36053
Update the
BlockList
'sRoot
component to always output element styles (e.g.style
andsvg
elements for layout, element, and duotone block supports) to the end of the document. To do so, add an extradiv
to the end ofRoot
to ensure that any changes to theuseInnerBlocksProps
element occur prior to the injectedstyle
andsvg
tags.Why?
The reason this change is needed is fairly subtle. React's
createPortal
appends nodes as the list child of an element. In an already loaded post or page, the inner blocks for the block list will all be rendered at the top, and the injectedstyle
tags will appear at the bottom of the DOM.Something interesting happens when we go to make changes, though. When hovering over the end of the document and going to insert blocks, the block appender will be rendered after the injects
style
tags in the DOM. Then, when we go to insert blocks, inserted blocks will also be rendered after the injected styles. Whereas, what we expect to happen is that the styles would still appear at the end.The reason why, I think, is because after the original injection, when React rerenders elements into the portal, it doesn't attempt to remount into the portal, rather it makes updates in place since the elements have already been rendered into the DOM. This means that subsequent additions are added to the end, but we wind up in an unexpected situation where
style
tags wind up "randomly" sitting between other blocks once we go to make changes to blocks within a document.To avoid this collision between an element where lots of mutation is happening due to addition, removal, or moving of blocks, and the injection of styles and svg tags, a solution is to create a separate
div
as the entrypoint for portal-based injection of style and svg tags, and have this always sit at the bottom of the document.For further explanation as to why the style and svg tags sitting between blocks is an issue, see the discussion in: #36053 — the TL;DR is that the presence of these tags can break CSS selectors as such sibling, first / last child, etc.
How?
div
to the bottom of theRoot
.setElement
ref state function to this node.Testing Instructions
style
tags in adiv
at the end of the document (beneath the block content).style
tags that contain thewp-container-123
etc rules.hidden
attribute to the containerdiv
, because Firefox requires the container to be visible in order for thesvg
elements to be accessible for rendering Duotone). As far as I can tell, the current state of this PR doesn't cause any styling issues, but it would be good to confirm via manual testing.Here is some test markup to begin with (you'll need to add your own Image blocks with Duotone for testing):
Testing Instructions for Keyboard
Screenshots or screencast
The below screenshots show the in editor markup for a post just after a paragraph block has been inserted at the end of the document.
Note that in the "before" screenshot, there is a Figure element for the image block, then a series of
style
andsvg
tags, then the paragraph block, then the block appender.In the "after" screenshot, in the top area there is the Figure element for thee image block, then the paragraph block, then the block appender. And below all of them is a separate
div
to contain all thestyle
andsvg
tags.