TypeScript를 사용하여 React Native에서 FunctionComponent와 함께 forwardRef를 사용하는 방법
많은 문서와 예제 forwardRef를 살펴 봤지만 React Native에서 TypeScript로 기능적 구성 요소 를 사용하는 방법을 여전히 이해하지 못하는 것 같습니다 . 아래는 MyCustomComponentref를 생성하여 부모로부터 호출하려는 사용자 지정 함수로를 생성하는 예입니다. 그러나 ref가 잘못 정의되어 null있고 함수가 존재하지 않는다는 오류 메시지가 분명히 나타납니다. forwardRefReact Native에서 올바르게 사용하는 방법을 이해하도록 도와주세요 . 미리 감사드립니다!
interface MyCustomComponentProps {
title: string
}
const MyCustomComponent: React.FunctionComponent<MyCustomComponentProps> = React.forwardRef((props, ref) => {
const coolAlert = () => {
Alert.alert('Hey!', 'This was called from MyCustomComponent')
}
return (
<View>
<Text>{props.title}</Text>
</View>
)
})
export default function App () {
const MyCustomComponentRef = useRef()
return (
<SafeAreaView>
<MyCustomComponent ref={MyCustomComponentRef} title='Hello World' />
<TouchableOpacity
onPress={() => {
MyCustomComponentRef.coolAlert()
}}>
<Text>Click Me</Text>
</TouchableOpacity>
</SafeAreaView>
)
}
답변
참조 전달
Ref는 여러 가지 방법으로 처리 할 수 있고 사람들이 ref 객체 ( React.MutableRefObject또는 React.RefObject)와 .currentref 객체 의 속성에 저장된 ref 값 사이의 차이를 인식하지 못하기 때문에 매우 혼란 스러울 수 있습니다 . 여기에서 누락되거나 잘못된 typescript 유형과 함께 실수를 저질렀습니다.
useRef<T>T값이 저장 될 값의 유형을 알려주 는 일반적인 후크 입니다. 우리 App는 coolAlert메소드를 사용하여 무언가를 저장할 것이라고 말할 필요가 있습니다. 실제로 우리는 나중에 ref가 불변해야한다는 것을 알게 될 것이므로 createRef<T>대신 사용할 것입니다.
interface MyRef {
coolAlert(): void;
}
const MyCustomComponentRef = createRef<MyRef>();
를 호출 할 때 onPressref 객체의 현재 값에 액세스해야합니다. 제네릭을에 추가함으로써 createReftypescript는이 값이 MyRef또는 중 하나임을 이미 알고 있습니다 undefined. coolAlert선택적 연결 ?.연산자로 호출 할 수 있습니다 .
onPress={() => MyCustomComponentRef.current?.coolAlert()}
이제 우리는 MyCustomComponent. React.FunctionComponent<MyCustomComponentProps>함수 구성 요소에는 필요한 참조 전달에 대한 지식이 없기 때문에 유형을 할당하여 오류가 발생했습니다 .
function forwardRef<T, P = {}>(Component: RefForwardingComponent<T, P>): ForwardRefExoticComponent<PropsWithoutRef<P> & RefAttributes<T>>;
의 유형은 MyCustomComponent.NET의 복잡한 반환 유형이어야합니다 forwardRef. 그러나 우리는 그 유형에게 자신을 할당 할 필요가 없습니다, 우리는 단지 제네릭을 통과해야 T하고 P받는 forwardRef함수 호출. T심판 P의 유형이고 소품의 유형입니다.
const MyCustomComponent = React.forwardRef<MyRef, MyCustomComponentProps>(...
그래서 우리 는 모든 타입 스크립트 오류를 제거했습니다 ! 예이! 단 ... 잠깐만 요. 실제로 아무것도 하지 않습니다 . 그 모든 것이 여전히 작동하지 않습니다. 나는 심판이 싫어. 심판이 나쁘다.
Ref 사용
이제 전달 된 참조에 MyCustomComponent액세스 할 수 있고 DOM 구성 요소에 연결할 수있는에 참조를 전달했습니다. 그러나 우리는 그것이 DOM 요소에 연결되는 것을 원하지 않고 MyCustomComponent. 하지만 우리는 그렇게 할 수 없습니다.
기본적으로 함수 구성 요소에는 인스턴스가 없기 때문에 ref 속성을 사용할 수 없습니다. [docs]
우리는 useImperativeHandle해킹 솔루션처럼 느껴지는 훅을 사용해야 하며 심지어 문서에서도 "이러지 마세요"라고 말합니다. 네, 심판이 싫어요.
useImperativeHandle은 ref를 사용할 때 부모 구성 요소에 노출되는 인스턴스 값을 사용자 지정합니다. 항상 그렇듯이 대부분의 경우 ref를 사용하는 명령형 코드는 피해야합니다. useImperativeHandle은 forwardRef와 함께 사용해야합니다. [문서]
우리는 우리의 노출이 coolAlert를 통해 방법을 useImperativeHandle.
useImperativeHandle(ref , () => ({coolAlert}));
그리고 이제 실제로 작동합니다 .