import React , { useEffect , useRef , useState , useMemo } from 'react' ; import { Dimensions , ScaledSize } from 'react-native' ; import { getBreakpointIndex } from '../css/get-breakpoint-index' ; import { useDripsyTheme } from '../use-dripsy-theme' ; import { BreakpointIndexContext } from './breakpoint-context' ; export const useBreakpoints = ( ) => { const dripsy = useDripsyTheme ( ) ; const breakpoints = dripsy ?. theme ?. breakpoints as ( number | string ) [ ] | undefined ; if ( breakpoints && typeof __DEV__ !== 'undefined' && __DEV__ ) { if ( ! Array . isArray ( breakpoints ) ) { const arrayError = '[dripsy] theme.breakpoints must be an array. Or, you can leave it blank. However, you used \n' + JSON . stringify ( breakpoints ) + '\n Please turn this into an array, or remove the "breakpoints" field from your theme.' ; throw new Error ( arrayError ) ; } } return useMemo ( ( ) => { return ( breakpoints || defaultBreakpoints ) . map ( ( breakpoint ) => { if ( typeof breakpoint === 'string' ) { if ( breakpoint . endsWith ( 'px' ) ) { return Number ( breakpoint . replace ( 'px' , '' ) ) ; } } if ( typeof breakpoint !== 'number' ) { console . error ( '[dripsy] Invalid breakpoints passed to theme.breakpoints. Expected an array of numbers, or strings ending with "px", but got this: \n' , JSON . stringify ( breakpoints ) , '\nPlease turn these into numbers, or remove the breakpoints array from your theme.' ) ; } return Number ( breakpoint ) ; } ) ; } , [ breakpoints ] ) ; } ; export const defaultBreakpoints = [ 576 , 768 , 992 , 1200 ] ; const useCreateBreakpointIndex = ( ) => { const breakpoints = useBreakpoints ( ) ; const [ index , setIndex ] = useState ( ( ) => { return getBreakpointIndex ( { width : Dimensions . get ( 'window' ) . width , breakpoints } ) ; } ) ; const indexRef = useRef ( index ) ; useEffect ( ( ) => { indexRef . current = index ; } , [ index ] ) ; useEffect ( ( ) => { const onChange = ( { window : { width } , } ) => { const breakpointIndex = getBreakpointIndex ( { width , breakpoints } ) ; if ( breakpointIndex !== indexRef . current ) { setIndex ( breakpointIndex ) ; } } ; const unsubscribe = Dimensions . addEventListener ( 'change' , onChange ) as undefined | { remove : ( ) => void ; } ; onChange ( { window : Dimensions . get ( 'window' ) , screen : Dimensions . get ( 'screen' ) } ) ; return ( ) => { if ( ! unsubscribe ?. remove ) { Dimensions . removeEventListener ( 'change' , onChange ) ; } else { unsubscribe . remove ( ) ; } } ; } , [ breakpoints ] ) ; return index ; } ; export function BreakpointIndexProvider ( { children , } ) { const breakpointIndex = useCreateBreakpointIndex ( ) ; return ( < BreakpointIndexContext . Provider value = { breakpointIndex } > { children } < /BreakpointIndexContext.Provider>); }