사진과 같이 Viewport의 크기에 따라 컴포넌트의 크기를 변경하려면 어떻게 해야 할까? 단순히 컴포넌트의 크기만 변경하는 것이라면 CSS를 이용하는 것이 좋지만, SearchBar 컴포넌트의 크기에 맞춰 Modal 컴포넌트의 크기가 같이 달라져야 하므로 Styled-Components를 이용해 Modal 컴포넌트의 너비를 동적으로 바꿔줘야 함. 하지만, SearchBar와 Modal은 별개의 컴포넌트이기 때문에 Context API를 사용하는 등의 방법이 필요함. 1. Resize 이벤트 A. 크기 변경 Viewport에 따라 변경되는 SearchBar 컴포넌트의 너비가 State여야 하므로 DOM의 resize 이벤트를 이용해 SearchBar의 너비를 가져와야 함. resize 이벤트는 windo..
1. React에서 이미지를 불러오기 React에서 네트워크 요청으로 이미지를 받아 화면에 나타내고자 할 때, 아래처럼 src에 직접 링크를 넣어 불러오도록 할 수 있음. const Image = () => { return ( ); } 이미지 용량이 크지 않을 경우, 이 방법도 문제가 없지만 이미지의 용량이 커지면 아래 사진처럼 이미지가 로드될 때까지 사용자는 빈 화면이나 잘린 이미지만 보게 되어 바람직하지 않음. 이미지를 보여주는 컴포넌트가 App 컴포넌트 등 첫화면에 바로 보이는 컴포넌트라면 로딩 컴포넌트를 이용하는 방법이 있지만, Image 컴포넌트처럼 그것의 하위 컴포넌트라면 첫 화면에서 로딩, Image 컴포넌트를 렌더링하고 로딩하는 워터폴 문제가 발생함. 현재 Image 컴포넌트는 에 src ..
네트워크 요청을 처리하다 보면 이전 요청과 현재 요청 간에 경쟁 상태(Race Condition)가 발생해 예상치 못한 버그가 발생하기도 함. 예를 들어, 사용자가 A 요청을 보냈다가 A 요청에 대한 응답이 처리되기 전에 B 요청을 보내는 경우를 생각해볼 수 있음. 만약, B 요청에 대한 응답이 먼저 도착해 UI에 반영되고 나서 A 응답이 도착한다면 어떻게 될까? 앱에 이러한 경쟁 상태를 처리하는 로직이 없다면 A 응답으로 UI가 다시 교체되는 버그가 발생함. 이러한 문제를 해결하기 위한 방법이 있는데... 1. useEffect에서 변수 선언하기 useEffect() 내부에 didCancel이라는 변수를 하나 선언함. 이 변수는 네트워크 요청이 실행될 때마다 false로 초기화되고, 네트워크 응답이 도..
일반적으로 부모 컴포넌트의 State, Props가 변경되면 부모 컴포넌트의 State를 Props로 전달받든, 아니든 모든 자식 컴포넌트는 재렌더링됨. 하지만, children 속성을 사용하는 컴포넌트는 State 변경에 대해 다르게 작동함. function App() { const [state, setState] = useState(0); return ( setState(state + 1)}>App 업데이트 ); } function Parent({ children }) { const [state, setState] = useState(0); return ( setState(state + 1)}>Parent 업데이트 {children} ); }; App 컴포넌트는 자식 컴포넌트로 Parent, Chil..
1. React에서 canvas 사용하기 캔버스는 DOM을 조작해야 하므로 useRef(), useEffect()를 사용해야 함. 한편, 캔버스는 React에서 재렌더링이 되지 않아도 화면에 그림이 나타나므로 캔버스와 관련된 변수는 특별한 경우가 아닌 한 State로 관리할 필요가 없음. export default function Drawing() { const canvas = useRef(null); return ; } useRef()를 이용해 요소를 선택하고, canvas 객체에 요소가 제대로 담기는 시점(Drawing 컴포넌트 렌더링이 완료되는 시점 이후)에 컨텍스트를 생성할 수 있음. export default function Drawing() { const canvas = useRef(null)..
1. Context API # Context API를 이용하면 여러 컴포넌트에서 사용해야 하는 State를 한번에 Props로 내려줄 수 있음. 하지만, Context API를 사용하면 상위, 하위 컴포넌트가 더 밀접하게 결합하게 되어 컴포넌트의 재사용성을 훼손하게 되므로 단지 Props Drilling을 해결하고자 하는 게 목적이라면 컴포넌트 합성을 쓰는 것이 더 간단함. A. Context 생성 # // App.jsx import { createContext } from "react"; export const AppContext = createContext(null); B. Context 값 전달하기 const App = () => { return ( ); } 앞서 만들어준 AppContext 객체에..
React에서 Side Effect는 보통 useEffect() 내부에 넣어 처리하는데 useEffect()는 dependency로 지정한 State가 변경되고 렝더링까지 완료된 이후에 실행됨. 이러한 특성을 이용하면 어떠한 상호작용을 했을 때 알림으로 나타나는 Toast 알림을 쉽게 구현할 수 있음. 일정 시간 후에 토스트를 제거해야 하므로 setTimeout() 타이머를 사용해야 하는데, 타이머 API는 Side Effect이므로 useEffect()에서 처리해줘야 함. 1. Toast 생성 이벤트 핸들러 만들기 토스트는 상위, 하위 컴포넌트에서 상호작용이 발생했을 때 나타나야 하므로 최상위 컴포넌트 App에 두는 편이 좋음. App 컴포넌트에서 토스트를 담을 State를 만들고 토스트를 추가해주는 ..
JavaScript/React 2022. 8. 25. 09:16
사진과 같이 Viewport의 크기에 따라 컴포넌트의 크기를 변경하려면 어떻게 해야 할까? 단순히 컴포넌트의 크기만 변경하는 것이라면 CSS를 이용하는 것이 좋지만, SearchBar 컴포넌트의 크기에 맞춰 Modal 컴포넌트의 크기가 같이 달라져야 하므로 Styled-Components를 이용해 Modal 컴포넌트의 너비를 동적으로 바꿔줘야 함. 하지만, SearchBar와 Modal은 별개의 컴포넌트이기 때문에 Context API를 사용하는 등의 방법이 필요함. 1. Resize 이벤트 A. 크기 변경 Viewport에 따라 변경되는 SearchBar 컴포넌트의 너비가 State여야 하므로 DOM의 resize 이벤트를 이용해 SearchBar의 너비를 가져와야 함. resize 이벤트는 windo..
JavaScript/React 2022. 8. 13. 21:51
1. React에서 이미지를 불러오기 React에서 네트워크 요청으로 이미지를 받아 화면에 나타내고자 할 때, 아래처럼 src에 직접 링크를 넣어 불러오도록 할 수 있음. const Image = () => { return ( ); } 이미지 용량이 크지 않을 경우, 이 방법도 문제가 없지만 이미지의 용량이 커지면 아래 사진처럼 이미지가 로드될 때까지 사용자는 빈 화면이나 잘린 이미지만 보게 되어 바람직하지 않음. 이미지를 보여주는 컴포넌트가 App 컴포넌트 등 첫화면에 바로 보이는 컴포넌트라면 로딩 컴포넌트를 이용하는 방법이 있지만, Image 컴포넌트처럼 그것의 하위 컴포넌트라면 첫 화면에서 로딩, Image 컴포넌트를 렌더링하고 로딩하는 워터폴 문제가 발생함. 현재 Image 컴포넌트는 에 src ..
JavaScript/React 2022. 8. 13. 16:34
네트워크 요청을 처리하다 보면 이전 요청과 현재 요청 간에 경쟁 상태(Race Condition)가 발생해 예상치 못한 버그가 발생하기도 함. 예를 들어, 사용자가 A 요청을 보냈다가 A 요청에 대한 응답이 처리되기 전에 B 요청을 보내는 경우를 생각해볼 수 있음. 만약, B 요청에 대한 응답이 먼저 도착해 UI에 반영되고 나서 A 응답이 도착한다면 어떻게 될까? 앱에 이러한 경쟁 상태를 처리하는 로직이 없다면 A 응답으로 UI가 다시 교체되는 버그가 발생함. 이러한 문제를 해결하기 위한 방법이 있는데... 1. useEffect에서 변수 선언하기 useEffect() 내부에 didCancel이라는 변수를 하나 선언함. 이 변수는 네트워크 요청이 실행될 때마다 false로 초기화되고, 네트워크 응답이 도..
JavaScript/React 2022. 8. 9. 17:35
1. Referential Equality React에서는 Referential Equality Check(Object.is())를 이용해 State, Props 변경을 감지함. State가 원시 자료형이면 State를 덮어씌워 변경해도 문제가 없지만, 배열/객체 등 참조 자료형이라면 해당 속성의 주소값이 바뀌지 않기 때문에 React에서는 State, Props가 변경되지 않았다고 판단할 수 있음. const obj1 = { p1: { innerP: 0 }, p2: 1 }; const obj2 = { ...obj1 }; const obj3 = { p1: { innerP: 0 }, p2: 1 }; console.log(Object.is(obj2, obj1)); // false: 두 객체 다르므로 렌더링 ..
JavaScript/React 2022. 8. 7. 16:43
일반적으로 부모 컴포넌트의 State, Props가 변경되면 부모 컴포넌트의 State를 Props로 전달받든, 아니든 모든 자식 컴포넌트는 재렌더링됨. 하지만, children 속성을 사용하는 컴포넌트는 State 변경에 대해 다르게 작동함. function App() { const [state, setState] = useState(0); return ( setState(state + 1)}>App 업데이트 ); } function Parent({ children }) { const [state, setState] = useState(0); return ( setState(state + 1)}>Parent 업데이트 {children} ); }; App 컴포넌트는 자식 컴포넌트로 Parent, Chil..
JavaScript/React 2022. 7. 31. 19:29
const Toast = ({ text, dismissTime }) => { // dismissRime: Toast 컴포넌트가 언마운트되는 시간 const [isFading, setIsFading] = useState(false); // 클래스 부여에 이용할 State useEffect(() => { let mounted = true; setTimeout(() => { if (mounted) { setIsFading(true); } }, dismissTime - 500) // 애니메이션 시간만큼 빼서 setTimeout() 실행 return () => { mounted = false } }, []) // 'fade-out' 클래스가 있으면 사라지는 애니메이션 실행 return ( {text} ) } To..
JavaScript/React 2022. 7. 22. 21:18
1. React에서 canvas 사용하기 캔버스는 DOM을 조작해야 하므로 useRef(), useEffect()를 사용해야 함. 한편, 캔버스는 React에서 재렌더링이 되지 않아도 화면에 그림이 나타나므로 캔버스와 관련된 변수는 특별한 경우가 아닌 한 State로 관리할 필요가 없음. export default function Drawing() { const canvas = useRef(null); return ; } useRef()를 이용해 요소를 선택하고, canvas 객체에 요소가 제대로 담기는 시점(Drawing 컴포넌트 렌더링이 완료되는 시점 이후)에 컨텍스트를 생성할 수 있음. export default function Drawing() { const canvas = useRef(null)..
JavaScript/React 2022. 7. 20. 22:30
1. Context API # Context API를 이용하면 여러 컴포넌트에서 사용해야 하는 State를 한번에 Props로 내려줄 수 있음. 하지만, Context API를 사용하면 상위, 하위 컴포넌트가 더 밀접하게 결합하게 되어 컴포넌트의 재사용성을 훼손하게 되므로 단지 Props Drilling을 해결하고자 하는 게 목적이라면 컴포넌트 합성을 쓰는 것이 더 간단함. A. Context 생성 # // App.jsx import { createContext } from "react"; export const AppContext = createContext(null); B. Context 값 전달하기 const App = () => { return ( ); } 앞서 만들어준 AppContext 객체에..
JavaScript/React 2022. 7. 9. 20:40
1. Props를 State에 바로 할당할 때는 주의해야 함 # A. 예시1 function Task(props) { const [dueDate, setDueDate] = useState(props.dueDate); // Props를 State의 초기값으로 할당하고 있음 const [title, setTitle] = useState(props.title); // Props를 State의 초기값으로 할당하고 있음 const onChange = (e) => { /* ... */ }; return ( /* ... */ ); } 컴포넌트가 TaskList > TaskListSection > Task 구조로 되어있을 때, Task에서 할일 만료일 dueDate를 변경하면 onChange 이벤트 핸들러에 의해 St..
JavaScript/React 2022. 7. 9. 16:24
React에서 Side Effect는 보통 useEffect() 내부에 넣어 처리하는데 useEffect()는 dependency로 지정한 State가 변경되고 렝더링까지 완료된 이후에 실행됨. 이러한 특성을 이용하면 어떠한 상호작용을 했을 때 알림으로 나타나는 Toast 알림을 쉽게 구현할 수 있음. 일정 시간 후에 토스트를 제거해야 하므로 setTimeout() 타이머를 사용해야 하는데, 타이머 API는 Side Effect이므로 useEffect()에서 처리해줘야 함. 1. Toast 생성 이벤트 핸들러 만들기 토스트는 상위, 하위 컴포넌트에서 상호작용이 발생했을 때 나타나야 하므로 최상위 컴포넌트 App에 두는 편이 좋음. App 컴포넌트에서 토스트를 담을 State를 만들고 토스트를 추가해주는 ..