빠른 시작
이 페이지에서는 emotion-variants로 Button 컴포넌트를 처음부터 만들어 봐요.
패키지를 설치하고 Emotion의 css prop을 활성화해 둔 상태를 전제로 해요.
1. 스타일 정의
컴포넌트의 스타일을 정의하는 객체 하나를 ev()에 넘겨요.
import { ev } from 'emotion-variants';
const button = ev({
base: {
padding: '10px 20px',
borderRadius: '8px',
border: 'none',
cursor: 'pointer',
fontWeight: 600,
},
variants: {
size: {
small: {
padding: '8px 16px',
fontSize: 12,
},
medium: {
padding: '10px 20px',
fontSize: 14,
},
large: {
padding: '12px 24px',
fontSize: 16,
},
},
color: {
primary: {
background: '#d36ac2',
color: 'white',
},
secondary: {
background: '#475569',
color: 'white',
},
},
},
defaultVariants: {
size: 'medium',
color: 'primary',
},
});ev()는 함수를 돌려줘요. 이 함수에 variant 값을 넘기면, Emotion의 css prop에 그대로 넣을 수 있는 스타일이 나와요.
2. 컴포넌트에서 사용
import type { ComponentPropsWithoutRef } from 'react';
type ButtonProps = ComponentPropsWithoutRef<'button'> & {
size?: 'small' | 'medium' | 'large';
color?: 'primary' | 'secondary';
};
export function Button({ size, color, ...rest }: ButtonProps) {
return <button css={button({ size, color })} {...rest} />;
}<Button>기본값</Button>
<Button size="large">큰 primary</Button>
<Button size="small" color="secondary">작은 secondary</Button>defaultVariants가 잡혀 있어서, <Button>기본값</Button>은 medium + primary로 렌더링돼요.
3. variant 함수에서 props 타입 추출
props 타입을 손으로 작성할 필요는 없어요. VariantProps 타입을 쓰면 variant 함수에서 바로 끌어낼 수 있어요.
import { ev, type VariantProps } from 'emotion-variants';
const button = ev({
/* ... */
});
type ButtonVariants = VariantProps<typeof button>;
type ButtonProps = ComponentPropsWithoutRef<'button'> & ButtonVariants;이 패턴을 쓰면 컴포넌트의 props 타입과 스타일이 항상 동기화돼요. variants.size에 새 값을 추가하면 ButtonProps도 자동으로 따라와요.
ref 전달 같은 패턴은 TypeScript를 참고해 주세요.
다음으로
- Variants —
base와variants자세히 보기. - API 레퍼런스 —
ev()의 전체 문서. - Compound Variants — 조합에만 적용되는 스타일.
GitHub에서 이 페이지 편집
마지막 업데이트