UNPKG

@appbuckets/react-ui

Version:
148 lines (145 loc) 4.12 kB
import { __read } from 'tslib'; import * as React from 'react'; import { useWindowResize } from './useWindowResize.js'; /* -------- * Internal Useful * -------- */ function computeDimension(initial, subtracts, minimum, maximum) { /** Subtract */ var dimension = initial - (subtracts || 0); if (dimension < (minimum || 0)) { return minimum || 0; } if (typeof maximum === 'number' && dimension > maximum) { return maximum; } return dimension; } /* -------- * Hook Definition * -------- */ function useElementSize(config) { var disabled = config.disabled, fixedHeight = config.fixedHeight, fixedWidth = config.fixedWidth, maximumHeight = config.maximumHeight, maximumWidth = config.maximumWidth, minimumHeight = config.minimumHeight, minimumWidth = config.minimumWidth, subtractToHeight = config.subtractToHeight, subtractToWidth = config.subtractToWidth, useDetectorHeightOnly = config.useDetectorHeightOnly, useDetectorWidthOnly = config.useDetectorWidthOnly; // ---- // Create the Unique DetectorID // ---- // const [ widthDetectorID ] = React.useState(`__rx-width-detector-${Math.round(Math.random() * 1000)}`); var widthDetectorID = React.useRef(undefined); React.useEffect(function () { widthDetectorID.current = Math.random().toString(36).slice(2); }, []); // ---- // Internal State // ---- var _a = __read( React.useState({ width: fixedWidth || 0, height: fixedHeight || 0, }), 2 ), size = _a[0], setElementSize = _a[1]; // ---- // Initialize the detector ref // ---- var elementRef = React.useRef(null); // ---- // Memoize the Handle to call On Window Resize Event // ---- var handleWindowResize = React.useCallback( function () { /** If no ref, or component is not mount, return */ if (!elementRef.current || !elementRef.current.parentNode) { return; } var detector = elementRef.current; /** Get current window height and width */ var windowHeight = window.innerHeight, windowWidth = window.innerWidth; /** Get the element top and left position */ var _a = detector.getBoundingClientRect(), detectorTopPosition = _a.top, detectorLeftPosition = _a.left; /** Get new Sizing */ var nextHeight = typeof fixedHeight !== 'number' ? computeDimension( useDetectorHeightOnly ? detector.clientHeight : windowHeight - detectorTopPosition, subtractToHeight, minimumHeight, maximumHeight ) : fixedHeight; var nextWidth = typeof fixedWidth !== 'number' ? computeDimension( useDetectorWidthOnly ? detector.clientWidth : windowWidth - detectorLeftPosition, subtractToWidth, minimumWidth, maximumWidth ) : fixedWidth; /** Check if state must be updated */ if (nextHeight !== size.height || nextWidth !== size.width) { setElementSize({ height: nextHeight, width: nextWidth, }); } }, [ useDetectorHeightOnly, useDetectorWidthOnly, fixedHeight, fixedWidth, maximumHeight, maximumWidth, minimumHeight, minimumWidth, size.height, size.width, subtractToHeight, subtractToWidth, ] ); // ---- // Memoize the Width Detector Element // ---- var widthDetector = React.useMemo(function () { return React.createElement('div', { ref: elementRef, id: widthDetectorID.current, style: { visibility: 'hidden', opacity: 0, }, }); }, []); // ---- // Active the Window Resize Hook // ---- useWindowResize({ disabled: disabled || !elementRef.current || !!(fixedWidth && fixedHeight), onResize: handleWindowResize, }); // ---- // Return Data // ---- return [widthDetector, size]; } export { useElementSize };