UNPKG

glass-app-manager

Version:

Informatica's Glass Framework CLI for bootstrapping

64 lines (53 loc) 1.91 kB
// @flow import * as React from "react"; import Popover from "react-tiny-popover"; import ArrowContainer from "react-tiny-popover/dist/ArrowContainer"; export type PopupProps = { /** * Set `true` to open the popup by default. Use this when * you want to _control_ when the popup is open or not. */ isOpen?: boolean, /** * Specify a custom trigger. This makes the popup _uncontrolled_ * and state will be handled internally. */ trigger: React.Element<any>, /** * Specify the content of the popup. */ children: React.Node, /** * When popup is uncontrolled, specify how you want the user to interact * with the popup. */ on: "click" | "focus" | "hover", }; const getEventProps = (on, setOpen, toggle) => ({ ...(on.indexOf("hover") !== -1 ? { onMouseEnter: () => setOpen(true), onMouseLeave: () => setOpen(false), } : {}), ...(on.indexOf("focus") !== -1 ? { onFocus: () => setOpen(true), onBlur: () => setOpen(false), } : {}), onClick: on.indexOf("click") !== -1 ? toggle : undefined, }); export default function Popup({ isOpen, trigger, children, on = "", ...rest }: PopupProps) { const [internalIsOpen, setInternalIsOpen] = React.useState(false); const triggers = React.useMemo( () => getEventProps(on, setInternalIsOpen, () => setInternalIsOpen(!internalIsOpen)), [internalIsOpen, on, setInternalIsOpen] ); return ( <Popover containerClassName="popup-container" containerStyle={{overflow: "visible"}} {...rest} isOpen={isOpen || internalIsOpen}> {trigger ? React.cloneElement(trigger, { ...triggers }) : children} </Popover> ); } Popup.ArrowContainer = ArrowContainer;