1
0
mirror of https://github.com/kremalicious/metamask-extension.git synced 2024-12-23 09:52:26 +01:00

migration of Popover to use TS Box version (#20279)

* migration of Popover to use TS Box version

* fix lint error

* Updating docs

---------

Co-authored-by: georgewrmarshall <george.marshall@consensys.net>
This commit is contained in:
jainex 2023-08-04 23:41:32 +05:30 committed by GitHub
parent 3915482edb
commit 798a9b0e60
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
6 changed files with 180 additions and 145 deletions

View File

@ -11,8 +11,6 @@ Popover is an overlay that appears by the trigger used for menus, additional con
## Props ## Props
The `Popover` accepts all props below as well as all [Box](/docs/ui-components-ui-box-box-stories-js--default-story#props) component props
<ArgsTable of={Popover} /> <ArgsTable of={Popover} />
### Reference Element ### Reference Element
@ -21,7 +19,8 @@ The `referenceElement` prop is required and used to position the popover relativ
```jsx ```jsx
import { useState } from 'react'; import { useState } from 'react';
import { Popover } from '../../ui/component-library'; import { BackgroundColor } from '../../../helpers/constants/design-system'
import { Popover, Box } from '../../component-library';
const [referenceElement, setReferenceElement] = useState(); const [referenceElement, setReferenceElement] = useState();
@ -29,8 +28,12 @@ const setBoxRef = (ref) => {
setReferenceElement(ref); setReferenceElement(ref);
}; };
<Box ref={setBoxRef}></Box> <Box
<Popover referenceElement={referenceElement}>Reference Element</Popover> ref={setBoxRef}
backgroundColor={BackgroundColor.primaryDefault}
style={{ width: 200, height: 200 }}
/>
<Popover referenceElement={referenceElement}>Reference element</Popover>
``` ```
### Children ### Children
@ -44,7 +47,7 @@ import {
Icon, Icon,
IconSize, IconSize,
IconName, IconName,
} from '../../ui/component-library'; } from '../../component-library';
<Popover> <Popover>
<Text> <Text>
@ -61,7 +64,7 @@ Use the `position` prop with the `PopoverPosition` enum to set the position of t
Default is `PopoverPosition.Auto` Default is `PopoverPosition.Auto`
```jsx ```jsx
import { Popover, PopoverPosition } from '../../ui/component-library'; import { Popover, PopoverPosition } from '../../component-library';
<Popover position={PopoverPosition.Auto}>Auto</Popover> <Popover position={PopoverPosition.Auto}>Auto</Popover>
<Popover position={PopoverPosition.AutoStart}>AutoStart</Popover> <Popover position={PopoverPosition.AutoStart}>AutoStart</Popover>
@ -86,7 +89,7 @@ The `isPortal` prop is a boolean that when set to true, causes the Popover to be
Default `false` Default `false`
```jsx ```jsx
import { Popover } from '../../ui/component-library'; import { Popover } from '../../component-library';
<Popover isPortal={true}>Popover using create portal</Popover>; <Popover isPortal={true}>Popover using create portal</Popover>;
``` ```
@ -96,7 +99,7 @@ import { Popover } from '../../ui/component-library';
Use the `hasArrow` boolean to add an arrow to the popover. Use the `hasArrow` boolean to add an arrow to the popover.
```jsx ```jsx
import { Popover } from '../../ui/component-library'; import { Popover } from '../../component-library';
<Popover hasArrow>Popover with arrow</Popover>; <Popover hasArrow>Popover with arrow</Popover>;
``` ```
@ -106,7 +109,7 @@ import { Popover } from '../../ui/component-library';
Use the `isOpen` boolean to control the visibility of the popover. Use the `isOpen` boolean to control the visibility of the popover.
```jsx ```jsx
import { Popover } from '../../ui/component-library'; import { Popover } from '../../component-library';
<Popover isOpen={true}>Popover with arrow</Popover>; <Popover isOpen={true}>Popover with arrow</Popover>;
``` ```
@ -117,7 +120,7 @@ Use the `flip` boolean to flip the popover to the opposite side of the reference
For `PopoverPosition.Auto` this will become true. For `PopoverPosition.Auto` this will become true.
```jsx ```jsx
import { Popover } from '../../ui/component-library'; import { Popover } from '../../component-library';
<Popover flip={true}>Flip demo</Popover>; <Popover flip={true}>Flip demo</Popover>;
``` ```
@ -128,7 +131,7 @@ Use the `preventOverflow` boolean to prevent the popover from overflowing the vi
For `PopoverPosition.Auto` this will become true. For `PopoverPosition.Auto` this will become true.
```jsx ```jsx
import { Popover } from '../../ui/component-library'; import { Popover } from '../../component-library';
<Popover preventOverflow={true}>Prevent overflow demo</Popover>; <Popover preventOverflow={true}>Prevent overflow demo</Popover>;
``` ```
@ -138,7 +141,7 @@ import { Popover } from '../../ui/component-library';
Use the `referenceHidden` boolean to hide the Popover when the reference element is no longer visible in the viewport. Use the `referenceHidden` boolean to hide the Popover when the reference element is no longer visible in the viewport.
```jsx ```jsx
import { Popover } from '../../ui/component-library'; import { Popover } from '../../component-library';
<Popover referenceHidden={true}>Reference hidden demo</Popover>; <Popover referenceHidden={true}>Reference hidden demo</Popover>;
``` ```
@ -148,7 +151,7 @@ import { Popover } from '../../ui/component-library';
Use the `matchWidth` boolean to match the width of the popover to the reference element. Use the `matchWidth` boolean to match the width of the popover to the reference element.
```jsx ```jsx
import { Popover } from '../../ui/component-library'; import { Popover } from '../../component-library';
<Popover matchWidth={true}>Match width demo</Popover>; <Popover matchWidth={true}>Match width demo</Popover>;
``` ```
@ -161,7 +164,7 @@ Use the `role` prop with `PopoverRole` enum to set the role of the popover.
Default: `PopoverRole.Tooltip` Default: `PopoverRole.Tooltip`
```jsx ```jsx
import { Popover, PopoverRole } from '../../ui/component-library'; import { Popover, PopoverRole } from '../../component-library';
<Popover role={PopoverRole.Tooltip}>PopoverRole.Tooltip</Popover>; <Popover role={PopoverRole.Tooltip}>PopoverRole.Tooltip</Popover>;
<Popover role={PopoverRole.Dialog}>PopoverRole.Dialog</Popover>; <Popover role={PopoverRole.Dialog}>PopoverRole.Dialog</Popover>;
@ -174,7 +177,7 @@ Default is `[0, 8]`
First number controls the skidding offset and the second number controls the distance offset. First number controls the skidding offset and the second number controls the distance offset.
```jsx ```jsx
import { Popover } from '../../ui/component-library'; import { Popover } from '../../component-library';
<Popover offset={[0, 32]}>offset override to [0,32]</Popover>; <Popover offset={[0, 32]}>offset override to [0,32]</Popover>;
``` ```
@ -184,7 +187,7 @@ import { Popover } from '../../ui/component-library';
`onPressEscKey` is a callback function that is invoked when the 'Escape' key is pressed within the `Popover` component `onPressEscKey` is a callback function that is invoked when the 'Escape' key is pressed within the `Popover` component
```jsx ```jsx
import { Popover } from '../../ui/component-library'; import { Popover } from '../../component-library';
const [isOpen, setIsOpen] = useState(false); const [isOpen, setIsOpen] = useState(false);
@ -202,7 +205,7 @@ const handleClick = () => {
Using the `PopoverHeader` component to add a header to the `Popover` component. The `PopoverHeader` is used to show common elements such as title, back button, and close button. Using the `PopoverHeader` component to add a header to the `Popover` component. The `PopoverHeader` is used to show common elements such as title, back button, and close button.
```jsx ```jsx
import { Popover } from '../../ui/component-library'; import { Popover } from '../../component-library';
<Popover> <Popover>
<PopoverHeader <PopoverHeader
@ -220,7 +223,7 @@ import { Popover } from '../../ui/component-library';
Not built into the `Popover` component, but a demo of `onMouseEnter` and `onMouseLeave` events on the reference element to control the visibility of the popover Not built into the `Popover` component, but a demo of `onMouseEnter` and `onMouseLeave` events on the reference element to control the visibility of the popover
```jsx ```jsx
import { Popover } from '../../ui/component-library'; import { Popover } from '../../component-library';
const [isOpen, setIsOpen] = useState(false); const [isOpen, setIsOpen] = useState(false);
@ -245,7 +248,7 @@ const handleMouseLeave = () => {
Not built into the `Popover` component, but a demo of `onFocus` and `onBlur` events on the reference element to control the visibility of the popover Not built into the `Popover` component, but a demo of `onFocus` and `onBlur` events on the reference element to control the visibility of the popover
```jsx ```jsx
import { Popover } from '../../ui/component-library'; import { Popover } from '../../component-library';
const [isOpen, setIsOpen] = useState(false); const [isOpen, setIsOpen] = useState(false);

View File

@ -3,7 +3,7 @@
exports[`Popover should render popover element correctly 1`] = ` exports[`Popover should render popover element correctly 1`] = `
<div> <div>
<div <div
class="box mm-popover mm-popover--open mm-popover--reference-hidden box--padding-4 box--flex-direction-row box--background-color-background-default box--rounded-lg box--border-color-border-muted box--border-style-solid box--border-width-1" class="mm-box mm-popover mm-popover--open mm-popover--reference-hidden mm-box--padding-4 mm-box--background-color-background-default mm-box--rounded-lg mm-box--border-color-border-muted box--border-style-solid box--border-width-1"
data-testid="popover" data-testid="popover"
role="tooltip" role="tooltip"
style="position: absolute; left: 0px; top: 0px; width: auto;" style="position: absolute; left: 0px; top: 0px; width: auto;"

View File

@ -1,3 +1,7 @@
export { Popover } from './popover'; export { Popover } from './popover';
export { PopoverPosition, PopoverRole } from './popover.types'; export { PopoverPosition, PopoverRole } from './popover.types';
export type { PopoverProps } from './popover.types'; export type {
PopoverProps,
PopoverStyleUtilityProps,
PopoverComponent,
} from './popover.types';

View File

@ -1,6 +1,6 @@
import React, { useState, useEffect } from 'react'; import React, { useState, useEffect } from 'react';
import { StoryFn, Meta } from '@storybook/react'; import { StoryFn, Meta } from '@storybook/react';
import Box from '../../ui/box/box'; import { Box, Icon, IconName, IconSize, PopoverHeader, Text } from '..';
import { import {
AlignItems, AlignItems,
BackgroundColor, BackgroundColor,
@ -9,8 +9,9 @@ import {
Display, Display,
JustifyContent, JustifyContent,
TextAlign, TextAlign,
TextColor,
} from '../../../helpers/constants/design-system'; } from '../../../helpers/constants/design-system';
import { Icon, IconName, IconSize, PopoverHeader, Text } from '..';
import README from './README.mdx'; import README from './README.mdx';
import { Popover, PopoverPosition, PopoverRole } from '.'; import { Popover, PopoverPosition, PopoverRole } from '.';
@ -78,7 +79,7 @@ const Template: StoryFn<typeof Popover> = (args) => {
onClick={handleClick} onClick={handleClick}
backgroundColor={BackgroundColor.primaryAlternative} backgroundColor={BackgroundColor.primaryAlternative}
style={{ width: 200, height: 200 }} style={{ width: 200, height: 200 }}
color={Color.primaryInverse} color={TextColor.primaryInverse}
as="button" as="button"
> >
Click to toggle popover Click to toggle popover
@ -751,7 +752,7 @@ export const OnPressEscKey: StoryFn<typeof Popover> = (args) => {
onClick={handleClick} onClick={handleClick}
backgroundColor={BackgroundColor.primaryAlternative} backgroundColor={BackgroundColor.primaryAlternative}
style={{ width: 200, height: 200 }} style={{ width: 200, height: 200 }}
color={Color.primaryInverse} color={TextColor.primaryInverse}
as="button" as="button"
> >
Click to open Click to open
@ -835,7 +836,7 @@ export const MouseEventDemo: StoryFn<typeof Popover> = (args) => {
onMouseLeave={handleMouseLeave} onMouseLeave={handleMouseLeave}
backgroundColor={BackgroundColor.primaryAlternative} backgroundColor={BackgroundColor.primaryAlternative}
style={{ width: 200, height: 200 }} style={{ width: 200, height: 200 }}
color={Color.primaryInverse} color={TextColor.primaryInverse}
> >
Hover Hover
</Box> </Box>
@ -872,7 +873,7 @@ export const OnFocusBlur: StoryFn<typeof Popover> = (args) => {
onBlur={handleClose} onBlur={handleClose}
backgroundColor={BackgroundColor.primaryAlternative} backgroundColor={BackgroundColor.primaryAlternative}
style={{ width: 200, height: 200 }} style={{ width: 200, height: 200 }}
color={Color.primaryInverse} color={TextColor.primaryInverse}
as="button" as="button"
> >
Focus to open Focus to open

View File

@ -10,10 +10,20 @@ import {
Display, Display,
JustifyContent, JustifyContent,
} from '../../../helpers/constants/design-system'; } from '../../../helpers/constants/design-system';
import Box from '../../ui/box/box';
import { PopoverPosition, PopoverProps, PopoverRole } from '.';
export const Popover = ({ import { Box } from '..';
import type { BoxProps, PolymorphicRef } from '../box';
import {
PopoverProps,
PopoverComponent,
PopoverPosition,
PopoverRole,
} from './popover.types';
export const Popover: PopoverComponent = React.forwardRef(
<C extends React.ElementType = 'div'>(
{
children, children,
className = '', className = '',
position = PopoverPosition.Auto, position = PopoverPosition.Auto,
@ -31,8 +41,12 @@ export const Popover = ({
arrowProps, arrowProps,
onPressEscKey, onPressEscKey,
...props ...props
}: PopoverProps) => { }: PopoverProps<C>,
const [popperElement, setPopperElement] = useState<HTMLElement | null>(null); ref?: PolymorphicRef<C>,
) => {
const [popperElement, setPopperElement] = useState<HTMLElement | null>(
null,
);
const [arrowElement, setArrowElement] = useState<HTMLElement | null>(null); const [arrowElement, setArrowElement] = useState<HTMLElement | null>(null);
// Define Popper options // Define Popper options
@ -101,9 +115,9 @@ export const Popover = ({
}, },
className, className,
)} )}
ref={setPopperElement} ref={ref || setPopperElement}
{...attributes.popper} {...attributes.popper}
{...props} {...(props as BoxProps<C>)}
style={{ ...styles.popper, ...contentStyle, ...props.style }} style={{ ...styles.popper, ...contentStyle, ...props.style }}
> >
{children} {children}
@ -117,7 +131,7 @@ export const Popover = ({
alignItems={AlignItems.center} alignItems={AlignItems.center}
style={styles.arrow} style={styles.arrow}
{...attributes.arrow} {...attributes.arrow}
{...arrowProps} {...(arrowProps as BoxProps<'div'>)}
/> />
)} )}
</Box> </Box>
@ -130,4 +144,5 @@ export const Popover = ({
: isOpen && PopoverContent} : isOpen && PopoverContent}
</> </>
); );
}; },
);

View File

@ -1,4 +1,9 @@
import type { BoxProps } from '../../ui/box/box.d'; import React from 'react';
import type {
StyleUtilityProps,
PolymorphicComponentPropWithRef,
BoxProps,
} from '../box';
export enum PopoverPosition { export enum PopoverPosition {
Auto = 'auto', Auto = 'auto',
@ -21,7 +26,7 @@ export enum PopoverRole {
Dialog = 'dialog', Dialog = 'dialog',
} }
export interface PopoverProps extends BoxProps { export interface PopoverStyleUtilityProps extends StyleUtilityProps {
/** /**
* The contents within the Popover * The contents within the Popover
*/ */
@ -46,7 +51,7 @@ export interface PopoverProps extends BoxProps {
/** /**
* Pass any `BoxProps` to the Popover arrow * Pass any `BoxProps` to the Popover arrow
*/ */
arrowProps?: BoxProps; arrowProps?: BoxProps<'div'>;
/** /**
* Boolean to control the width of the Popover to match the width of the reference element * Boolean to control the width of the Popover to match the width of the reference element
* Default: false * Default: false
@ -92,3 +97,10 @@ export interface PopoverProps extends BoxProps {
*/ */
onPressEscKey?: () => void; onPressEscKey?: () => void;
} }
export type PopoverProps<C extends React.ElementType> =
PolymorphicComponentPropWithRef<C, PopoverStyleUtilityProps>;
export type PopoverComponent = <C extends React.ElementType = 'div'>(
props: PopoverProps<C>,
) => React.ReactElement | null;