wix-style-react
Version:
wix-style-react
120 lines • 6.43 kB
JavaScript
import { X } from '@wix/wix-ui-icons-common';
import PropTypes from 'prop-types';
import React from 'react';
import IconButton from '../IconButton';
import Text from '../Text';
import Tooltip from '../Tooltip';
import { arrowsDirection, dataHooks, modalPreviewIDs, skins, } from './constants';
import { classes, st } from './ModalPreviewLayout.st.css';
import NavigationButton from './NavigationButton/NavigationButton';
/** This is a fullscreen modal to present a document to the user overlaying the entire view port */
class ModalPreviewLayout extends React.PureComponent {
constructor(props) {
super(props);
this._onRightNavigationClick = () => {
const { childIndexDisplayed } = this.state;
const { onClick } = this.props.nextButtonProps;
const newChildIndexDisplayed = childIndexDisplayed + 1;
this.setState({ childIndexDisplayed: newChildIndexDisplayed }, () => {
onClick && onClick(newChildIndexDisplayed);
});
};
this._onLeftNavigationClick = () => {
const { childIndexDisplayed } = this.state;
const { onClick } = this.props.prevButtonProps;
const newChildIndexDisplayed = childIndexDisplayed - 1;
this.setState({ childIndexDisplayed: newChildIndexDisplayed }, () => {
onClick && onClick(newChildIndexDisplayed);
});
};
this.state = {
childIndexDisplayed: this.props.startDisplayingAtChildIndex,
};
}
_shouldClose(id) {
return (this.props.shouldCloseOnOverlayClick &&
[modalPreviewIDs.overlay, modalPreviewIDs.innerOverlay].includes(id));
}
_onOverlayClick(onClose) {
return ({ target: { id } }) => {
if (this._shouldClose(id) && typeof onClose === 'function') {
onClose();
}
};
}
_renderNavigationButtons(hasLeft, hasRight) {
const { prevButtonProps, nextButtonProps } = this.props;
return (React.createElement(React.Fragment, null,
hasLeft && (React.createElement(NavigationButton, { tooltipText: prevButtonProps.tooltipText, direction: arrowsDirection.leftArrow, onClick: this._onLeftNavigationClick })),
hasRight && (React.createElement(NavigationButton, { tooltipText: nextButtonProps.tooltipText, direction: arrowsDirection.rightArrow, onClick: this._onRightNavigationClick }))));
}
render() {
const { dataHook, actions, title, children, onClose, closeButtonTooltipText, skin, } = this.props;
const { childIndexDisplayed } = this.state;
const childrenArr = React.Children.toArray(children);
const hasLeft = childIndexDisplayed > 0;
const hasRight = childIndexDisplayed < childrenArr.length - 1;
return (React.createElement("div", { id: modalPreviewIDs.overlay, "data-hook": dataHook, className: classes.root, onClick: this._onOverlayClick(onClose), "data-skin": skin },
React.createElement("div", { className: st(classes.header, { skin }) },
React.createElement("div", { "data-hook": dataHooks.modalPreviewTitle, className: classes.title },
React.createElement(Text, { light: skin === skins.dark, ellipsis: true, tooltipProps: { placement: 'bottom' } }, title)),
React.createElement("div", { className: classes.actions, "data-hook": dataHooks.modalPreviewActions }, actions),
React.createElement("div", { className: classes.closeButton },
React.createElement(Tooltip, { disabled: !closeButtonTooltipText, className: classes.modalTooltip, dataHook: dataHooks.closeButtonTooltip, appendTo: "scrollParent", content: React.createElement(Text, null, closeButtonTooltipText), placement: "bottom" },
React.createElement(IconButton, { as: "button", onClick: onClose, priority: "secondary", skin: skin === skins.dark ? 'transparent' : 'standard', dataHook: dataHooks.modalPreviewCloseButton },
React.createElement(X, null))))),
React.createElement("div", { id: modalPreviewIDs.innerOverlay, "data-hook": dataHooks.innerOverlay, className: classes.innerOverlay },
React.createElement("div", { "data-hook": dataHooks.modalPreviewContent, className: classes.content, "data-index": childIndexDisplayed }, childrenArr[childIndexDisplayed]),
this._renderNavigationButtons(hasLeft, hasRight))));
}
}
ModalPreviewLayout.displayName = 'ModalPreviewLayout';
ModalPreviewLayout.propTypes = {
/** Applied as data-hook HTML attribute that can be used in the tests */
dataHook: PropTypes.string,
/** component to be displayed in header strip to preform actions relevant to the displayed content */
actions: PropTypes.node,
/** title text to be displayed in the header strip */
title: PropTypes.string,
/** modal content displayed mid-screen*/
children: PropTypes.node.isRequired,
/** callback for when the modal is closed */
onClose: PropTypes.func.isRequired,
/** boolean to determine whether closing the overlay on click */
shouldCloseOnOverlayClick: PropTypes.bool,
/** Tooltip close button text */
closeButtonTooltipText: PropTypes.node,
/** Previous button props
* ##### onClick signature:
* function(childIndexDisplayed: number) => void
* * `childIndexDisplayed`: the index of the child component displayed.
*/
prevButtonProps: PropTypes.shape({
onClick: PropTypes.func,
tooltipText: PropTypes.node,
}),
/** Next button props
* ##### onClick signature:
* function(childIndexDisplayed: number) => void
* * `childIndexDisplayed`: the index of the child component displayed.
*/
nextButtonProps: PropTypes.shape({
onClick: PropTypes.func,
tooltipText: PropTypes.node,
}),
/**
* Pass an index to start rendering from a specific child component.
*/
startDisplayingAtChildIndex: PropTypes.number,
/** Controls the skin of the component */
skin: PropTypes.oneOf(Object.keys(skins)),
};
ModalPreviewLayout.defaultProps = {
shouldCloseOnOverlayClick: true,
nextButtonProps: {},
prevButtonProps: {},
startDisplayingAtChildIndex: 0,
skin: 'dark',
};
export default ModalPreviewLayout;
//# sourceMappingURL=ModalPreviewLayout.js.map