디자이너가 자주 빠뜨리는 컴포넌트 상태들 — hover부터 skeleton까지 실무 체크리스트

 

"디자인엔 없는데요?" — 개발자가 가장 많이 하는 말이에요. hover, disabled, loading, error, empty, skeleton… 실무에서 디자이너가 자주 빠뜨리는 컴포넌트 상태들, 빠졌을 때 개발에서 벌어지는 일, 그리고 다시는 놓치지 않는 체크리스트까지 한 번에 정리했어요!

 

디자이너 동료에게서 받은 컴포넌트 파일을 열었는데 버튼이 딱 하나예요. 기본(Default) 상태 하나. 개발자가 "hover는요? disabled는요? 로딩 중엔 어떻게 보여요?" 물어보면 "아 그건 알아서 해주세요~"가 돌아오는 그 상황. 😅 반대로 디자이너 입장에서도 억울해요. 솔직히 처음에 뭘 챙겨야 하는지 아무도 알려주지 않았거든요.

이 글은 디자이너를 탓하려는 게 아니에요. 실무에서 정말 자주 누락되는 상태들이 있고, 그게 빠졌을 때 개발 과정에서 어떤 일이 일어나는지, 그리고 앞으로 어떤 기준으로 체크하면 되는지를 같이 정리해 보려고 해요. 이 글 한 번만 읽으면 "디자인엔 없는데요?"라는 말을 훨씬 덜 들을 수 있을 거예요!

 

클린 플랫 스타일로 제작된 UI 컴포넌트 디자인 가이드 일러스트입니다. 왼쪽에는 테라코타 및 라이트 그레이 색상 팔레트를 사용한 버튼의 6가지 상태(Default, Hover, Active, Disabled, Loading, Error)가 나란히 배열되어 있습니다. 오른쪽에는 'No Items Yet'이라는 문구와 함께 빈 상자 일러스트, 그리고 'Create First Item'이라고 적힌 CTA 버튼이 포함된 빈 상태 카드(Empty State Card)가 배치되어 있습니다. 디자인 시스템 구축 및 디자이너와 개발자 간의 원활한 협업 과정을 보여줍니다.

왜 상태(State)가 이렇게 중요한가요? 🤔

UI 컴포넌트는 언제나 딱 한 가지 모습만 가지지 않아요. 같은 버튼이라도 사용자가 마우스를 올리는 순간, 클릭하는 순간, 비활성화된 순간, 로딩 중인 순간에 모두 다르게 보여야 해요. 이 각각의 모습이 바로 "상태(State)"예요.

상태 디자인이 누락됐을 때 벌어지는 일은 크게 세 가지예요. 첫째, 개발자가 임의로 스타일을 만들어 넣어요. 그 결과는 브랜드 가이드와 전혀 다른 UI가 될 수 있어요. 둘째, 개발자가 기획자나 디자이너에게 다시 확인을 요청하면서 피드백 루프가 길어지고 일정이 지연돼요. 셋째, 그냥 아무 처리도 안 한 채로 배포됐다가 사용자가 이상한 화면을 만나는 최악의 상황이 오기도 해요.

💡 알아두세요!
컴포넌트 하나를 완성도 있게 디자인한다는 건 "이 컴포넌트가 가질 수 있는 모든 상태를 커버했는가"를 뜻해요. Default 하나만 있는 컴포넌트는 사실 30% 정도만 완성된 거예요.

 

자주 누락되는 상태 목록 — 카테고리별 정리 📋

실무에서 가장 자주 빠지는 상태들을 인터랙션 상태, 기능 상태, 데이터 상태 세 카테고리로 나눠서 정리해 드릴게요.

① 인터랙션 상태 (Interaction States)

사용자의 마우스·터치·키보드 동작에 반응하는 상태들이에요. 이 중 hover와 focus가 가장 자주 빠져요.

상태 발생 시점 빠졌을 때 발생하는 일
Hover 마우스 오버 시 개발자가 opacity 70% 같은 임시 처리를 넣거나 아무 반응 없이 배포됨
Active / Pressed 클릭·탭 누르는 순간 클릭 피드백 없음 → 사용자가 "버튼이 눌렸나?" 혼란
Focus 키보드 Tab 포커스 시 접근성(A11y) 심각 문제. 키보드 사용자가 현재 위치를 알 수 없음
Focus-visible 키보드 포커스 (마우스 제외) 마우스 클릭 시에도 포커스 링이 보여 시각적으로 지저분해짐
Visited 링크 방문 후 브라우저 기본 보라색으로 바뀌어 브랜드 색상 깨짐

② 기능 상태 (Functional States)

컴포넌트의 기능적 조건에 따라 달라지는 상태들이에요. disabled와 loading이 압도적으로 많이 빠져요.

상태 발생 시점 빠졌을 때 발생하는 일
Disabled 비활성화 조건 충족 시 개발자가 opacity 40% 처리. hover도 함께 꺼야 하는데 놓치는 경우 많음
Loading / Pending API 요청·처리 대기 중 스피너 위치·크기를 개발자가 임의로 결정. 버튼 너비가 갑자기 바뀌는 레이아웃 쉬프트 발생
Selected / Checked 선택된 상태 라디오·체크박스·탭 선택 시 시각적 구분 없음
Readonly 수정 불가 입력 필드 disabled와 구분 없이 처리됨 → 복사 가능 여부 UI 혼동
Indeterminate 체크박스 부분 선택 "전체 선택" 체크박스에서 일부만 선택됐을 때의 상태 누락

③ 데이터 상태 (Data States)

데이터의 존재 여부·유효성에 따른 상태들이에요. empty, error, skeleton이 3대 누락 단골이에요.

상태 발생 시점 빠졌을 때 발생하는 일
Empty State 데이터가 0건일 때 빈 컨테이너만 덩그러니. 개발자가 "데이터 없음" 텍스트를 임의 삽입
Error State API 실패·유효성 오류 빨간 테두리만 추가. 에러 메시지 위치·폰트·색상이 컴포넌트마다 제각각
Skeleton 데이터 로딩 전 데이터 로드 완료 후 레이아웃 쉬프트 발생. 혹은 스피너로 대체되어 UX 저하
Partial / Truncated 텍스트 넘침·말줄임 실제 긴 데이터 입력 시 레이아웃 깨짐. "짧은 텍스트"로만 디자인된 경우 빈번
Success 작업 완료 직후 제출 완료·저장 후 피드백 없음 → 사용자가 완료 여부를 모름
⚠️ 가장 치명적인 누락 TOP 3
실무 경험상 개발 일정에 가장 큰 영향을 주는 누락 상태는 ① Loading (버튼·폼 전반), ② Empty State (리스트·테이블), ③ Error State (인풋 필드) 순이에요. 이 세 가지만 챙겨도 개발자와의 마찰이 절반 이상 줄어요.

 

빠뜨렸을 때 개발에서 벌어지는 일 🔥

상태가 빠졌다는 걸 개발자가 처음 인지하는 시점은 보통 구현 도중이에요. 이때 선택지는 세 가지예요.

📌 시나리오 A — 개발자가 임의로 처리한다

일정이 촉박하면 개발자가 "그냥 opacity 낮출게요" 하고 처리해버려요. 이 판단이 나쁜 게 아니에요. 하지만 결과적으로 브랜드 일관성이 깨지고, 나중에 디자이너가 보고 "이게 뭐예요?"가 되는 상황이 와요.

📌 시나리오 B — 디자이너에게 다시 요청한다

더 좋은 선택이지만 시간이 들어요. 디자이너가 해당 파일을 다시 열어서 상태를 추가하고, 검토 받고, 개발에 전달하는 루프가 돌아요. 규모가 작으면 하루, 크면 며칠이 날아가요. 스프린트 계획 전체가 흔들리기도 해요.

📌 시나리오 C — 그냥 배포한다

가장 무서운 케이스예요. "일단 베타니까"로 넘어갔다가 그게 그대로 프로덕션에 가는 일이 생각보다 자주 일어나요. 사용자가 아무 반응 없는 버튼을 보거나, 에러 후 빈 화면을 마주하면 이탈률이 올라가요.

결국 상태 하나를 빠뜨리는 건 단순히 "UI 누락"이 아니라 팀 전체의 시간과 제품 품질에 직접 영향을 미치는 문제예요. 디자이너가 미리 챙기는 게 가장 저렴한 해결책이에요.

 

컴포넌트별 상태 체크리스트 ✅

컴포넌트 유형별로 챙겨야 할 상태 목록을 체크리스트로 정리했어요. Figma에서 컴포넌트 작업 마칠 때 이 리스트를 한 번씩 훑어보세요!

🔘 Button

  • ☐ Default
  • ☐ Hover
  • ☐ Active (Pressed)
  • ☐ Focus
  • ☐ Disabled — hover도 비활성화되어야 함
  • ☐ Loading — 스피너 위치, 버튼 너비 고정 여부 명시 필수
  • ☐ Success (필요한 경우) — 완료 아이콘·텍스트 변경 등

📝 Input / Form Field

  • ☐ Default (Empty)
  • ☐ Placeholder
  • ☐ Focus
  • ☐ Filled (값 입력된 상태)
  • ☐ Error — 에러 메시지 공간, 아이콘, 색상 포함
  • ☐ Success / Valid
  • ☐ Disabled
  • ☐ Readonly — disabled와 시각적으로 구분돼야 함
  • ☐ Long text (텍스트 넘침 처리)

📋 List / Table / Card

  • ☐ Default (데이터 있음)
  • ☐ Loading / Skeleton — 레이아웃 쉬프트 없도록 실제 크기와 동일하게
  • ☐ Empty State — 일러스트·메시지·CTA 버튼 포함 여부 결정
  • ☐ Error State — 재시도 버튼 포함 권장
  • ☐ Row hover (테이블)
  • ☐ Partial load / Pagination (더 보기 상태)

☑️ Checkbox / Radio / Toggle

  • ☐ Default (Unchecked)
  • ☐ Hover
  • ☐ Focus
  • ☐ Checked / On
  • ☐ Indeterminate — 체크박스만 해당. 부분 선택 상태
  • ☐ Disabled Unchecked
  • ☐ Disabled Checked — 이미 선택된 항목이 비활성화된 경우

🧭 Navigation / Tab

  • ☐ Default
  • ☐ Hover
  • ☐ Active / Current (현재 페이지)
  • ☐ Focus
  • ☐ Disabled (비활성 메뉴 항목)
💡 Skeleton 상태 설계 팁!
Skeleton은 실제 컨텐츠와 동일한 크기와 레이아웃으로 만들어야 해요. 높이가 다르면 데이터 로드 후 레이아웃 쉬프트(CLS)가 발생해요. Figma에서 실제 카드 컴포넌트 위에 Skeleton 레이어를 올려 크기를 맞춰보는 습관을 들이면 좋아요.

 

핵심 내용 정리 📝

오늘 다룬 내용을 마지막으로 정리할게요!

  1. 상태는 3가지 카테고리: 인터랙션(hover, active, focus), 기능(disabled, loading, selected), 데이터(empty, error, skeleton)로 분류해서 생각하면 누락이 줄어요.
  2. 3대 치명 누락: Loading·Empty State·Error State — 이 세 가지는 무조건 챙기세요.
  3. 누락의 결과: 개발자 임의 처리 → 브랜드 깨짐 / 재요청 루프 → 일정 지연 / 그냥 배포 → 사용자 이탈. 모두 미리 챙기는 것보다 비쌀 수밖에 없어요.
  4. 체크리스트 활용: 컴포넌트 완성 후 오늘 정리한 리스트를 한 번씩 훑어보는 습관만으로 커뮤니케이션 비용이 크게 줄어요.
  5. Skeleton은 실제 크기 기준: 레이아웃 쉬프트 방지를 위해 컨텐츠 컴포넌트와 동일한 크기로 설계하는 게 핵심이에요.

 

🔍

컴포넌트 상태 체크 요약 카드

🚨 무조건 챙길 3가지 (치명적 누락):
⚡ Loading 📭 Empty State ❌ Error State
🖱️ 인터랙션 상태:
hover active focus focus-visible visited
⚙️ 기능 상태:
disabled loading selected readonly indeterminate
📊 데이터 상태:
empty error skeleton truncated success

 

자주 묻는 질문 ❓

Q: 모든 컴포넌트에 이 상태를 다 만들어야 하나요? 너무 많은 것 같아요.
A: 꼭 그렇지는 않아요! 컴포넌트의 용도에 따라 필요한 상태가 달라요. 예를 들어 Static한 텍스트 배지(Badge)엔 hover나 focus가 없어도 돼요. 중요한 건 "이 컴포넌트가 인터랙티브한가?", "데이터를 표시하는가?", "사용자 입력을 받는가?" 세 가지 기준으로 필요한 상태를 추려내는 거예요.
Q: disabled와 readonly의 차이를 시각적으로 어떻게 구분하면 좋나요?
A: 일반적으로 disabled는 배경색을 연하게 처리하고 커서를 not-allowed로 바꿔요. 반면 readonly는 배경색은 약간 다르게 하되(예: 연한 회색 배경) 텍스트 색상은 normal로 유지해서 "읽을 수 있고 복사도 되지만 편집은 안 된다"는 느낌을 줘요. 두 상태를 구분하는 가장 중요한 힌트는 커서(cursor) 스타일과 텍스트 가독성이에요.
Q: Figma에서 상태를 효율적으로 관리하는 방법이 있나요?
A: Figma의 Component Properties를 활용하면 효율적이에요. Variant Property로 State(default, hover, focus, disabled 등)를 정의하고, Boolean Property로 isLoading, isError 같은 플래그를 추가해요. 그러면 하나의 컴포넌트 안에서 Properties 패널만 토글해도 모든 상태를 확인하고 프리뷰할 수 있어요.
Q: Empty State 디자인에 꼭 들어가야 하는 요소가 있나요?
A: 기본적으로 세 가지를 권장해요. ① 상황을 설명하는 일러스트 또는 아이콘, ② "아직 항목이 없어요" 같은 상태 메시지, ③ 사용자가 다음 행동을 할 수 있는 CTA 버튼(예: "첫 번째 항목 추가하기"). 세 가지 모두 있으면 이상적이지만, 최소한 메시지와 CTA는 있어야 사용자가 막히지 않아요.
Q: 개발자와 디자이너가 상태 누락을 사전에 방지하는 협업 방법이 있을까요?
A: 몇 가지 효과적인 방법이 있어요. ① 컴포넌트 인수인계 전에 오늘 정리한 체크리스트를 함께 리뷰하는 "상태 리뷰 세션"을 스프린트에 포함하기, ② Figma 파일에 상태별 커버 페이지를 만들어서 누락 상태를 시각적으로 확인하기, ③ 개발자가 구현 시작 전에 "이 컴포넌트의 모든 상태를 확인했나요?" 체크박스를 Definition of Ready에 추가하는 방법도 있어요.

디자이너를 오래 하신 분들은 이 리스트를 보면 "맞아, 이거 나도 빠뜨린 적 있지" 하고 공감하실 거예요. 처음엔 이걸 다 챙기려면 시간이 더 걸리는 것 같아도, 결과적으로는 개발자와 핑퐁하는 시간, 다시 수정하는 시간, 버그 리포트 받는 시간이 훨씬 줄어요. 오늘 체크리스트, 바탕화면에 저장해두고 컴포넌트 작업 마칠 때마다 꺼내 보세요! 더 추가하고 싶은 상태나 팀에서 겪은 사례가 있다면 댓글로 공유해 주세요 😊