From 1f675c3bdeb9b6db68515ade52eff192cdbfe556 Mon Sep 17 00:00:00 2001 From: Danielle D'Souza Date: Thu, 18 Aug 2022 19:55:37 +0000 Subject: [PATCH 1/3] Trigger pressed animation on backdrop click --- polaris-react/src/components/Modal/Modal.tsx | 23 ++++++++++++++++--- .../components/CloseButton/CloseButton.scss | 3 ++- .../components/CloseButton/CloseButton.tsx | 8 ++++++- .../Modal/components/Header/Header.tsx | 15 ++++++++++-- 4 files changed, 42 insertions(+), 7 deletions(-) diff --git a/polaris-react/src/components/Modal/Modal.tsx b/polaris-react/src/components/Modal/Modal.tsx index 0967d78e459..8ae553208d8 100644 --- a/polaris-react/src/components/Modal/Modal.tsx +++ b/polaris-react/src/components/Modal/Modal.tsx @@ -1,4 +1,4 @@ -import React, {useState, useCallback, useRef} from 'react'; +import React, {useState, useCallback, useRef, useEffect} from 'react'; import {TransitionGroup} from 'react-transition-group'; import {focusFirstFocusableNode} from '../../utilities/focus'; @@ -90,6 +90,7 @@ export const Modal: React.FunctionComponent & { fullScreen, }: ModalProps) { const [iframeHeight, setIframeHeight] = useState(IFRAME_LOADING_HEIGHT); + const [closing, setClosing] = useState(false); const headerId = useUniqueId('modal-header'); const activatorRef = useRef(null); @@ -136,6 +137,17 @@ export const Modal: React.FunctionComponent & { [onIFrameLoad], ); + useEffect(() => { + if (closing) { + onClose(); + setClosing(false); + } + }, [closing, onClose]); + + const handleOnClose = () => { + setClosing(true); + }; + if (open) { const footerMarkup = !footer && !primaryAction && !secondaryActions ? null : ( @@ -196,7 +208,12 @@ export const Modal: React.FunctionComponent & { limitHeight={limitHeight} fullScreen={fullScreen} > -
+
{title}
{bodyMarkup}
@@ -204,7 +221,7 @@ export const Modal: React.FunctionComponent & { ); - backdrop = ; + backdrop = ; } const animated = !instant; diff --git a/polaris-react/src/components/Modal/components/CloseButton/CloseButton.scss b/polaris-react/src/components/Modal/components/CloseButton/CloseButton.scss index cd79fee5ac7..8cc0a360491 100644 --- a/polaris-react/src/components/Modal/components/CloseButton/CloseButton.scss +++ b/polaris-react/src/components/Modal/components/CloseButton/CloseButton.scss @@ -13,7 +13,8 @@ @include recolor-icon(var(--p-icon-hovered)); } - &:active { + &:active, + &.pressed { background: var(--p-surface-pressed); } diff --git a/polaris-react/src/components/Modal/components/CloseButton/CloseButton.tsx b/polaris-react/src/components/Modal/components/CloseButton/CloseButton.tsx index 7517c5fc159..176f52ef244 100644 --- a/polaris-react/src/components/Modal/components/CloseButton/CloseButton.tsx +++ b/polaris-react/src/components/Modal/components/CloseButton/CloseButton.tsx @@ -8,11 +8,16 @@ import {Icon} from '../../../Icon'; import styles from './CloseButton.scss'; export interface CloseButtonProps { + pressed?: boolean; titleHidden?: boolean; onClick(): void; } -export function CloseButton({titleHidden = false, onClick}: CloseButtonProps) { +export function CloseButton({ + pressed, + titleHidden = false, + onClick, +}: CloseButtonProps) { const i18n = useI18n(); return ( @@ -21,6 +26,7 @@ export function CloseButton({titleHidden = false, onClick}: CloseButtonProps) { className={classNames( styles.CloseButton, titleHidden && styles.titleHidden, + pressed && styles.pressed, )} aria-label={i18n.translate('Polaris.Common.close')} > diff --git a/polaris-react/src/components/Modal/components/Header/Header.tsx b/polaris-react/src/components/Modal/components/Header/Header.tsx index e5d9c71dafd..47e6f86947c 100644 --- a/polaris-react/src/components/Modal/components/Header/Header.tsx +++ b/polaris-react/src/components/Modal/components/Header/Header.tsx @@ -8,11 +8,18 @@ import styles from './Header.scss'; export interface HeaderProps { id: string; titleHidden: boolean; + closing: boolean; children?: React.ReactNode; onClose(): void; } -export function Header({id, titleHidden, children, onClose}: HeaderProps) { +export function Header({ + id, + titleHidden, + closing, + children, + onClose, +}: HeaderProps) { return (
- + ); } From fa1eef6521b5eae0cacbd31187107104ca273d9a Mon Sep 17 00:00:00 2001 From: Danielle D'Souza Date: Fri, 2 Sep 2022 11:59:27 -0400 Subject: [PATCH 2/3] Trigger pressed state on Escape keydown --- .../src/components/Backdrop/Backdrop.tsx | 21 ++++++++++++++-- polaris-react/src/components/Modal/Modal.tsx | 16 +++---------- .../Modal/components/Dialog/Dialog.tsx | 24 +++++++++++++++++-- 3 files changed, 44 insertions(+), 17 deletions(-) diff --git a/polaris-react/src/components/Backdrop/Backdrop.tsx b/polaris-react/src/components/Backdrop/Backdrop.tsx index ba274071f75..4a0ca77d734 100644 --- a/polaris-react/src/components/Backdrop/Backdrop.tsx +++ b/polaris-react/src/components/Backdrop/Backdrop.tsx @@ -1,4 +1,4 @@ -import React from 'react'; +import React, {Dispatch, SetStateAction} from 'react'; import {classNames} from '../../utilities/css'; import {ScrollLock} from '../ScrollLock'; @@ -10,10 +10,12 @@ export interface BackdropProps { transparent?: boolean; onClick?(): void; onTouchStart?(): void; + setClosing?: Dispatch>; } export function Backdrop(props: BackdropProps) { - const {onClick, onTouchStart, belowNavigation, transparent} = props; + const {onClick, onTouchStart, belowNavigation, transparent, setClosing} = + props; const className = classNames( styles.Backdrop, @@ -21,6 +23,19 @@ export function Backdrop(props: BackdropProps) { transparent && styles.transparent, ); + const handleMouseDown = () => { + if (setClosing) { + setClosing(true); + } + }; + + const handleMouseUp = () => { + if (setClosing && onClick) { + setClosing(false); + onClick(); + } + }; + return ( <> @@ -28,6 +43,8 @@ export function Backdrop(props: BackdropProps) { className={className} onClick={onClick} onTouchStart={onTouchStart} + onMouseDown={handleMouseDown} + onMouseUp={handleMouseUp} /> ); diff --git a/polaris-react/src/components/Modal/Modal.tsx b/polaris-react/src/components/Modal/Modal.tsx index 8ae553208d8..b1126b44f70 100644 --- a/polaris-react/src/components/Modal/Modal.tsx +++ b/polaris-react/src/components/Modal/Modal.tsx @@ -1,4 +1,4 @@ -import React, {useState, useCallback, useRef, useEffect} from 'react'; +import React, {useState, useCallback, useRef} from 'react'; import {TransitionGroup} from 'react-transition-group'; import {focusFirstFocusableNode} from '../../utilities/focus'; @@ -137,17 +137,6 @@ export const Modal: React.FunctionComponent & { [onIFrameLoad], ); - useEffect(() => { - if (closing) { - onClose(); - setClosing(false); - } - }, [closing, onClose]); - - const handleOnClose = () => { - setClosing(true); - }; - if (open) { const footerMarkup = !footer && !primaryAction && !secondaryActions ? null : ( @@ -207,6 +196,7 @@ export const Modal: React.FunctionComponent & { small={small} limitHeight={limitHeight} fullScreen={fullScreen} + setClosing={setClosing} >
& { ); - backdrop = ; + backdrop = ; } const animated = !instant; diff --git a/polaris-react/src/components/Modal/components/Dialog/Dialog.tsx b/polaris-react/src/components/Modal/components/Dialog/Dialog.tsx index f640db87986..f13f4ef74b1 100644 --- a/polaris-react/src/components/Modal/components/Dialog/Dialog.tsx +++ b/polaris-react/src/components/Modal/components/Dialog/Dialog.tsx @@ -1,4 +1,4 @@ -import React, {useRef, useEffect} from 'react'; +import React, {useRef, useEffect, SetStateAction, Dispatch} from 'react'; import {Transition, CSSTransition} from 'react-transition-group'; import {motion} from '@shopify/polaris-tokens'; @@ -22,6 +22,7 @@ export interface DialogProps { onExited?(): void; in?: boolean; fullScreen?: boolean; + setClosing?: Dispatch>; } export function Dialog({ @@ -35,6 +36,7 @@ export function Dialog({ small, limitHeight, fullScreen, + setClosing, ...props }: DialogProps) { const containerNode = useRef(null); @@ -53,6 +55,19 @@ export function Dialog({ focusFirstFocusableNode(containerNode.current); }, []); + const handleKeyDown = () => { + if (setClosing) { + setClosing(true); + } + }; + + const handleKeyUp = () => { + if (setClosing) { + setClosing(false); + } + onClose(); + }; + return (
- + + {children}
From 2d63d25662c40baaf25195c1c2110447daf5ba64 Mon Sep 17 00:00:00 2001 From: Danielle D'Souza Date: Fri, 2 Sep 2022 12:06:09 -0400 Subject: [PATCH 3/3] Add changeset --- .changeset/strong-poems-double.md | 5 +++++ 1 file changed, 5 insertions(+) create mode 100644 .changeset/strong-poems-double.md diff --git a/.changeset/strong-poems-double.md b/.changeset/strong-poems-double.md new file mode 100644 index 00000000000..4df6142f2ed --- /dev/null +++ b/.changeset/strong-poems-double.md @@ -0,0 +1,5 @@ +--- +'@shopify/polaris': minor +--- + +Clicking on the modal backdrop triggers the pressed state of the modal's close button