페이지 인터랙션 — 모바일 앱 (2depth · 풀레이어 팝업)
모바일 앱 전용
이 페이지의 규칙은 모바일 앱(직원 앱 · hereby Works) 에만 적용합니다. admin · hr-system 같은 웹 앱은 대상이 아닙니다 — 웹의 모달 · 패널 모달은 모달 규칙을 따릅니다.
화면 위에 화면이 열리는 두 가지 방법
모바일 앱에서 지금 화면 위로 화면 한 장이 통째로 열리는 방법은 두 가지뿐입니다 — 「뒤로(<)」로 돌아가는 2depth 페이지와, 「닫기(X)」로 닫는 풀레이어 팝업. 이 페이지가 둘을 한곳에 정리합니다: 언제 무엇을 쓰는지, 구조 · 헤더 · 여백 · 하단 버튼 · 닫기, 그리고 열리고 닫힐 때의 움직임(2depth 는 옆에서, 풀레이어 팝업은 아래에서)과 iOS 엣지 스와이프(2026-10-12).
규칙 (강제) · 코딩 에이전트용
2depth · 풀레이어 팝업의 강제 규칙(모바일 앱 전용 — 웹 앱은 대상 아님). 상세·근거는 아래 본문.
고르기
- 화면 한 장 전체를 여는 방법은 2depth 와 풀레이어 팝업 둘뿐이다. 들어가서 보고 돌아오는 하위 화면은 2depth(「뒤로(<)」), 무언가를 작성 · 고르고 끝내는 화면은 풀레이어 팝업(「닫기(X)」). 둘을 섞지 않는다 — 2depth 에 X 를, 풀레이어 팝업에 < 를 두지 않는다.
2depth 페이지
- 헤더는 앱 셸의 앱 헤더 하나를 쓴다(
showBack으로 깊이를 가름). 화면 안에 제목 · 뒤로 버튼을 따로 그리지 않는다. - 루트에
x-show+x-depth-page.x-if를 쓰지 않는다 — 조건이 꺼지는 순간 DOM 이 지워져 이탈 애니메이션이 없다. - 본문 좌우 여백 12(
px-3). 하단 고정 버튼은.page-footer-cta(바) 또는.page-footer-cta--flow(본문 끝).
풀레이어 팝업
- 구조는 딤 루트(
.modal-backdrop) > 시트(.modal-sheet.modal-sheet--full) > 본문(.modal-full__body, 안에 제목 줄.modal-full__header) + 하단 바(.modal-full__footer). 공용 모달을 풀레이어로 쓸 때는.ds-modal--full(호스트가fullLayer: true). - 제목은
<div role="heading" aria-level="3" class="modal-full__title">— 2depth 제목과 같은 규격(text-b3· semibold · 한 줄 말줄임 · 화면 설정과 무관한 고정 크기).<h3>에 크기 클래스를 주지 않는다(태그 기본값에 밀린다). - 닫기(X)는 제목 줄 오른쪽
.ds-btn--icon.modal-full__close, 본문 선(오른쪽 12)에 둔다 — 2depth 뒤로(<)의 좌우 대칭. - 본문만 스크롤하고 하단 바는 고정한다. 좌우 여백 12. 입력칸
ds-input--48, 라벨text-b4이상, 하단 버튼ds-btn--lg· 둘까지(셋이면 「취소」를 빼고 X 에 맡긴다). <template x-if>대신<template x-layer-if>,x-show로 여는 공용 모달은x-layer-page="<풀레이어일 때만 참>".- 새 풀레이어 클래스를 만들면 직원 앱
main.css의 글자 배율 보정 선택자(html[data-font-scale="lg"] .modal-sheet--full, … .ds-modal--full)에 같이 넣는다.
움직임
- 2depth 는 우 → 좌, 풀레이어 팝업은 아래 → 위. 세 번째 방향(왼쪽에서 · 위에서 · 페이드만 · 확대)을 만들지 않는다.
- 풀레이어 팝업은 시트만 움직이고 딤은 배경색만 옅어진다. 딤 루트 바로 아래 자식이 시트(
.modal-sheet·.ds-modal)여야 한다. - 길이 260ms · 곡선
cubic-bezier(0.32, 0.72, 0, 1)하나(apps/employee-app/src/directives/page-motion.ts). 화면마다 바꾸지 않고,x-transition클래스로 따로 그리지 않는다. - 모션 줄이기(
prefers-reduced-motion: reduce)면 바로 열고 닫는다 — 디렉티브가 처리한다. - 엣지 스와이프는 2depth 에만, iOS 네이티브 앱에만. 풀레이어 팝업 · 안드로이드 · 웹에는 걸지 않는다. 대상 뒤로 버튼에
data-edge-swipe-back(앱 헤더 「뒤로(<)」에는 이미 있음). 모양만 < 인 버튼(이전 달)에는 달지 않는다.
대상 아님 — 바텀시트(.modal-sheet 단독 — 확인 시트 · 이미지 자르기), 컨펌 다이얼로그(.ds-dialog), 오른쪽 서랍(AI 이전 대화), 1depth 탭 전환, 토스트 · 배너.
- 다크 모드(2026-10-19) — 2depth 페이지 · 풀레이어 팝업의 면 · 글자 · 선은 직원 앱 전 화면 이관으로 시멘틱을 읽는다: 풀레이어 바탕
bg-bg-container, 하단 버튼 영역 윗선.modal-full__footerline-normal(전 neutral-100 고정 — 다크에서 흰선), 흰 면 화면 표시app-surface-white가 넘기는 헤더 · 하단 내비 면bg-container. 사용 안내(투어) 말풍선 제목 · 본문은label-normal·label-body. 확인: Playground 「미리보기 테마 → 다크」.
두 종류 한눈에
| 2depth 페이지 | 풀레이어 팝업 | |
|---|---|---|
| 언제 | 목록 · 홈에서 들어가 보고 돌아오는 하위 화면 | 무언가를 작성 · 고르고 끝내는 화면 |
| 예 | 결재 상세, 급여명세서, 알림, 내 정보, 나의 결재선, 근무 기록 | 휴가 · 연장근무 · 외근 신청, 보고서, 출퇴근 정정, 서류 제출, 인센티브 등록, 결재자 지정, 명세서 상세, 불편 · 오류 신고 |
| 돌아가는 버튼 | 왼쪽 뒤로(<) — 44 유리 원 | 오른쪽 닫기(X) — 32 투명 버튼 |
| 헤더 | 앱 셸의 앱 헤더(.ds-app-header--depth2) | 시트 안 제목 줄(.modal-full__header) |
| 제목 | text-b3 · semibold · hr-gray-900 · 한 줄 | 같은 규격(.modal-full__title) |
| 하단 내비 | 숨김 | 시트가 덮음 |
| 하단 버튼 | .page-footer-cta | .modal-full__footer |
| 진입 | 우 → 좌 — 오른쪽 밖에서 제자리로 | 아래 → 위 — 화면 아래 밖에서 제자리로 · 딤이 짙어짐 |
| 이탈 | 좌 → 우 — 그 아래로 1depth 가 드러남 | 위 → 아래 — 딤이 옅어지며 아래 화면이 드러남 |
| 엣지 스와이프 (iOS) | 있음 | 없음 — 「닫기(X)」로만 닫음 |
| 마크업 | x-show + x-depth-page | <template x-layer-if> / x-show + x-layer-page |
| 구현 | directives/depth-page.ts | directives/layer-page.ts |
무엇을 쓸까
- 돌아갈 곳을 보여 주는 화면이면 2depth — 사용자가 「보고」 돌아갑니다. 그 안에서 또 들어가면 3depth 이상이지만 헤더 모양은 2depth 와 같습니다(깊이를 세지 않고 「뒤로 갈 곳이 있는가」만 봄).
- 끝내야 하는 일이면 풀레이어 팝업 — 사용자가 「쓰고 · 고르고」 닫습니다. 저장하지 않고 닫을 때 물어볼 수 있는 것도 이쪽입니다.
- 짧은 확인 · 선택이면 둘 다 아닙니다 — 바텀시트나 컨펌 다이얼로그를 씁니다. 풀레이어 팝업은 입력이 있는 폼에 어울립니다.
공통 — 움직임 값
| 항목 | 값 |
|---|---|
| 길이 | 260ms — 두 종류 같음 |
| 곡선 | cubic-bezier(0.32, 0.72, 0, 1) — 빠르게 출발해 부드럽게 멈추는 iOS 시트 곡선 |
| 모션 줄이기 | 움직이지 않고 바로 열고 닫음(prefers-reduced-motion: reduce) |
| 정본 | apps/employee-app/src/directives/page-motion.ts |
DS 모션 토큰은 --duration-fast(100ms) · --duration-normal(200ms) 두 단계뿐이라 페이지 전환 값이 없어, 직원 앱 한 곳에 상수로 둡니다.
2depth 페이지
목록 줄을 눌러 들어가고 「뒤로(<)」로 돌아와 보세요. 플랫폼을 iOS 로 두고 왼쪽 가장자리를 끌면 엣지 스와이프입니다.
목록 줄을 누르면 2depth 가 오른쪽에서 들어와요.
<!-- 헤더는 앱 셸의 앱 헤더 하나 — showBack 으로 1depth · 2depth 를 가른다 -->
<div class="contents" x-data="appHeader({ …, onBack: () => goBack(), showBack: () => isDepth })"> … </div>
<!-- 2depth 페이지 — 우 → 좌. 여는 조건은 반드시 x-show (x-if 는 이탈 애니메이션이 없다) -->
<div x-show="showPayslips" x-cloak x-depth-page class="px-3 pt-4">
…
<div class="page-footer-cta"> <!-- 하단 고정 버튼(필요할 때만) -->
<button class="ds-btn ds-btn--solid ds-btn--primary ds-btn--lg">저장</button>
</div>
</div>
// 엣지 스와이프 — iOS 네이티브만, 2depth 가 열려 있을 때만 (capacitor-init.ts)
if (Capacitor.getPlatform() === "ios") {
const edgeSwipe = installEdgeSwipeBack();
Alpine.effect(() => edgeSwipe.setArmed(Alpine.store("router").depth !== null));
}
<!-- 스와이프 대상 뒤로 버튼 — 앱 헤더 「뒤로(<)」에는 이미 달려 있다 -->
<button data-edge-swipe-back aria-label="뒤로"> … </button>구조
<!-- 앱 셸 헤더 하나가 1depth · 2depth 를 오간다 — showBack 으로 깊이를 가른다 -->
<div class="contents" x-data="appHeader({ …, onBack: () => goBack(), showBack: () => isDepth })"> … </div>
<!-- 2depth 화면 — 루트에 x-show + x-depth-page, 본문 좌우 12 -->
<div x-show="showPayslips" x-cloak x-depth-page class="px-3 pt-4">
…
<div class="page-footer-cta"> <!-- 하단 고정 버튼(필요할 때만) -->
<button class="ds-btn ds-btn--solid ds-btn--primary ds-btn--lg">저장</button>
</div>
</div>- 헤더는 화면이 그리지 않습니다. 앱 셸의 앱 헤더 하나가
showBack으로 1depth · 2depth 를 오가고, 2depth 면 왼쪽에 뒤로(<) 유리 원(44)과 화면 제목이 붙습니다. 벨 · 아바타는 보통 끕니다. 상세 → 앱 헤더 · 깊이. - 좌우 여백 12 — 1depth 와 같습니다(2026-10-12). 헤더도 같은 선(
--app-depth-side)에 섭니다. - 하단 내비는 숨습니다. 그래서 하단 고정 버튼(
.page-footer-cta)이 safe-area 여백을 직접 갖습니다 — 흰 바탕 · 윗선 · 좌우 12 · 아래 16 + safe-area, 버튼은 반반(flex: 1). 바가 아니라 본문 끝에 얹으려면.page-footer-cta--flow(내 정보).
움직임 — 우 → 좌
- 진입은 오른쪽 밖 → 제자리, 이탈은 제자리 → 오른쪽 밖이고 그 아래로 1depth 가 드러납니다.
- 2depth 화면 대부분은 자기 배경이 없어(앱 셸 배경이 비침), 이탈할 때 디렉티브가 조상에서 실제로 칠해진 배경색을 찾아 떠나는 화면에 입힙니다. 그래야 그 아래 다시 보이기 시작한 1depth 가 비쳐 보이지 않습니다.
- 떠나는 화면은 지금 그려진 자리 그대로 흐름에서 빠집니다(절대배치). 그대로 두면 같은 순간 다시 보이기 시작한 1depth 와 세로로 쌓여 목록이 밀린 채 움직입니다.
- 공용 템플릿(메신저)은 값을 줘 조건부로 씁니다 —
x-depth-page="useHostHeader". 거짓이면 아무것도 심지 않아 그 요소의 기존x-transition(PC 드로어 등)이 그대로 삽니다.
엣지 스와이프 — iOS 한정
iOS 네이티브 앱에서는 2depth 화면의 왼쪽 가장자리(20px)를 오른쪽으로 밀면 「뒤로(<)」를 누른 것과 같습니다.
| 항목 | 값 |
|---|---|
| 켜지는 곳 | iOS 네이티브 앱만(Capacitor.getPlatform() === "ios"). 안드로이드는 시스템 뒤로 제스처가 이미 앱의 뒤로 가기로 이어져 있어 겹치고, Safari 웹은 브라우저 자체 스와이프와 겹쳐서 켜지 않습니다. |
| 켜지는 때 | 2depth 가 열려 있을 때만입니다($store.router.depth). 1depth 탭 첫 화면에서는 리스너를 걸지 않아 긴 목록의 스크롤에 영향이 없습니다. |
| 대상 버튼 | 화면 맨 위에 실제로 보이는 data-edge-swipe-back 버튼(앱 헤더의 「뒤로(<)」)입니다. 다이얼로그 · 튜토리얼 · 풀레이어 팝업이 덮고 있으면 동작하지 않습니다. |
| 따라오기 | 가장자리에서 시작해 가로로 밀면 2depth 화면이 손가락을 따라 오른쪽으로 밀립니다. |
| 손을 떼면 | 화면 폭의 35% 이상 밀었거나 빠르게 튕겼으면 뒤로 갑니다. 이때 그 버튼을 그대로 누르므로 저장 확인 같은 화면별 뒤로 가기 규칙도 똑같이 탑니다. 이탈 슬라이드는 밀린 위치에서 이어집니다. 그렇지 않으면 제자리로 돌아옵니다. |
| 햅틱 | 없음 |
풀레이어 팝업(「닫기(X)」)에는 엣지 스와이프를 걸지 않습니다. 아래에서 올라온 화면이라 옆으로 밀어 닫는 동작이 방향과 맞지 않습니다.
풀레이어 팝업
「휴가 신청」을 눌러 열고 「닫기(X)」로 닫아 보세요. 속도를 느리게 하면 시트만 올라오고 딤은 짙어지는 것이 보입니다.
「휴가 신청」을 누르면 풀레이어 팝업이 아래에서 올라와요.
<!-- 풀레이어 팝업 — 아래 → 위. x-if 대신 x-layer-if (닫으면 내려간 뒤 지운다) -->
<template x-teleport="body">
<template x-layer-if="showLeaveModal">
<div class="modal-backdrop"> <!-- 딤 루트 -->
<div class="modal-sheet modal-sheet--full"> <!-- 시트 · 이것만 움직인다 -->
<div class="modal-full__body flex flex-col px-3 pt-5 pb-5"> <!-- 이것만 스크롤 -->
<div class="modal-full__header flex items-center justify-between mb-4">
<div role="heading" aria-level="3" class="modal-full__title">휴가 신청</div>
<button class="ds-btn ds-btn--icon ds-btn--muted modal-full__close" aria-label="닫기"
@click="requestCloseForm('leave')">
<span class="ds-ico" aria-hidden="true" x-html="$icon('ic-close')"></span>
</button>
</div>
… 입력 …
</div>
<div class="modal-full__footer"> <!-- 하단 고정 바 -->
<button class="ds-btn ds-btn--solid ds-btn--primary ds-btn--lg">신청</button>
</div>
</div>
</div>
</template>
</template>
<!-- x-show 로 여는 공용 모달의 풀레이어 모드 -->
<div x-show="isOpen" x-layer-page="fullLayer" class="ds-modal-backdrop"> … </div>구조
<template x-teleport="body">
<template x-layer-if="showLeaveModal">
<div class="modal-backdrop"> <!-- 딤 루트 -->
<div class="modal-sheet modal-sheet--full"> <!-- 시트 = 화면 전체 · 이것만 움직인다 -->
<div class="modal-full__body flex flex-col px-3 pt-5 pb-5"> <!-- 이것만 스크롤 -->
<div class="modal-full__header flex items-center justify-between mb-4">
<div role="heading" aria-level="3" class="modal-full__title">휴가 신청</div>
<button class="ds-btn ds-btn--icon ds-btn--muted modal-full__close" aria-label="닫기"
@click="requestCloseForm('leave')">
<span class="ds-ico" aria-hidden="true" x-html="$icon('ic-close')"></span>
</button>
</div>
… 입력 …
</div>
<div class="modal-full__footer"> <!-- 하단 고정 바 -->
<button class="ds-btn ds-btn--solid ds-btn--primary ds-btn--lg">신청</button>
</div>
</div>
</div>
</template>
</template>시트는 화면 전체(100dvh · 모서리 0 · 위 safe-area)를 덮는 flex 컬럼입니다. 본문(.modal-full__body)만 스크롤하고 하단 바는 바닥에 남습니다. 제목 줄은 본문 안 첫 줄입니다(앱 헤더가 아니라 스크롤 상자 안에 있어 유리 효과 대상이 아님).
제목 줄 — 제목 · 닫기(X)
| 요소 | 규격 |
|---|---|
| 제목 | <div role="heading" aria-level="3" class="modal-full__title"> — text-b3 · semibold · hr-gray-900 · 한 줄 말줄임. 2depth 제목과 같은 규격이고, 화면 설정(작게 · 기본 · 크게)과 무관한 고정 크기(calc(var(--text-b3) * var(--app-nav-zoom))). |
| 닫기(X) | 제목 줄 오른쪽 .ds-btn--icon.modal-full__close — 박스 32 · 글리프 20 · hr-gray-800. 본문 선 그대로(오른쪽 12)에 둬 2depth 뒤로(<) 원(왼쪽 12)과 좌우 대칭. |
| 세로 위치 | 2depth 헤더와 같은 높이(--app-header-top-in-body = 상태바 + 8). 버튼만이 아니라 줄 전체를 맞춘다. |
| 글자 버튼(「도움」) | 제목과 같이 크기 고정(.modal-full__header .ds-btn-text). |
- ⚠️ 아직 맞추지 않은 것 — 닫기(X)는 32 투명 버튼이고 화면 설정을 따라 커지고 작아집니다. 2depth 뒤로(<)의 44 유리 원과는 크기 · 재질이 다릅니다(알고 두는 차이).
- 제목에
<h3>를 쓰고 클래스로 크기를 주면 unlayered 태그 기본값에 밀려 조용히 무시됩니다 → 타이포그래피.
본문 · 여백
- 좌우 12 — 본문
px-3, 하단 바도 12. 2depth · 1depth 와 같은 선입니다(2026-10-12, 예전 20). - 입력칸
ds-input--48/ds-select--48(손가락 타깃), 라벨 · 설명text-b4이상. 직원 앱 최소 글자는 13px(text-b5)입니다. - 키보드 — 네이티브 셸이라 키보드가 뜨면
body.keyboard-open+--kb-height로 시트 높이를 줄입니다. 웹 모달에는 옮기지 않습니다. - ⚠️ 글자 배율 보정 — 직원 앱은 화면 설정을
body { zoom }으로 걸어100dvh가 배율만큼 넘칩니다.apps/employee-app/src/styles/main.css의html[data-font-scale="lg"] .modal-sheet--full, … .ds-modal--full선택자에 새 풀레이어 클래스를 같이 넣어야 합니다. 빠뜨리면 기본 배율(1.2)에서만 하단 바가 화면 밖으로 밀리고, 개발자 브라우저(1.0)에서는 멀쩡해 보입니다. - iOS 에서 14px 입력칸을 탭하면 자동 확대되는 문제는 아직 규칙이 없습니다 → 모달 · iOS 자동 확대.
하단 버튼
| 변형 | 클래스 | 모양 |
|---|---|---|
| 고정 바(기본) | .modal-full__footer | 시트 바닥에 고정 · 흰 바탕 · 위 12 · 좌우 12 · 아래 16 + safe-area · 버튼 사이 8 |
| 본문 끝 | .modal-full__footer--flow | 본문 안 마지막 자식 — 내용이 짧으면 바닥까지 내려가고 길면 내용 끝에 붙음(신청서 4종) |
- 버튼은
ds-btn--lg, 둘이면 반반(flex: 1). - 둘까지. 셋이면 각각 1/3 로 쪼개져 라벨이 줄바꿈됩니다 — 「취소」는 빼고 제목 줄의 X 에 맡깁니다.
닫기
- 닫는 길은 X 하나(+ 안드로이드 시스템 뒤로, 하단 「완료」류 버튼). 시트가 화면 전체를 덮어 휴대폰에는 「바깥」이 없으므로 딤 클릭으로 닫는 동작에 기대지 않습니다.
- 써 넣은 것이 있으면 닫기 전에 묻습니다(신청서 —
requestCloseForm). 저장 확인은 컨펌 다이얼로그입니다. - 엣지 스와이프로는 닫지 않습니다(위).
공용 모달을 풀레이어로 — .ds-modal--full
공용 템플릿의 모달(불편 · 오류 신고)을 직원 앱에서 띄우면, 가운데 뜬 카드 대신 같은 풀레이어로 그립니다. 호스트가 켭니다.
<!-- 직원 앱 index.html -->
<div x-data="csReport({ fullLayer: true })" data-cs-report-host>.ds-modal--full 은 일반 모달의 표시 변형이라 __header/__title/__body/__footer 구조는 그대로이고, 직원 앱에서는 위와 같은 값(좌우 12 · 제목 규격 · X 위치)을 받습니다. 제목 색만 DS label-normal 그대로입니다(.ds-modal__title 에 색을 얹지 않는 규칙). 켜는 방법 · 폭과의 관계 → 모달 · 풀레이어.
움직임 — 아래 → 위
시트가 화면 아래 밖에서 제자리로 올라오고(딤은 함께 짙어짐), 닫으면 아래 밖으로 내려갑니다(딤은 함께 옅어짐). 시트만 움직입니다 — 루트(딤)째 움직이면 딤까지 같이 올라와 화면이 통째로 밀려 오는 것처럼 읽힙니다.
x-if 로 여는 팝업 — x-layer-if
직원 앱 풀레이어 팝업은 열 때마다 폼을 새로 그리려고 x-if 를 씁니다. x-if 는 조건이 꺼지는 순간 DOM 을 지워 이탈 애니메이션을 걸 수 없으므로, x-if 를 x-layer-if 로 바꿉니다(위 구조의 마크업). 나머지는 그대로입니다.
- 열 때 —
x-if와 똑같이 새로 그린 뒤 시트를 아래에서 올립니다. - 닫을 때 — 팝업을 먼저 Alpine 에서 떼고(그 순간의 모습으로 굳힘) 아래로 내린 뒤 지웁니다. 닫으면서 비운 상태(
selectedPayslip = null등)에 바인딩이 다시 반응해 빈 화면이 된 채 내려가지 않게 하려는 것입니다. 내려가는 동안에는 터치가 아래 화면으로 갑니다. - 내려가는 도중 다시 열면 남은 한 장을 바로 지우고 새로 올립니다 — 두 장이 겹치지 않습니다.
- 올라오는 도중 닫으면 지금 위치에서 이어 내려갑니다.
x-show 로 여는 팝업 — x-layer-page
공용 모달은 x-show 로 열고 닫으므로 루트(딤)에 x-layer-page 를 붙입니다. 값을 주면 조건부입니다.
<div x-show="isOpen" x-cloak x-layer-page="fullLayer" class="ds-modal-backdrop ds-modal-backdrop--report">
<div class="ds-modal" :class="fullLayer ? 'ds-modal--full' : 'mx-4'"> … </div>
</div>x-layer-page 는 직원 앱이 등록하는 디렉티브라, 같은 공용 템플릿을 카드 모달로 쓰는 다른 앱(admin 등)에서는 아무 일도 하지 않습니다.
적용 현황 — 직원 앱
| 종류 | 화면 |
|---|---|
풀레이어 팝업 · x-layer-if | 휴가 신청 · 연장근무 신청 · 외근 신청 · 주말 당직 세션 신청 · 연장근무 보고서 · 외근 보고서 · 출퇴근 정정 · 서류 제출 · 인센티브 등록 · 결재자 지정(신청서 「변경」) · 급여명세서 상세 |
풀레이어 팝업 · x-layer-page | 불편 · 오류 신고(공용 cs-report.html, fullLayer 일 때) |
2depth · x-depth-page | 결재 상세(신청 · 받은 결재) · 나의 결재선 · 결재선 편집 · 결재자 지정 · 급여명세서 · 근무 기록 · 근무 설정 · 근무 형태 변경 · 팀 근태 · 내 정보 · 화면 설정 · 서명 · 알림 · 앱 정보 · 드라이브 · AI 어시스턴트 · 홈 할 일 · 공지 · 축하 · 메신저 대화방 · 연락처 프로필 · 공지 상세 |
새 화면을 만들면 — 「뒤로(<)」 화면이면 x-depth-page, 「닫기(X)」 풀레이어 팝업이면 x-layer-if(또는 x-layer-page)를 붙이고 위 표에 한 줄을 더합니다.
단일 출처
| 파트 | 파일 |
|---|---|
| 2depth 전환 | apps/employee-app/src/directives/depth-page.ts |
| 풀레이어 팝업 전환 | apps/employee-app/src/directives/layer-page.ts |
| 전환 길이 · 곡선 | apps/employee-app/src/directives/page-motion.ts |
| 엣지 스와이프 | apps/employee-app/src/utils/edge-swipe-back.ts · 켜는 곳 capacitor-init.ts |
풀레이어 팝업 스타일(.modal-sheet--full · .modal-full__*) · 2depth 하단 버튼(.page-footer-cta) · 좌우 12 | apps/employee-app/src/styles/main.css |
| 2depth 헤더 | packages/components/html/app-header.html → 앱 헤더 |
공용 풀레이어(.ds-modal--full) | packages/static/styles/design-system.css → 모달 |