designpaca/apps/site/research/mobile-app-ux-v1.md
Yun Chan 2b7fa32b5b
All checks were successful
ci / build (push) Successful in 51s
release / release (push) Successful in 2m34s
feat: 한국어 우선 쇼케이스 정리
2026-08-26 18:14:41 +09:00

79 lines
8.2 KiB
Markdown
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

# 모바일 앱 수준 UX 조사 — v1 (2026-08-22)
대상: 가온 학적부·두레대학 수강신청의 모바일(iOS/Android) 경험을 **네이티브 앱 수준**으로 올리는 작업의 근거 모음.
방법: 인터넷 조사(방법론·표준·패턴) → Nielsen 10 휴리스틱 감사 → 구현 → 시나리오 E2E(RED→GREEN 1000+).
## 1. 표준·근거 (인터넷 조사)
### 1.1 내비게이션 — 탭 바
- **Apple HIG — Tab bars/Tab views**: 탭은 **5~6개 이하**, "Avoid overflow tabs"(화면 밖으로 밀려나는 탭 지양). https://developer.apple.com/design/human-interface-guidelines/tab-bars , /tab-views
- **Material 3**: 바텀 내비 **3~5개 목적지**, 터치 타깃 **48×48dp(≈9mm)**, NavigationBar 높이 80dp. https://m3.material.io/foundations/designing/structure
- **Smashing — Golden rules of bottom navigation**: 3~5개, 항상 보이게, 라벨 권장. https://www.smashingmagazine.com/2016/11/the-golden-rules-of-mobile-navigation-design/
- 적용: 두 앱 모두 화면이 6~9개 → **바텀 탭 5 + ‘더보기’ 시트**(나머지 화면). 더보기 시트는 모바일 웹의 정립된 패턴(UIKit의 전통적 More와 같은 결).
### 1.2 시트(모달)
- **Apple HIG — Sheets**: 집중된 자기 완결 작업용, 부모 화면 위에 떠오르고 완료 후 복귀. https://developer.apple.com/design/human-interface-guidelines/sheets
- **NN/g — Bottom Sheets**: 정의·UX 지침. 썸 존(화면 하단)에 있어 한 손 조작에 최적. https://www.nngroup.com/articles/bottom-sheet/
- **Material — Sheets: bottom**: 모바일에서 대화상자 대안, 드래그 핸들(그래버)은 선택 사항. https://m2.material.io/components/sheets-bottom , https://mobbin.com/glossary/bottom-sheet
- 적용: ≤680px에서 기존 중앙 모달을 **바텀 시트**로(그래버 표시, 상단 라운드, 내부 스크롤, 최대 90dvh, safe-area 준수).
### 1.3 안전 영역·뷰포트
- **WebKit 공식 — Designing Websites for iPhone X**: `viewport-fit=cover` 선언 후 **중요 콘텐츠 컨테이너에 선택적으로 padding**. https://webkit.org/blog/7929/designing-websites-for-iphone-x/
- **MDN env()**: `env(safe-area-inset-{top,right,bottom,left})`. cover 없으면 값이 0으로 고정. https://developer.mozilla.org/docs/Web/CSS/Reference/Values/env
- **Polypane 가이드**: `max(16px, env(safe-area-inset-left))` 폴백 패턴, 헤더·푸터·고정 요소에 적용. https://polypane.app/blog/using-safe-area-inset-to-build-mobile-safe-layouts/
- 적용: viewport에 `viewport-fit=cover` 추가 + 헤더(상단 inset)·바텀 내비(하단 inset)·시트(하단 inset)에 `max()` 패딩.
### 1.4 입력 확대(iOS)
- **CSS-Tricks**: 입력 font-size **16px 이상이면 iOS Safari 포커스 자동 확대가 발생 안 함**. `maximum-scale=1` 은 접근성(WCAG 확대 금지)으로 금지. https://css-tricks.com/16px-or-larger-text-prevents-ios-form-zoom/
- 적용: ≤680px에서 `input, select, textarea { font-size: 16px }`.
### 1.5 뒤로 가기(안드로이드/브라우저 히스토리)
- **Baymard — Back button expectations**: `pushState()` 로 모달/뷰 전환마다 히스토리 항목을 만들면 뒤로 가기가 기대(모달 닫기·이전 화면)와 일치. https://baymard.com/blog/back-button-expectations
- **Android 공식 — Navigation principles**: 뒤로 가기는 **최근 화면의 역순 이동**(스택). https://developer.android.com/guide/navigation/principles
- 적용: 뷰 전환·모달 open마다 `history.pushState`, `popstate` 로 복원·닫기. iOS 엣지 스와이프 뒤로도 같은 경로로 자동 작동.
### 1.6 감사 방법론
- **Nielsen 10 휴리스틱**(위반 문서화·심각도 부여): https://www.nngroup.com/articles/ten-usability-heuristics/
- **Google HEART**(Happiness·Engagement·Adoption·Retention·Task success): https://www.heartframework.com/
- **Maze 7단계 UX 감사**: 범위→데이터→휴리스틱 평가→심층 조사→우선순위→권고→보고. https://maze.co/collections/ux-ui-design/ux-audit/
### 1.7 터치·모션 위생
- M3 48dp / HIG 44pt 최소. WCAG 2.5.8: 인라인 텍스트 링크는 24×24px 최소(AA).
- `-webkit-tap-highlight-color: transparent`(그레이 플래시 제거), `touch-action: manipulation`(더블탭 줌 지연 제거), 스크롤 컨테이너 `overscroll-behavior: contain`, 앱 문서 `overscroll-behavior-y: none`(의도치 않은 pull-to-refresh 방지).
## 2. 현재 상태 감사 (Nielsen 10 매핑)
| # | 휴리스틱 | 위반(실측) |
|---|---|---|
| 1 | 시스템 상태 가시성 | 뷰가 URL/히스토리에 없음 — 새로고침·공유 시 첫 화면으로 소실 |
| 3 | 사용자 통제와 자유 | **안드로이드 뒤로 가기 = 앱 이탈**(뷰·모달이 히스토리에 없음). 취소 실행취소는 v19 에 있음 ✓ |
| 4 | 일관성(플랫폼 표준) | 모바일에서 데스크톱 사이드바/탭이 **가로 스크롤 줄**로 축소(iOS/Android 앱 표준=바텀 탭 아님). 모달이 중앙(모바일 표준=바텀 시트 아님). safe-area 무시(viewport-fit 없음 → env() 0px). 노치·홈 인디케이터 영역 침범 가능 |
| 5 | 오류 예방 | 입력 폰트 14px → **iOS 포커스 자동 확대 유발**. 탭 하이라이트(그레이 플래시) 기본값 |
| 6 | 재인식 > 기억 | 가온 모바일 내비 줄 = 9항목 스크롤 — 화면 밖 항목 존재를 모름(HIG "avoid overflow tabs" 위반) |
| 7 | 유연성·효율 | 엄지 존(하단 ~25%)이 전부 빈 여백 — 한 손 도달성 있는 조작 0개. 터치 타깃 일부 40px(coarse 상향분) — 44pt/48dp 미달 |
| 8 | 미니멀·미학 | 데스크톱 문법은 정립됨 ✓ — 모바일만 앱 문법 부재 |
기술 위반 목록: viewport-fit=cover 부재 / manifest·앱 아이콘 부재(설치 불가·앱 아님) / overscroll-behavior 부재 / 뷰 전환 히스토리 부재.
## 3. 구현 계획
- **A 공통 기반**: viewport-fit=cover + safe-area 토큰(`--safe-tb` 등, max() 패딩) / 입력 16px(≤680) / 탭 하이라이트 제거·touch-action / overscroll 위생 / manifest+192·512 아이콘(sharp 생성)·apple-touch-icon / 터치 타깃 ≥44px(coarse).
- **B 바텀 내비**(≤900px): 탭 5 + 더보기 시트. 가온: 홈·수강생·출석부·성적·더보기(자료실·학사 일정·상담·리포트·공지). 두레: 찾기·관심·신청·이수·더보기(총람·공지). 데스크톱 크롬은 현행 유지(사이드바/탭).
- **C 바텀 시트**(≤680px): 기존 `<dialog>` 3종+더보기 시트를 시트 문법으로(그래버·상단 라운드·내부 스크롤·safe-area·슬라이드 업 250ms).
- **D 히스토리**: 뷰 pushState, 모달 open pushState·popstate 닫기(억제 플래그로 이중 back 방지).
- **E 검증**: 시나리오 E2E(RED→GREEN 1000+ 단언) + 리포 게이트 L0~L5 + 시각 기준 갱신 + 안드로이드 에뮬레이터 실기기 스크린샷(iOS 는 Windows 에서 시뮬레이터 불가 — WebKit 엔진(L4)으로 검증, 한계 명시).
## 4. E2E 시나리오 계획 (목표 단언 1000+)
| 스위트 | 내용 | 예상 단언 |
|---|---|---|
| M1 터치 타깃 매트릭스 | 각 앱×전 뷰×{320,390,768} coarse — 버튼·입력 ≥44px, 인라인 링크 ≥24px (요소당 1단언) | ~450 |
| M2 대비 스윕 | 각 앱×전 뷰@390 — 텍스트 요소별 WCAG 대비 | ~200 |
| M3 구조 불변식 | 뷰×폭×{오버플로 0, h1 1줄, 브랜드 1줄, 바텀내비 존재·높이·safe-area 패딩, 본문 하단 여백} | ~360 |
| M4 앱 기반 | viewport-fit, manifest·아이콘, 입력 16px(요소당), 탭 하이라이트, overscroll | ~30 |
| S1~S6 사용자 여정 | 강사 아침(출결)·오후(채점)·저녁(상담·리포트)·**하루 종일 종단(전 9화면 실조작, 실사용 10분+ 상당)** / 학생 첫 신청·정정기간(변경·undo·이수·공지·시간표 확정·인쇄) | ~200 |
| S7 뒤로 가기 | 뷰 3이동→back×2 복원, 모달 open→back 닫힘→back 이전 뷰 (2앱) | ~40 |
| S8 시트·S9 더보기 | 시트 하단 고정·그래버·스크롤·safe-area / 더보기 열기·이동·활성 표시 | ~50 |
| V 시각 게이트 | 390px 전 뷰+시트 상태 스크린샷 pixelmatch | ~40 |
합계 ≈ 1300. RED: 신규 기능 단언은 구현 전 실패로 확인(RED) → 구현 후 전부 GREEN.