📌 Higher Order Component(HOC)
<컴포넌트>를 인자로 받아 <새로운 컴포넌트>를 리턴하는 함수
- 컴포넌트 안에 있는 로직을 다시 재활용할 수 있는 고급 기술이다.
- React API의 한 파트가 아니다.
- 리액트 컴포넌트를 상속받거나 재활용하는 방식이 아니라 조합 방식으로 하는 본성으로부터 야기된 패턴이다.
HOC = function(컴포넌트) {return 새로운 컴포넌트;}
withRouter()
보통 with가 붙은 함수가 HOC인 경우가 많다.
고차 컴포넌트 – React
A JavaScript library for building user interfaces
ko.reactjs.org
withLoading.jsx
import React, { useState, useEffect } from "react";
// HOC 함수
export default function withLoading(Component) {
const WidthLoadingComponent = (props) => {
const [loading, setLoading] = useState(true);
useEffect(() => {
const timer = setTimeout(() => setLoading(false), 3000);
return () => clearTimeout(timer);
}, []);
return loading ? <p>Loading...</p> : <Component {...props} />;
};
return WidthLoadingComponent;
}
Button.jsx
import React from "react";
import withLoading from "./withLoading.jsx";
function Button() {
return <button>Button</button>;
}
export default withLoading(Button);
Input.jsx
import React from "react";
import withLoading from "./withLoading";
function Input() {
return <input defaultValue="Input" />;
}
export default withLoading(Input);
📌 Controlled Component, Uncontrolled Component
엘리먼트의 '상태'를 누가 관리하느냐에 따라 다르다.
✅ 제어 컴포넌트 (Controlled Component)
엘리먼트를 가지고 있는 컴포넌트가 상태 관리
<input value={someValue} onChange={handleChange} />
제어된 입력은 현재값을 prop, state 로 받고 해당 값을 변경하기 위한 콜백을 받는다. 이는 좀 더 리액트스러운 방식이라고 말할 수 있다. 일반적으로 제어 컴포넌트는 입력을 렌더링하는 컴포넌트에서 해당 상태를 저장한다. 물론 컴포넌트의 상태일 수 도 있고 Redux 와 같은 별도의 상태 저장소에 있을 수도 있다. 입력값을 변경할 때마다 리렌더링이 일어나게 된다. 이러한 특징 때문에 값을 명시적으로 요청할 필요가 없이 입력 상태값이 항상 최신의 값을 갖게 된다. 즉, 데이터(상태)와 UI (입력) 가 항상 동기화 된다.
import React, { FormEvent, useState } from "react";
function App() {
const [value, setValue] = useState<string>('');
const [result, setResult] = useState<string>('');
const handleNameChange = (e: React.ChangeEvent<HTMLInputElement>) => {
setValue(e.target.value);
}
const handleSubmit = (e: FormEvent<HTMLFormElement>) => {
e.preventDefault();
setResult(value);
}
return (
<form onSubmit={handleSubmit}>
<input type="text" value={value} onChange={handleNameChange} />
<input type="submit" />
<p>{result}</p>
</form>
);
}
export default App;
✅ 비제어 컴포넌트 (Uncontrolled Component)
엘리먼트의 상태를 관리하지 않고, 엘리먼트의 참조만 컴포넌트가 소유
비제어된 입력은 기존 HTML 폼 input과 동일하다.
const Form = () => {
return (
<div>
<input type="text" />
</div>
)
}
But 리액트에서는 지양하는 방식이다. 리액트는 Virtual DOM을 쓰고 있고, jsx로 react element를 만들어내고 있기 때문에 직접 가져와서 real DOM에 변조를 가하거나, 값을 읽어 들이는 것을 선호하지 않는다. 단방향으로 게속 render 되는 상태를 깰 수 있다. 그래서 나온 reference 일종의 저장 장치가 나왔고, 사용자가 입력한 것을 기억하고, 아래의 예시와 같이 ref 를 사용하여 값을 얻을 수 있다.
import React, { FormEvent, useRef, useState } from "react";
function App() {
const inputRef = useRef<HTMLInputElement>(null);
const [result, setResult] = useState('');
const handleSubmit = (e: FormEvent<HTMLFormElement>) => {
e.preventDefault();
inputRef.current && setResult(inputRef.current.value);
}
return (
<form onSubmit={handleSubmit}>
<input type="text" ref={inputRef} />
<input type="submit" />
<p>{result}</p>
</form>
);
}
export default App;
일반적으로 리액트에서는 제어 컴포넌트 (Controlled Component)로 입력을 제어하는 것을 권하지만 react-hook-form 은 비제어 컴포넌트(Uncontrolled Component)가 불필요한 렌더링을 하지 않기 때문에 성능상 우위를 점한다는 점에서 이 방법을 사용한다.
비제어 컴포넌트 – React
A JavaScript library for building user interfaces
ko.reactjs.org
'🍞 Front-End > React' 카테고리의 다른 글
[React] 컴포넌트 간 통신 Context API (0) | 2022.09.13 |
---|---|
[React] Hooks & Content (0) | 2022.09.13 |
[React] Styled Component (0) | 2022.09.01 |
[React] SPA와 react-router-dom v6 되면서 바뀐점 (0) | 2022.09.01 |
[React] Component Lifecycle (v16.3) (0) | 2022.09.01 |