CVA + Zustand로 설계하는 디자인 시스템 기반 UI 컴포넌트 (with Storybook)
이 글에서 소개한 Modal, Input, DatePicker, SelectInput, Toast 등의 UI 컴포넌트는 실제로 프로젝트에 구현되어 있으며, 아래 GitHub 저장소에서 확인하실 수 있습니다:
👉 oneday-coding/DOT-DAILY - components/ui
<Modal isOpen={open} onClose={() => setOpen(false)}>
<h2>할 일 등록</h2>
<Input label="제목" />
<SelectInput label="우선순위" />
<DatePicker label="날짜" />
</Modal>
components/ui/Input/
├── Input.tsx // 기본 인풋 (스타일)
├── TextInput.tsx // 텍스트 필드
├── TextareaInput.tsx // 멀티라인 입력
├── DateInput.tsx // 날짜 선택
├── SelectInput.tsx // 셀렉트 필드
├── Input.stories.tsx // 📕 Storybook 문서
└── index.ts // barrel export
Toast, Modal 등 UI 상태는 컴포넌트 간 공유되기 때문에 전역 관리가 필요합니다.
export const useUIStore = create(set => ({
modal: null,
openModal: (name: string) => set({ modal: name }),
closeModal: () => set({ modal: null }),
toast: { message: '', type: 'success' },
showToast: (msg, type) => set({ toast: { message: msg, type } }),
}));
각 컴포넌트를 독립적으로 문서화하여 아래 항목 포함:
export default {
title: 'Components/Input',
component: TextInput,
};
export const Basic = () => (
<TextInput label="할 일 제목" placeholder="입력하세요" />
);