mirror of https://git.lenooby09.tech/LeNooby09/social-app.git
at ruby-v 2.5 kB view raw
1import { 2 createContext, 3 useCallback, 4 useContext, 5 useEffect, 6 useMemo, 7 useRef, 8} from 'react' 9import { 10 KeyboardProvider, 11 useKeyboardController, 12} from 'react-native-keyboard-controller' 13import {useFocusEffect} from '@react-navigation/native' 14 15import {IS_DEV} from '#/env' 16 17const KeyboardControllerRefCountContext = createContext<{ 18 incrementRefCount: () => void 19 decrementRefCount: () => void 20}>({ 21 incrementRefCount: () => {}, 22 decrementRefCount: () => {}, 23}) 24 25export function KeyboardControllerProvider({ 26 children, 27}: { 28 children: React.ReactNode 29}) { 30 return ( 31 <KeyboardProvider 32 enabled={false} 33 // I don't think this is necessary, but Chesterton's fence and all that -sfn 34 statusBarTranslucent={true}> 35 <KeyboardControllerProviderInner> 36 {children} 37 </KeyboardControllerProviderInner> 38 </KeyboardProvider> 39 ) 40} 41 42function KeyboardControllerProviderInner({ 43 children, 44}: { 45 children: React.ReactNode 46}) { 47 const {setEnabled} = useKeyboardController() 48 const refCount = useRef(0) 49 50 const value = useMemo( 51 () => ({ 52 incrementRefCount: () => { 53 refCount.current++ 54 setEnabled(refCount.current > 0) 55 }, 56 decrementRefCount: () => { 57 refCount.current-- 58 setEnabled(refCount.current > 0) 59 60 if (IS_DEV && refCount.current < 0) { 61 console.error('KeyboardController ref count < 0') 62 } 63 }, 64 }), 65 [setEnabled], 66 ) 67 68 return ( 69 <KeyboardControllerRefCountContext.Provider value={value}> 70 {children} 71 </KeyboardControllerRefCountContext.Provider> 72 ) 73} 74 75export function useEnableKeyboardController(shouldEnable: boolean) { 76 const {incrementRefCount, decrementRefCount} = useContext( 77 KeyboardControllerRefCountContext, 78 ) 79 80 useEffect(() => { 81 if (!shouldEnable) { 82 return 83 } 84 incrementRefCount() 85 return () => { 86 decrementRefCount() 87 } 88 }, [shouldEnable, incrementRefCount, decrementRefCount]) 89} 90 91/** 92 * Like `useEnableKeyboardController`, but using `useFocusEffect` 93 */ 94export function useEnableKeyboardControllerScreen(shouldEnable: boolean) { 95 const {incrementRefCount, decrementRefCount} = useContext( 96 KeyboardControllerRefCountContext, 97 ) 98 99 useFocusEffect( 100 useCallback(() => { 101 if (!shouldEnable) { 102 return 103 } 104 incrementRefCount() 105 return () => { 106 decrementRefCount() 107 } 108 }, [shouldEnable, incrementRefCount, decrementRefCount]), 109 ) 110}