diff --git a/projects/js-packages/base-styles/admin-page-layout.scss b/projects/js-packages/base-styles/admin-page-layout.scss index 2213d16093b4..15b9a8769b46 100644 --- a/projects/js-packages/base-styles/admin-page-layout.scss +++ b/projects/js-packages/base-styles/admin-page-layout.scss @@ -12,6 +12,12 @@ // body.jetpack_page_my-jetpack { @include jetpack-admin-page-layout; } // } +// To style the scrollable middle from a consumer, include +// `jetpack-admin-page-scrollable-middle` inside the same scope instead of +// copying its selectors: + +// @include jetpack-admin-page-scrollable-middle { scrollbar-gutter: stable; } + // Selector hooks this mixin relies on (all stable, not CSS-Modules hashed): // wp-admin shell: #wpcontent, #wpbody-content, #wpfooter @@ -25,6 +31,9 @@ // admin-ui's header:
element rendered by admin-ui's // inside `.jp-admin-page__page` (no class hooks — // we anchor structurally to the HTML5 element) +// content: .jp-admin-page__content (content wrapper of an +// without a +// title or breadcrumbs) // : .jetpack-footer // Tabs wrapper convention: .jp-admin-page-tabs (consumer-applied div that // wraps `@wordpress/ui` @@ -66,6 +75,18 @@ $jp-admin-bar-height-mobile: 46px; $jp-breakpoint-auto-fold: 960px; $jp-breakpoint-mobile: 782px; +// The scrollable middle of an : everything between the header and +// the footer. With a title, admin-ui's renders children as its own +// direct children ( passes no `hasPadding`, so no content wrapper). +// Without a title, wraps them in `.jp-admin-page__content`. +@mixin jetpack-admin-page-scrollable-middle { + + .jp-admin-page__page > :not(:first-child):not(.jetpack-footer), + .jp-admin-page > .jp-admin-page__content { + @content; + } +} + @mixin jetpack-admin-page-layout { // ── wp-admin chrome resets ──────────────────────────────────────── #wpcontent { @@ -247,17 +268,13 @@ $jp-breakpoint-mobile: 782px; padding-bottom: 0; } - // The scrollable middle. does not pass `hasPadding` to - // admin-ui's , so admin-ui's content wrapper is not rendered — - // children drop in as direct descendants of the page node. Target - // anything that isn't the header or the footer. - + // ── The scrollable middle ───────────────────────────────────────── // `overflow: auto` (both axes) lets any child wider than the column // (dashboard grids with fixed column widths, wide tables, `100vw` // descendants) scroll horizontally inside the middle instead of // dragging the whole window into a horizontal scrollbar. - // `` (title-branch) wraps children in + // `` wraps children in // `{children}` // — that outer Container is `display: grid` and the single Col is a // grid cell. Without intervention, the chain breaks here: any inner @@ -270,7 +287,7 @@ $jp-breakpoint-mobile: 782px; // fill their bounded slot. Form-style pages keep working: their // children stay content-sized (default `flex: 0 1 auto`) and any // overflow still falls back to Container's `overflow: auto`. - .jp-admin-page__page > :not(:first-child):not(.jetpack-footer) { + @include jetpack-admin-page-scrollable-middle { flex: 1 1 auto; min-height: 0; min-width: 0; @@ -301,7 +318,7 @@ $jp-breakpoint-mobile: 782px; // width of the panel area, so the hairline spans the column. // `position: sticky` pins the strip to the top of the scrollable middle - // (`.jp-admin-page__page > :not(header):not(.jetpack-footer)`), + // (see `jetpack-admin-page-scrollable-middle`), // which is the local opt-in equivalent of admin-ui's native sticky // header — disabled globally by `` per JETPACK-1386. Pinning // the tabs strip here keeps cross-section navigation accessible while diff --git a/projects/js-packages/base-styles/changelog/add-admin-page-scrollable-middle-mixin b/projects/js-packages/base-styles/changelog/add-admin-page-scrollable-middle-mixin new file mode 100644 index 000000000000..a67b58ed11d1 --- /dev/null +++ b/projects/js-packages/base-styles/changelog/add-admin-page-scrollable-middle-mixin @@ -0,0 +1,4 @@ +Significance: minor +Type: added + +Admin page layout: add a `jetpack-admin-page-scrollable-middle` mixin so consumers can style the scroll surface without copying its selectors. diff --git a/projects/js-packages/base-styles/changelog/fix-admin-page-header-less-scroll-surface b/projects/js-packages/base-styles/changelog/fix-admin-page-header-less-scroll-surface new file mode 100644 index 000000000000..73577259bceb --- /dev/null +++ b/projects/js-packages/base-styles/changelog/fix-admin-page-header-less-scroll-surface @@ -0,0 +1,4 @@ +Significance: patch +Type: fixed + +Admin page layout: make the content of AdminPage screens without a title or breadcrumbs scroll instead of being clipped by the fixed content column. diff --git a/projects/js-packages/components/changelog/fix-admin-page-header-less-scroll-surface b/projects/js-packages/components/changelog/fix-admin-page-header-less-scroll-surface new file mode 100644 index 000000000000..883f0bc92864 --- /dev/null +++ b/projects/js-packages/components/changelog/fix-admin-page-header-less-scroll-surface @@ -0,0 +1,4 @@ +Significance: patch +Type: fixed + +AdminPage: add a stable `jp-admin-page__content` class to the content wrapper of pages without a title or breadcrumbs so the shared admin page layout can make it scrollable. diff --git a/projects/js-packages/components/components/admin-page/index.tsx b/projects/js-packages/components/components/admin-page/index.tsx index 4fa00a0342ee..c8b935f06f20 100644 --- a/projects/js-packages/components/components/admin-page/index.tsx +++ b/projects/js-packages/components/components/admin-page/index.tsx @@ -120,7 +120,8 @@ const AdminPage: FC< AdminPageProps > = ( { ) } - + { /* `jp-admin-page__content` is a stable hook for `jetpack-admin-page-layout`. Do not rename. */ } + { children } { showFooter && } diff --git a/projects/js-packages/components/components/admin-page/test/component.tsx b/projects/js-packages/components/components/admin-page/test/component.tsx new file mode 100644 index 000000000000..221d86bd7a74 --- /dev/null +++ b/projects/js-packages/components/components/admin-page/test/component.tsx @@ -0,0 +1,42 @@ +/* eslint-disable testing-library/no-node-access -- these tests check class hooks + that the `jetpack-admin-page-layout` mixin selects on. */ +import { render, screen } from '@testing-library/react'; +import AdminPage from '../index.tsx'; + +describe( 'AdminPage', () => { + it( 'wraps children in the scrollable content hook when there is no header', () => { + render( + +

Page body

+
+ ); + + const content = screen.getByText( 'Page body' ).closest( '.jp-admin-page__content' ); + expect( content ).not.toBeNull(); + expect( content.parentElement ).toHaveClass( 'jp-admin-page' ); + } ); + + it( 'wraps children in the scrollable content hook with the legacy header', () => { + render( + +

Page body

+
+ ); + + const content = screen.getByText( 'Page body' ).closest( '.jp-admin-page__content' ); + expect( content ).not.toBeNull(); + expect( content.parentElement ).toHaveClass( 'jp-admin-page' ); + } ); + + it( 'renders the admin-ui page hook instead when a title is given', () => { + render( + +

Page body

+
+ ); + + const body = screen.getByText( 'Page body' ); + expect( body.closest( '.jp-admin-page__page' ) ).not.toBeNull(); + expect( body.closest( '.jp-admin-page__content' ) ).toBeNull(); + } ); +} ); diff --git a/projects/packages/backup/changelog/fix-admin-page-header-less-scroll-surface b/projects/packages/backup/changelog/fix-admin-page-header-less-scroll-surface new file mode 100644 index 000000000000..75d6d3b0a21e --- /dev/null +++ b/projects/packages/backup/changelog/fix-admin-page-header-less-scroll-surface @@ -0,0 +1,4 @@ +Significance: patch +Type: fixed + +Secondary admin connection screen: restore scrolling so the connect button is reachable on short viewports. diff --git a/projects/packages/my-jetpack/_inc/style.module.scss b/projects/packages/my-jetpack/_inc/style.module.scss index 26b2d3bc3bcc..eafb771898ac 100644 --- a/projects/packages/my-jetpack/_inc/style.module.scss +++ b/projects/packages/my-jetpack/_inc/style.module.scss @@ -32,9 +32,8 @@ // between search results and category browse — which changes the content // height, and thus whether the scrollbar is present — doesn't shift the // layout sideways. Most noticeable on Firefox / platforms with classic - // (space-consuming) scrollbars; a no-op where unsupported. The selector - // mirrors the "scrollable middle" defined by jetpack-admin-page-layout. - .jp-admin-page__page > :not(:first-child):not(.jetpack-footer) { + // (space-consuming) scrollbars; a no-op where unsupported. + @include jetpack-admin-page-scrollable-middle { scrollbar-gutter: stable; } } diff --git a/projects/packages/my-jetpack/changelog/fix-admin-page-header-less-scroll-surface b/projects/packages/my-jetpack/changelog/fix-admin-page-header-less-scroll-surface new file mode 100644 index 000000000000..eb12098c9d11 --- /dev/null +++ b/projects/packages/my-jetpack/changelog/fix-admin-page-header-less-scroll-surface @@ -0,0 +1,4 @@ +Significance: patch +Type: fixed + +Connection screen: restore scrolling so the connect button is reachable on short viewports. diff --git a/projects/plugins/backup/changelog/fix-admin-page-header-less-scroll-surface b/projects/plugins/backup/changelog/fix-admin-page-header-less-scroll-surface new file mode 100644 index 000000000000..75d6d3b0a21e --- /dev/null +++ b/projects/plugins/backup/changelog/fix-admin-page-header-less-scroll-surface @@ -0,0 +1,4 @@ +Significance: patch +Type: fixed + +Secondary admin connection screen: restore scrolling so the connect button is reachable on short viewports. diff --git a/projects/plugins/boost/changelog/fix-admin-page-header-less-scroll-surface b/projects/plugins/boost/changelog/fix-admin-page-header-less-scroll-surface new file mode 100644 index 000000000000..6d3a50c72bd0 --- /dev/null +++ b/projects/plugins/boost/changelog/fix-admin-page-header-less-scroll-surface @@ -0,0 +1,4 @@ +Significance: patch +Type: fixed + +My Jetpack: restore scrolling on the connection screen so the connect button is reachable on short viewports. diff --git a/projects/plugins/jetpack/changelog/fix-admin-page-header-less-scroll-surface b/projects/plugins/jetpack/changelog/fix-admin-page-header-less-scroll-surface new file mode 100644 index 000000000000..c39a01035d1a --- /dev/null +++ b/projects/plugins/jetpack/changelog/fix-admin-page-header-less-scroll-surface @@ -0,0 +1,4 @@ +Significance: patch +Type: bugfix + +My Jetpack: restore scrolling on the connection screen so the connect button is reachable on short viewports. diff --git a/projects/plugins/protect/changelog/fix-admin-page-header-less-scroll-surface b/projects/plugins/protect/changelog/fix-admin-page-header-less-scroll-surface new file mode 100644 index 000000000000..6d3a50c72bd0 --- /dev/null +++ b/projects/plugins/protect/changelog/fix-admin-page-header-less-scroll-surface @@ -0,0 +1,4 @@ +Significance: patch +Type: fixed + +My Jetpack: restore scrolling on the connection screen so the connect button is reachable on short viewports. diff --git a/projects/plugins/search/changelog/fix-admin-page-header-less-scroll-surface b/projects/plugins/search/changelog/fix-admin-page-header-less-scroll-surface new file mode 100644 index 000000000000..6d3a50c72bd0 --- /dev/null +++ b/projects/plugins/search/changelog/fix-admin-page-header-less-scroll-surface @@ -0,0 +1,4 @@ +Significance: patch +Type: fixed + +My Jetpack: restore scrolling on the connection screen so the connect button is reachable on short viewports. diff --git a/projects/plugins/social/changelog/fix-admin-page-header-less-scroll-surface b/projects/plugins/social/changelog/fix-admin-page-header-less-scroll-surface new file mode 100644 index 000000000000..6d3a50c72bd0 --- /dev/null +++ b/projects/plugins/social/changelog/fix-admin-page-header-less-scroll-surface @@ -0,0 +1,4 @@ +Significance: patch +Type: fixed + +My Jetpack: restore scrolling on the connection screen so the connect button is reachable on short viewports. diff --git a/projects/plugins/stats/changelog/fix-admin-page-header-less-scroll-surface b/projects/plugins/stats/changelog/fix-admin-page-header-less-scroll-surface new file mode 100644 index 000000000000..6d3a50c72bd0 --- /dev/null +++ b/projects/plugins/stats/changelog/fix-admin-page-header-less-scroll-surface @@ -0,0 +1,4 @@ +Significance: patch +Type: fixed + +My Jetpack: restore scrolling on the connection screen so the connect button is reachable on short viewports. diff --git a/projects/plugins/videopress/changelog/fix-admin-page-header-less-scroll-surface b/projects/plugins/videopress/changelog/fix-admin-page-header-less-scroll-surface new file mode 100644 index 000000000000..6d3a50c72bd0 --- /dev/null +++ b/projects/plugins/videopress/changelog/fix-admin-page-header-less-scroll-surface @@ -0,0 +1,4 @@ +Significance: patch +Type: fixed + +My Jetpack: restore scrolling on the connection screen so the connect button is reachable on short viewports.