diff --git a/packages/components/src/modal/index.tsx b/packages/components/src/modal/index.tsx index ed00dd2624452c..d9c7b602b83920 100644 --- a/packages/components/src/modal/index.tsx +++ b/packages/components/src/modal/index.tsx @@ -14,6 +14,7 @@ import { useRef, useState, forwardRef, + useLayoutEffect, } from '@wordpress/element'; import { useInstanceId, @@ -25,6 +26,7 @@ import { } from '@wordpress/compose'; import { __ } from '@wordpress/i18n'; import { close } from '@wordpress/icons'; +import { getScrollContainer } from '@wordpress/dom'; /** * Internal dependencies @@ -76,8 +78,26 @@ function UnforwardedModal( const constrainedTabbingRef = useConstrainedTabbing(); const focusReturnRef = useFocusReturn(); const focusOutsideProps = useFocusOutside( onRequestClose ); + const contentRef = useRef< HTMLDivElement >( null ); + const childrenContainerRef = useRef< HTMLDivElement >( null ); const [ hasScrolledContent, setHasScrolledContent ] = useState( false ); + const [ hasScrollableContent, setHasScrollableContent ] = useState( false ); + + // Determines whether the Modal content is scrollable and updates the state. + const isContentScrollable = useCallback( () => { + if ( ! contentRef.current ) { + return; + } + + const closestScrollContainer = getScrollContainer( contentRef.current ); + + if ( contentRef.current === closestScrollContainer ) { + setHasScrollableContent( true ); + } else { + setHasScrollableContent( false ); + } + }, [ contentRef ] ); useEffect( () => { openModalCount++; @@ -97,6 +117,22 @@ function UnforwardedModal( }; }, [ bodyOpenClassName ] ); + // Calls the isContentScrollable callback when the Modal children container resizes. + useLayoutEffect( () => { + if ( ! window.ResizeObserver || ! childrenContainerRef.current ) { + return; + } + + const resizeObserver = new ResizeObserver( isContentScrollable ); + resizeObserver.observe( childrenContainerRef.current ); + + isContentScrollable(); + + return () => { + resizeObserver.disconnect(); + }; + }, [ isContentScrollable, childrenContainerRef ] ); + function handleEscapeKeyDown( event: KeyboardEvent< HTMLDivElement > ) { if ( // Ignore keydowns from IMEs @@ -172,10 +208,18 @@ function UnforwardedModal(
+ Change options related to publishing. +
++ Review settings, such as visibility and tags. +
- Review settings, such as visibility and tags. -
+ Highlights the current block and fades other content. +
- Highlights the current block and fades other content. -
+ Show text instead of icons on buttons. +
- Show text instead of icons on buttons. -
+ Opens the block list view sidebar by default. +
- Opens the block list view sidebar by default. -
+ Make the editor look like your theme. +
- Make the editor look like your theme. -
+ Shows block breadcrumbs at the bottom of the editor. +
- Shows block breadcrumbs at the bottom of the editor. -