UNPKG

13 kBJavaScriptView Raw
1import _extends from "@babel/runtime/helpers/esm/extends";
2import _objectWithoutPropertiesLoose from "@babel/runtime/helpers/esm/objectWithoutPropertiesLoose";
3import * as React from 'react';
4import PropTypes from 'prop-types';
5import clsx from 'clsx';
6import withStyles from '../styles/withStyles';
7import capitalize from '../utils/capitalize';
8import deprecatedPropType from '../utils/deprecatedPropType';
9import Modal from '../Modal';
10import Backdrop from '../Backdrop';
11import Fade from '../Fade';
12import { duration } from '../styles/transitions';
13import Paper from '../Paper';
14export const styles = theme => ({
15 /* Styles applied to the root element. */
16 root: {
17 '@media print': {
18 // Use !important to override the Modal inline-style.
19 position: 'absolute !important'
20 }
21 },
22
23 /* Styles applied to the container element if `scroll="paper"`. */
24 scrollPaper: {
25 display: 'flex',
26 justifyContent: 'center',
27 alignItems: 'center'
28 },
29
30 /* Styles applied to the container element if `scroll="body"`. */
31 scrollBody: {
32 overflowY: 'auto',
33 overflowX: 'hidden',
34 textAlign: 'center',
35 '&:after': {
36 content: '""',
37 display: 'inline-block',
38 verticalAlign: 'middle',
39 height: '100%',
40 width: '0'
41 }
42 },
43
44 /* Styles applied to the container element. */
45 container: {
46 height: '100%',
47 '@media print': {
48 height: 'auto'
49 },
50 // We disable the focus ring for mouse, touch and keyboard users.
51 outline: 0
52 },
53
54 /* Styles applied to the `Paper` component. */
55 paper: {
56 margin: 32,
57 position: 'relative',
58 overflowY: 'auto',
59 // Fix IE 11 issue, to remove at some point.
60 '@media print': {
61 overflowY: 'visible',
62 boxShadow: 'none'
63 }
64 },
65
66 /* Styles applied to the `Paper` component if `scroll="paper"`. */
67 paperScrollPaper: {
68 display: 'flex',
69 flexDirection: 'column',
70 maxHeight: 'calc(100% - 64px)'
71 },
72
73 /* Styles applied to the `Paper` component if `scroll="body"`. */
74 paperScrollBody: {
75 display: 'inline-block',
76 verticalAlign: 'middle',
77 textAlign: 'left' // 'initial' doesn't work on IE 11
78
79 },
80
81 /* Styles applied to the `Paper` component if `maxWidth=false`. */
82 paperWidthFalse: {
83 maxWidth: 'calc(100% - 64px)'
84 },
85
86 /* Styles applied to the `Paper` component if `maxWidth="xs"`. */
87 paperWidthXs: {
88 maxWidth: Math.max(theme.breakpoints.values.xs, 444),
89 '&$paperScrollBody': {
90 [theme.breakpoints.down(Math.max(theme.breakpoints.values.xs, 444) + 32 * 2)]: {
91 maxWidth: 'calc(100% - 64px)'
92 }
93 }
94 },
95
96 /* Styles applied to the `Paper` component if `maxWidth="sm"`. */
97 paperWidthSm: {
98 maxWidth: theme.breakpoints.values.sm,
99 '&$paperScrollBody': {
100 [theme.breakpoints.down(theme.breakpoints.values.sm + 32 * 2)]: {
101 maxWidth: 'calc(100% - 64px)'
102 }
103 }
104 },
105
106 /* Styles applied to the `Paper` component if `maxWidth="md"`. */
107 paperWidthMd: {
108 maxWidth: theme.breakpoints.values.md,
109 '&$paperScrollBody': {
110 [theme.breakpoints.down(theme.breakpoints.values.md + 32 * 2)]: {
111 maxWidth: 'calc(100% - 64px)'
112 }
113 }
114 },
115
116 /* Styles applied to the `Paper` component if `maxWidth="lg"`. */
117 paperWidthLg: {
118 maxWidth: theme.breakpoints.values.lg,
119 '&$paperScrollBody': {
120 [theme.breakpoints.down(theme.breakpoints.values.lg + 32 * 2)]: {
121 maxWidth: 'calc(100% - 64px)'
122 }
123 }
124 },
125
126 /* Styles applied to the `Paper` component if `maxWidth="xl"`. */
127 paperWidthXl: {
128 maxWidth: theme.breakpoints.values.xl,
129 '&$paperScrollBody': {
130 [theme.breakpoints.down(theme.breakpoints.values.xl + 32 * 2)]: {
131 maxWidth: 'calc(100% - 64px)'
132 }
133 }
134 },
135
136 /* Styles applied to the `Paper` component if `fullWidth={true}`. */
137 paperFullWidth: {
138 width: 'calc(100% - 64px)'
139 },
140
141 /* Styles applied to the `Paper` component if `fullScreen={true}`. */
142 paperFullScreen: {
143 margin: 0,
144 width: '100%',
145 maxWidth: '100%',
146 height: '100%',
147 maxHeight: 'none',
148 borderRadius: 0,
149 '&$paperScrollBody': {
150 margin: 0,
151 maxWidth: '100%'
152 }
153 }
154});
155const defaultTransitionDuration = {
156 enter: duration.enteringScreen,
157 exit: duration.leavingScreen
158};
159/**
160 * Dialogs are overlaid modal paper based components with a backdrop.
161 */
162
163const Dialog = /*#__PURE__*/React.forwardRef(function Dialog(props, ref) {
164 const {
165 BackdropProps,
166 children,
167 classes,
168 className,
169 disableBackdropClick = false,
170 disableEscapeKeyDown = false,
171 fullScreen = false,
172 fullWidth = false,
173 maxWidth = 'sm',
174 onBackdropClick,
175 onClose,
176 onEnter,
177 onEntered,
178 onEntering,
179 onEscapeKeyDown,
180 onExit,
181 onExited,
182 onExiting,
183 open,
184 PaperComponent = Paper,
185 PaperProps = {},
186 scroll = 'paper',
187 TransitionComponent = Fade,
188 transitionDuration = defaultTransitionDuration,
189 TransitionProps,
190 'aria-describedby': ariaDescribedby,
191 'aria-labelledby': ariaLabelledby
192 } = props,
193 other = _objectWithoutPropertiesLoose(props, ["BackdropProps", "children", "classes", "className", "disableBackdropClick", "disableEscapeKeyDown", "fullScreen", "fullWidth", "maxWidth", "onBackdropClick", "onClose", "onEnter", "onEntered", "onEntering", "onEscapeKeyDown", "onExit", "onExited", "onExiting", "open", "PaperComponent", "PaperProps", "scroll", "TransitionComponent", "transitionDuration", "TransitionProps", "aria-describedby", "aria-labelledby"]);
194
195 const mouseDownTarget = React.useRef();
196
197 const handleMouseDown = event => {
198 mouseDownTarget.current = event.target;
199 };
200
201 const handleBackdropClick = event => {
202 // Ignore the events not coming from the "backdrop"
203 // We don't want to close the dialog when clicking the dialog content.
204 if (event.target !== event.currentTarget) {
205 return;
206 } // Make sure the event starts and ends on the same DOM element.
207
208
209 if (event.target !== mouseDownTarget.current) {
210 return;
211 }
212
213 mouseDownTarget.current = null;
214
215 if (onBackdropClick) {
216 onBackdropClick(event);
217 }
218
219 if (!disableBackdropClick && onClose) {
220 onClose(event, 'backdropClick');
221 }
222 };
223
224 return /*#__PURE__*/React.createElement(Modal, _extends({
225 className: clsx(classes.root, className),
226 BackdropComponent: Backdrop,
227 BackdropProps: _extends({
228 transitionDuration
229 }, BackdropProps),
230 closeAfterTransition: true
231 }, disableBackdropClick ? {
232 disableBackdropClick
233 } : {}, {
234 disableEscapeKeyDown: disableEscapeKeyDown,
235 onEscapeKeyDown: onEscapeKeyDown,
236 onClose: onClose,
237 open: open,
238 ref: ref
239 }, other), /*#__PURE__*/React.createElement(TransitionComponent, _extends({
240 appear: true,
241 in: open,
242 timeout: transitionDuration,
243 onEnter: onEnter,
244 onEntering: onEntering,
245 onEntered: onEntered,
246 onExit: onExit,
247 onExiting: onExiting,
248 onExited: onExited,
249 role: "none presentation"
250 }, TransitionProps), /*#__PURE__*/React.createElement("div", {
251 className: clsx(classes.container, classes[`scroll${capitalize(scroll)}`]),
252 onMouseUp: handleBackdropClick,
253 onMouseDown: handleMouseDown
254 }, /*#__PURE__*/React.createElement(PaperComponent, _extends({
255 elevation: 24,
256 role: "dialog",
257 "aria-describedby": ariaDescribedby,
258 "aria-labelledby": ariaLabelledby
259 }, PaperProps, {
260 className: clsx(classes.paper, classes[`paperScroll${capitalize(scroll)}`], classes[`paperWidth${capitalize(String(maxWidth))}`], PaperProps.className, fullScreen && classes.paperFullScreen, fullWidth && classes.paperFullWidth)
261 }), children))));
262});
263process.env.NODE_ENV !== "production" ? Dialog.propTypes = {
264 // ----------------------------- Warning --------------------------------
265 // | These PropTypes are generated from the TypeScript type definitions |
266 // | To update them edit the d.ts file and run "yarn proptypes" |
267 // ----------------------------------------------------------------------
268
269 /**
270 * The id(s) of the element(s) that describe the dialog.
271 */
272 'aria-describedby': PropTypes.string,
273
274 /**
275 * The id(s) of the element(s) that label the dialog.
276 */
277 'aria-labelledby': PropTypes.string,
278
279 /**
280 * @ignore
281 */
282 BackdropProps: PropTypes.object,
283
284 /**
285 * Dialog children, usually the included sub-components.
286 */
287 children: PropTypes.node,
288
289 /**
290 * Override or extend the styles applied to the component.
291 * See [CSS API](#css) below for more details.
292 */
293 classes: PropTypes.object,
294
295 /**
296 * @ignore
297 */
298 className: PropTypes.string,
299
300 /**
301 * If `true`, clicking the backdrop will not fire the `onClose` callback.
302 * @deprecated Use the onClose prop with the `reason` argument to filter the `backdropClick` events.
303 */
304 disableBackdropClick: deprecatedPropType(PropTypes.bool, 'Use the onClose prop with the `reason` argument to filter the `backdropClick` events.'),
305
306 /**
307 * If `true`, hitting escape will not fire the `onClose` callback.
308 */
309 disableEscapeKeyDown: PropTypes.bool,
310
311 /**
312 * If `true`, the dialog will be full-screen
313 */
314 fullScreen: PropTypes.bool,
315
316 /**
317 * If `true`, the dialog stretches to `maxWidth`.
318 *
319 * Notice that the dialog width grow is limited by the default margin.
320 */
321 fullWidth: PropTypes.bool,
322
323 /**
324 * Determine the max-width of the dialog.
325 * The dialog width grows with the size of the screen.
326 * Set to `false` to disable `maxWidth`.
327 */
328 maxWidth: PropTypes.oneOf(['lg', 'md', 'sm', 'xl', 'xs', false]),
329
330 /**
331 * Callback fired when the backdrop is clicked.
332 * @deprecated Use the onClose prop with the `reason` argument to handle the `backdropClick` events.
333 */
334 onBackdropClick: deprecatedPropType(PropTypes.func, 'Use the onClose prop with the `reason` argument to handle the `backdropClick` events.'),
335
336 /**
337 * Callback fired when the component requests to be closed.
338 *
339 * @param {object} event The event source of the callback.
340 * @param {string} reason Can be: `"escapeKeyDown"`, `"backdropClick"`.
341 */
342 onClose: PropTypes.func,
343
344 /**
345 * Callback fired before the dialog enters.
346 * @deprecated Use the `TransitionProps` prop instead.
347 */
348 onEnter: deprecatedPropType(PropTypes.func, 'Use the `TransitionProps` prop instead.'),
349
350 /**
351 * Callback fired when the dialog has entered.
352 * @deprecated Use the `TransitionProps` prop instead.
353 */
354 onEntered: deprecatedPropType(PropTypes.func, 'Use the `TransitionProps` prop instead.'),
355
356 /**
357 * Callback fired when the dialog is entering.
358 * @deprecated Use the `TransitionProps` prop instead.
359 */
360 onEntering: deprecatedPropType(PropTypes.func, 'Use the `TransitionProps` prop instead.'),
361
362 /**
363 * Callback fired when the escape key is pressed,
364 * `disableKeyboard` is false and the modal is in focus.
365 * @deprecated Use the onClose prop with the `reason` argument to handle the `escapeKeyDown` events.
366 */
367 onEscapeKeyDown: deprecatedPropType(PropTypes.func, 'Use the onClose prop with the `reason` argument to handle the `escapeKeyDown` events.'),
368
369 /**
370 * Callback fired before the dialog exits.
371 * @deprecated Use the `TransitionProps` prop instead.
372 */
373 onExit: deprecatedPropType(PropTypes.func, 'Use the `TransitionProps` prop instead.'),
374
375 /**
376 * Callback fired when the dialog has exited.
377 * @deprecated Use the `TransitionProps` prop instead.
378 */
379 onExited: deprecatedPropType(PropTypes.func, 'Use the `TransitionProps` prop instead.'),
380
381 /**
382 * Callback fired when the dialog is exiting.
383 * @deprecated Use the `TransitionProps` prop instead.
384 */
385 onExiting: deprecatedPropType(PropTypes.func, 'Use the `TransitionProps` prop instead.'),
386
387 /**
388 * If `true`, the Dialog is open.
389 */
390 open: PropTypes.bool.isRequired,
391
392 /**
393 * The component used to render the body of the dialog.
394 */
395 PaperComponent: PropTypes.elementType,
396
397 /**
398 * Props applied to the [`Paper`](/api/paper/) element.
399 */
400 PaperProps: PropTypes.object,
401
402 /**
403 * Determine the container for scrolling the dialog.
404 */
405 scroll: PropTypes.oneOf(['body', 'paper']),
406
407 /**
408 * The component used for the transition.
409 * [Follow this guide](/components/transitions/#transitioncomponent-prop) to learn more about the requirements for this component.
410 */
411 TransitionComponent: PropTypes.elementType,
412
413 /**
414 * The duration for the transition, in milliseconds.
415 * You may specify a single timeout for all transitions, or individually with an object.
416 */
417 transitionDuration: PropTypes.oneOfType([PropTypes.number, PropTypes.shape({
418 appear: PropTypes.number,
419 enter: PropTypes.number,
420 exit: PropTypes.number
421 })]),
422
423 /**
424 * Props applied to the [`Transition`](http://reactcommunity.org/react-transition-group/transition#Transition-props) element.
425 */
426 TransitionProps: PropTypes.object
427} : void 0;
428export default withStyles(styles, {
429 name: 'MuiDialog'
430})(Dialog);
\No newline at end of file