| 1 | "use strict";
|
|---|
| 2 |
|
|---|
| 3 | Object.defineProperty(exports, "__esModule", {
|
|---|
| 4 | value: true
|
|---|
| 5 | });
|
|---|
| 6 | exports.ZIndexLayer = ZIndexLayer;
|
|---|
| 7 | var _react = require("react");
|
|---|
| 8 | var _reactDom = require("react-dom");
|
|---|
| 9 | var _DataUtils = require("../util/DataUtils");
|
|---|
| 10 | var _hooks = require("../state/hooks");
|
|---|
| 11 | var _zIndexSelectors = require("./zIndexSelectors");
|
|---|
| 12 | var _zIndexSlice = require("../state/zIndexSlice");
|
|---|
| 13 | var _chartLayoutContext = require("../context/chartLayoutContext");
|
|---|
| 14 | var _PanoramaContext = require("../context/PanoramaContext");
|
|---|
| 15 | /**
|
|---|
| 16 | * @since 3.4
|
|---|
| 17 | */
|
|---|
| 18 |
|
|---|
| 19 | /**
|
|---|
| 20 | * A layer that renders its children into a portal corresponding to the given zIndex.
|
|---|
| 21 | * We can't use regular CSS `z-index` because SVG does not support it.
|
|---|
| 22 | * So instead, we create separate DOM nodes for each zIndex layer
|
|---|
| 23 | * and render the children into the corresponding DOM node using React portals.
|
|---|
| 24 | *
|
|---|
| 25 | * This component must be used inside a Chart component.
|
|---|
| 26 | *
|
|---|
| 27 | * @param zIndex numeric zIndex value, higher values are rendered on top of lower values
|
|---|
| 28 | * @param children the content to render inside this zIndex layer
|
|---|
| 29 | *
|
|---|
| 30 | * @since 3.4
|
|---|
| 31 | */
|
|---|
| 32 | function ZIndexLayer(_ref) {
|
|---|
| 33 | var {
|
|---|
| 34 | zIndex,
|
|---|
| 35 | children
|
|---|
| 36 | } = _ref;
|
|---|
| 37 | /*
|
|---|
| 38 | * If we are outside of chart, then we can't rely on the zIndex portal state,
|
|---|
| 39 | * so we just render normally.
|
|---|
| 40 | */
|
|---|
| 41 | var isInChartContext = (0, _chartLayoutContext.useIsInChartContext)();
|
|---|
| 42 | /*
|
|---|
| 43 | * If zIndex is undefined then we render normally without portals.
|
|---|
| 44 | * Also, if zIndex is 0, we render normally without portals,
|
|---|
| 45 | * because 0 is the default layer that does not need a portal.
|
|---|
| 46 | */
|
|---|
| 47 | var shouldRenderInPortal = isInChartContext && zIndex !== undefined && zIndex !== 0;
|
|---|
| 48 | var isPanorama = (0, _PanoramaContext.useIsPanorama)();
|
|---|
| 49 | var dispatch = (0, _hooks.useAppDispatch)();
|
|---|
| 50 | (0, _react.useLayoutEffect)(() => {
|
|---|
| 51 | if (!shouldRenderInPortal) {
|
|---|
| 52 | // Nothing to do. We have to call the hook because of the rules of hooks.
|
|---|
| 53 | return _DataUtils.noop;
|
|---|
| 54 | }
|
|---|
| 55 | /*
|
|---|
| 56 | * Because zIndexes are dynamic (meaning, we're not working with a predefined set of layers,
|
|---|
| 57 | * but we allow users to define any zIndex at any time), we need to register
|
|---|
| 58 | * the requested zIndex in the global store. This way, the ZIndexPortals component
|
|---|
| 59 | * can render the corresponding portals and only the requested ones.
|
|---|
| 60 | */
|
|---|
| 61 | dispatch((0, _zIndexSlice.registerZIndexPortal)({
|
|---|
| 62 | zIndex
|
|---|
| 63 | }));
|
|---|
| 64 | return () => {
|
|---|
| 65 | dispatch((0, _zIndexSlice.unregisterZIndexPortal)({
|
|---|
| 66 | zIndex
|
|---|
| 67 | }));
|
|---|
| 68 | };
|
|---|
| 69 | }, [dispatch, zIndex, shouldRenderInPortal]);
|
|---|
| 70 | var portalElement = (0, _hooks.useAppSelector)(state => (0, _zIndexSelectors.selectZIndexPortalElement)(state, zIndex, isPanorama));
|
|---|
| 71 | if (!shouldRenderInPortal) {
|
|---|
| 72 | // If no zIndex is provided or zIndex is 0, render normally without portals
|
|---|
| 73 | return children;
|
|---|
| 74 | }
|
|---|
| 75 | if (!portalElement) {
|
|---|
| 76 | /*
|
|---|
| 77 | * If we don't have a portal element yet, this means that the registration
|
|---|
| 78 | * has not been processed yet by the ZIndexPortals component.
|
|---|
| 79 | * So here we render null and wait for the next render cycle.
|
|---|
| 80 | */
|
|---|
| 81 | return null;
|
|---|
| 82 | }
|
|---|
| 83 | return /*#__PURE__*/(0, _reactDom.createPortal)(children, portalElement);
|
|---|
| 84 | } |
|---|