컴포넌트
- React 컴포넌트 이름은 항상 대문자로 시작해야 하고 HTML 태그는 소문자로 시작해야 합니다.
- export default 키워드는 파일의 주요 컴포넌트를 지정합니다
- <div>...</div> 또는 빈 <>...</> 래퍼와 같이 하나의 공유 부모로 감싸야 합니다.
- <br />과 같은 태그를 닫아야 합니다.
데이터 표시하기
- 중괄호를 사용하면 코드에서 일부 변수를 삽입하여 사용자에게 표시할 수 있도록 JavaScript로 “이스케이프”할 수 있습니다.
return (
<h1>
{user.name}
</h1>
);
return (
<img
className="avatar"
src={user.imageUrl}
/>
);
- JSX 중괄호 안에 문자열 연결과 같이 더 복잡한 표현식을 넣을 수도 있습니다:
- style={{}}은 특별한 구문이 아니라 style={ } JSX 중괄호 안에 있는 일반 {} 객체입니다.
조건부 렌더링
- if문을 사용할 수 있다.
let content;
if (isLoggedIn) {
content = <AdminPanel />;
} else {
content = <LoginForm />;
}
return (
<div>
{content}
</div>
);
- 조건부 ? 연산자를 사용할 수 있다.
<div>
{isLoggedIn ? (
<AdminPanel />
) : (
<LoginForm />
)}
</div>
- else 분기가 필요하지 않은 경우 더 짧은 논리 && 구문을 사용할 수 있다.
<div>
{isLoggedIn && <AdminPanel />}
</div>
목록 렌더링
- 컴포넌트 내에서 map() 함수를 사용하여 배열을 반환합니다.
- 중복되는 태그 안에는 key 속성이 존재하는데, 목록의 각 항목에 대해, 형제 항목 중에서 해당 항목을 고유하게 식별하는 문자열 또는 숫자를 전달해야 합니다.
- 보통 키는 데이터베이스 ID와 같은 데이터에서 가져와야 합니다.
- React는 나중에 항목을 삽입, 삭제 또는 재정렬할 때 어떤 일이 일어났는지 이해하기 위해 키를 사용합니다.
const products = [
{ title: 'Cabbage', isFruit: false, id: 1 },
{ title: 'Garlic', isFruit: false, id: 2 },
{ title: 'Apple', isFruit: true, id: 3 },
];
export default function ShoppingList() {
const listItems = products.map(product =>
<li
key={product.id}
style={{
color: product.isFruit ? 'magenta' : 'darkgreen'
}}
>
{product.title}
</li>
);
return (
<ul>{listItems}</ul>
);
}
이벤트에 응답하기
- onClick={handleClick}의 끝에 괄호가 없다.
function MyButton() {
function handleClick() {
alert('You clicked me!');
}
return (
<button onClick={handleClick}>
Click me
</button>
);
}
화면 업데이트 하기
- 동일한 컴포넌트를 여러 번 렌더링하면 각각 고유한 state를 갖게 됩니다
훅 사용하기
- use로 시작하는 함수를 *훅(Hook)*이라고 합니다.
- 컴포넌트(또는 다른 훅)의 최상위 레벨에서만 훅을 호출할 수 있습니다.
컴포넌트 간 데이터 공유하기
- 데이터 공유가 이루어지는 최상단 컴포넌트를 제작하고, 최상단 컴포넌트에서 하위 컴포넌트로 공유 클릭 핸들러와 함꼐 state를 전달한다. 이를 state 끌어올리기라고 말할 수 있습니다.
export default function MyApp() {
const [count, setCount] = useState(0);
function handleClick() {
setCount(count + 1);
}
return (
<div>
<h1>Counters that update together</h1>
<MyButton count={count} onClick={handleClick} />
<MyButton count={count} onClick={handleClick} />
</div>
);
}
mockup으로 시작하기
UI를 컴포넌트 계층 구조로 나누기
React로 정적인 UI 만들기
- 정적 버전을 먼저 만든 다음 상호작용을 별도로 추가하는 것이 더 쉬운 경우가 많습니다
- 데이터 모델을 렌더링하는 앱의 정적 버전을 만들기 위해서는 다른 컴포넌트를 재사용하는 components를 만들고 props를 사용하여 데이터를 전달해야 합니다.
- 단방향 데이터 흐름이란? 데이터가 최상위 컴포넌트에서 트리 하단에 있는 컴포넌트로 흘러내리는 것이다.
function ProductCategoryRow({ category }) {
return (
<tr>
<th colSpan="2">
{category}
</th>
</tr>
);
}
function ProductRow({ product }) {
const name = product.stocked ? product.name :
<span style={{ color: 'red' }}>
{product.name}
</span>;
return (
<tr>
<td>{name}</td>
<td>{product.price}</td>
</tr>
);
}
function ProductTable({ products }) {
const rows = [];
let lastCategory = null;
products.forEach((product) => {
if (product.category !== lastCategory) {
rows.push(
<ProductCategoryRow
category={product.category}
key={product.category} />
);
}
rows.push(
<ProductRow
product={product}
key={product.name} />
);
lastCategory = product.category;
});
return (
<table>
<thead>
<tr>
<th>Name</th>
<th>Price</th>
</tr>
</thead>
<tbody>{rows}</tbody>
</table>
);
}
function SearchBar() {
return (
<form>
<input type="text" placeholder="Search..." />
<label>
<input type="checkbox" />
{' '}
Only show products in stock
</label>
</form>
);
}
function FilterableProductTable({ products }) {
return (
<div>
<SearchBar />
<ProductTable products={products} />
</div>
);
}
const PRODUCTS = [
{category: "Fruits", price: "$1", stocked: true, name: "Apple"},
{category: "Fruits", price: "$1", stocked: true, name: "Dragonfruit"},
{category: "Fruits", price: "$2", stocked: false, name: "Passionfruit"},
{category: "Vegetables", price: "$2", stocked: true, name: "Spinach"},
{category: "Vegetables", price: "$4", stocked: false, name: "Pumpkin"},
{category: "Vegetables", price: "$1", stocked: true, name: "Peas"}
];
export default function App() {
return <FilterableProductTable products={PRODUCTS} />;
}
최소한의 완전한 UI state 찾기
- UI를 상호작용하게 만들려면 사용자가 기반이 되는 데이터 모델을 변경할 수 있도록 해야 합니다. 이를 위해 state를 사용합니다.
- state를 앱이 기억해야 하는 최소한의 변화하는 데이터 집합을 생각해야한다.
- state를 구조화할 때 가장 중요한 원칙은 DRY(직접 반복하지 않기)를 유지하는 것이다.
state를 식벽하는 요소
- 시간이 지나면 변해야 한다.
- 부모로부터 porps를 통해 전달되지 않아야 한다.
- 컴포넌트의 기존 state 또는 props를 가지고 계산 할 수 없다면 state이다.
state가 어디에 있어야 할지 파악하기
- 이 state를 변경하는 데 책임이 있는 컴포넌트, 즉,state를 ‘소유’하는 컴포넌트를 식별해야 합니다.
- 해당 state를 기반으로 렌더링하는 모든 컴포넌트를 찾으세요.
- 가장 가까운 공통 상위 컴포넌트, 즉,계층상 그 state의 영향을 받는 모든 컴포넌트들의 위에 있는 컴포넌트를 찾으세요.
- state가 어디에 위치할지 결정합시다:
- 대개 공통 부모에 state를 그대로 둘 수 있습니다.
- 혹은 공통 부모보다 더 상위 컴포넌트에 state를 둘 수도 있습니다.
- state를 소유할 적절한 컴포넌트를 찾지 못했다면, state를 소유하는 새 컴포넌트를 만들어 공통 부모 컴포넌트보다 상위에 추가하세요.
'개발 공부' 카테고리의 다른 글
[리액트 공식 문서] context로 데이터 깊숙이 전달하기 (0) | 2023.09.06 |
---|---|
[리액트 공식 문서] state 로직을 reducer로 추출하기 (0) | 2023.09.06 |
.yarn 디렉토리가 없는 경우 (0) | 2023.07.10 |
[JS] Number()와 parseInt와 차이점 (0) | 2023.07.10 |
[JS]함수형 프로그램이란 (0) | 2023.07.10 |