Skip to content
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

Expand main content area to viewport when zoomed out #59512

Merged
merged 1 commit into from
Mar 15, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
16 changes: 16 additions & 0 deletions packages/block-editor/src/components/block-list/content.scss
Original file line number Diff line number Diff line change
Expand Up @@ -360,6 +360,22 @@ _::-webkit-full-page-media, _:future, :root .has-multi-selection .block-editor-b
z-index: z-index("{core/image aligned left or right} .wp-block");
}

body.is-zoomed-out {
display: flex;
flex-direction: column;

> .is-root-container {
flex: 1;
display: flex;
flex-direction: column;
height: 100%;

> main {
flex: 1;
}
}
}
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@jasmussen @MaggieCabrera Sorry to ping you, but maybe with your CSS wizardry skills you can think of ways to make this work for all themes. Otherwise I think we'll have to rely on themes to add it. Or maybe this is fine for block-based themes if they don't use a custom stylesheet?

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Can we make this css conditional to having no patterns inserted instead? We only care about this when the page is empty, otherwise if we insert a pattern that doesn't fill the whole viewport height we are introducing fake space that is not really there in the frontend.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Sorry I'm catching up after a bit. What does this property do?

I'd agree we want to ideally avoid a theme needing to add anything at all in order for the zoom prop to work.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

How does it break themes? Doesn't this CSS be just in editor? Also what makes it work in zoom out mode only?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think there's some misunderstandings:

  • No, this CSS is not required for zoom out mode, it's just nice that the footer is pushed down when the viewport is made higher.
  • Since it's not a requirement for zoom out mode, it something that we let theme implement. I think this is a nice thing on the front-end as well (pushing the footer down when there's no or little content).
  • I don't see this as fake space at all, I just see this ensuring the footer is at the bottom of the page. Again, if it's something that the theme does it would be on the front-end too.
  • I didn't say it breaks themes, I just said it may clash with theme CSS, but actually this may not be the case at all for block based themes 🤔

Or maybe we can rely on block-based themes never styling is-root-container, in which case this CSS may be safe to use as it won't clash with anything. It still relies on header, main and footer being top-level blocks though.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@jasmussen when zooming out the content is scaled. We would want that the scaling of an empty page to not cause a small zoomed out patch containing header a small nothing and a footer but instead when zooming out to enlarge vertically the shape to obtain header a large nothing footer. The purpose of this trickery is to make it obvious that the big nothing is where the assembly of patterns will happen (assuming an empty page is zoomed out for building it).

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Valid enough, I think there's some nuance to explore there in terms of what that means for the blue pattern insertion plus buttons as well, and where they show up. I.e. to your point, we certainly don't want those to stack right next to each other. But we also want to avoid an accordion behavior where the document is always at least full-viewport-height when empty, and then it collapses as soon as you add a single section pattern. So I'd be tempted to apply a min-height instead of flex magic.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@jasmussen I think this does exactly what you say: #59512 (review)

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Ideally the shape of the page doesn't change when you zoom out. If the page is short, it should be even shorter when zoomed out.

The whole point of this PR is to not have that. Maybe @richtabor can explain this better :)

Copy link
Member

@richtabor richtabor Mar 7, 2024

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Just to clarify, this simply ensures the footer is at the bottom of an empty page, or rather when there is not enough content to push it there—and only when zoom-out mode is engaged. It helps align the interface with expectations of where content (i.e. patterns) will be inserted.

This is not a "fit" view, but rather an initial state when there's not a full page of content.

Before After
CleanShot 2024-03-07 at 14 56 27 CleanShot 2024-03-07 at 14 55 51


.wp-site-blocks > [data-align="left"] {
float: left;
margin-right: 2em;
Expand Down
36 changes: 35 additions & 1 deletion packages/block-editor/src/components/iframe/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -207,13 +207,31 @@ function Iframe( {
};
}, [] );

const windowResizeRef = useRefEffect( ( node ) => {
const onResize = () => {
setIframeWindowInnerHeight(
node.ownerDocument.defaultView.innerHeight
);
};
node.ownerDocument.defaultView.addEventListener( 'resize', onResize );
return () => {
node.ownerDocument.defaultView.removeEventListener(
'resize',
onResize
);
};
}, [] );

const [ iframeWindowInnerHeight, setIframeWindowInnerHeight ] = useState();

const disabledRef = useDisabled( { isDisabled: ! readonly } );
const bodyRef = useMergeRefs( [
useBubbleEvents( iframeDocument ),
contentRef,
clearerRef,
writingFlowRef,
disabledRef,
windowResizeRef,
] );

// Correct doctype is required to enable rendering in standards
Expand Down Expand Up @@ -268,18 +286,34 @@ function Iframe( {
// Hack to get proper margins when scaling the iframe document.
const bottomFrameSize = frameSize - contentHeight * ( 1 - _scale );

iframeDocument.body.classList.add( 'is-zoomed-out' );

iframeDocument.documentElement.style.transform = `scale( ${ _scale } )`;
iframeDocument.documentElement.style.marginTop = `${ frameSize }px`;
// TODO: `marginBottom` doesn't work in Firefox. We need another way to do this.
iframeDocument.documentElement.style.marginBottom = `${ bottomFrameSize }px`;
if ( iframeWindowInnerHeight > contentHeight * _scale ) {
iframeDocument.body.style.minHeight = `${ Math.floor(
( iframeWindowInnerHeight - 2 * frameSize ) / _scale
) }px`;
}

return () => {
iframeDocument.body.classList.remove( 'is-zoomed-out' );
iframeDocument.documentElement.style.transform = '';
iframeDocument.documentElement.style.marginTop = '';
iframeDocument.documentElement.style.marginBottom = '';
iframeDocument.body.style.minHeight = '';
};
}
}, [ scale, frameSize, contentHeight, contentWidth, iframeDocument ] );
}, [
scale,
frameSize,
iframeDocument,
contentHeight,
iframeWindowInnerHeight,
contentWidth,
] );

// Make sure to not render the before and after focusable div elements in view
// mode. They're only needed to capture focus in edit mode.
Expand Down
22 changes: 13 additions & 9 deletions packages/edit-site/src/components/block-editor/editor-canvas.js
Original file line number Diff line number Diff line change
Expand Up @@ -103,6 +103,17 @@ function EditorCanvas( { enableResizing, settings, children, ...props } ) {
[ settings.styles, enableResizing, canvasMode ]
);

const frameSize = isZoomOutMode ? 20 : undefined;

const scale = isZoomOutMode
? ( contentWidth ) =>
computeIFrameScale(
{ width: 1000, scale: 0.45 },
{ width: 400, scale: 0.9 },
contentWidth
)
: undefined;

return (
<EditorCanvasRoot
className={ classnames( 'edit-site-editor-canvas__block-list', {
Expand All @@ -111,15 +122,8 @@ function EditorCanvas( { enableResizing, settings, children, ...props } ) {
renderAppender={ showBlockAppender }
styles={ styles }
iframeProps={ {
scale: isZoomOutMode
? ( contentWidth ) =>
computeIFrameScale(
{ width: 1000, scale: 0.45 },
{ width: 400, scale: 0.9 },
contentWidth
)
: undefined,
frameSize: isZoomOutMode ? 100 : undefined,
scale,
frameSize,
className: classnames(
'edit-site-visual-editor__editor-canvas',
{
Expand Down
Loading