Drawer — 정의, DrawerLayout 및 앱의 사이드 메뉴

저자: IT Sectr 게시일: 2026-02-23 읽는 시간: 12 분

Drawer(Navigation Drawer)는 화면의 왼쪽(또는 오른쪽) 가장자리에서 슬라이드되어 나오는 대화형 패널로, 내비게이션 링크를 표시합니다. Android에서는 DrawerLayout, iOS에서는 SideMenu와 같은 커스텀 솔루션이나 iPad의 표준 UISplitViewController를 통해 구현됩니다. 사양에 대한 자세한 내용은 Material Design 3 문서를 참조하세요.

핵심 요점

  • Drawer — 스와이프 또는 햄버거 아이콘 탭으로 슬라이드되는 사이드 내비게이션 메뉴
  • DrawerLayout — 슬라이딩 메뉴 구현을 위한 Android 표준 컨테이너
  • SideMenu — 커스터마이징 가능한 사이드 메뉴를 위한 인기 iOS 라이브러리
  • Modal Drawer — 콘텐츠를 오버레이하며, 내비게이션에 집중하기 위해 사용
  • Standard Drawer — 콘텐츠를 오른쪽으로 밀어내며 일부를 보이게 함

Drawer란?

Drawer(Navigation Drawer)는 스와이프 제스처 또는 햄버거 아이콘(세 개의 가로선) 탭을 통해 화면 왼쪽 가장자리에서 슬라이드되는 패널 형태의 내비게이션 요소입니다. Drawer에는 내비게이션 링크, 헤더 및 선택적 요소(사용자 아바타, 알림 배지, 구분선)가 포함됩니다. 패널은 콘텐츠를 오버레이(Modal)하거나 밀어낼(Standard) 수 있습니다.

Material Design 3(2026)는 Navigation Drawer를 6개 이상의 내비게이션 항목이 있는 앱의 구성 요소로 정의합니다. Bottom Navigation과 달리 Drawer는 화면에서 영구적인 공간을 차지하지 않으며 사용자 요청 시에만 표시됩니다. 이는 콘텐츠 공간을 확보하지만 열기 위한 추가 작업이 필요합니다. Google은 섹션 계층 구조가 깊은 앱에 Drawer를 권장합니다.

UX Planet 연구(2025)에 따르면: Drawer는 5~15개 섹션이 있는 앱에 적합하지만, 내비게이션 시간이 Bottom Navigation보다 40% 더 깁니다. 사용자는 화면 접힘(스크롤) 아래에 있는 메뉴 항목을 놓치는 경우가 많습니다. 따라서 중요한 섹션은 Drawer 상단에, 덜 중요한 섹션(앱 정보, 설정)은 하단에 구분선으로 분리하여 배치해야 합니다.

Drawer 유형: Modal 및 Standard

Modal Drawer는 콘텐츠 위로 슬라이드되며 배경을 어둡게 합니다. 화면 너비가 제한된 모바일 기기에서 사용됩니다. 항목을 선택하면 Drawer가 자동으로 닫힙니다. Standard Drawer(Permanent)는 항상 표시되는 고정 패널로, 콘텐츠를 밀어냅니다. 900 dp 이상의 화면 너비를 가진 태블릿 및 데스크톱에서 사용됩니다. Material 3는 Rail Drawer도 정의합니다—아이콘만 표시하는 태블릿용 컴팩트 버전입니다.

유형동작용도
Modal콘텐츠 오버레이, 배경 어두워짐전화, 임시 내비게이션
Standard콘텐츠 밀어냄, 고정태블릿, 데스크톱(900+ dp)
Rail아이콘이 있는 컴팩트 사이드 패널태블릿, 적응형 내비게이션

Android의 DrawerLayout

DrawerLayout은 슬라이딩 사이드 메뉴를 구현하는 Android의 표준 ViewGroup입니다. DrawerLayout에는 두 개의 하위 요소가 있습니다: 첫 번째는 메인 콘텐츠(NavHostFragment가 있는 FrameLayout), 두 번째는 메뉴가 있는 NavigationView입니다. DrawerLayout은 ActionBarDrawerToggle을 통해 스와이프 제스처와 프로그래매틱 열기/닫기를 처리합니다.

kotlin
// DrawerLayout 및 NavigationView를 사용한 액티비티
class MainActivity : AppCompatActivity() {

    private lateinit var binding: ActivityMainBinding
    private lateinit var drawerLayout: DrawerLayout

    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        binding = ActivityMainBinding.inflate(layoutInflater)
        setContentView(binding.root)

        drawerLayout = binding.drawerLayout
        val navView = binding.navView
        val navController = findNavController(R.id.nav_host_fragment)

        // Navigation Component에 Drawer 연결
        NavigationUI.setupActionBarWithNavController(
            this, navController, drawerLayout
        )
        NavigationUI.setupWithNavController(navView, navController)
    }

    override fun onSupportNavigateUp(): Boolean {
        return NavigationUI.navigateUp(
            findNavController(R.id.nav_host_fragment),
            drawerLayout
        )
    }
}

// XML: activity_main.xml
// <androidx.drawerlayout.widget.DrawerLayout
//   android:id="@+id/drawerLayout"
//   ...>
//   <!-- 메인 콘텐츠 -->
//   <FrameLayout android:id="@+id/nav_host_fragment"
//     android:layout_width="match_parent"
//     android:layout_height="match_parent" />
//   <!-- Navigation Drawer -->
//   <com.google.android.material.navigation.NavigationView
//     android:id="@+id/navView"
//     android:layout_width="wrap_content"
//     android:layout_height="match_parent"
//     android:layout_gravity="start"
//     app:menu="@menu/nav_menu" />
// </androidx.drawerlayout.widget.DrawerLayout>

NavigationView는 Drawer 콘텐츠를 위한 Material Design 구성 요소입니다. 헤더(headerLayout), 메뉴 항목(menu), 부제목, 체크박스 및 스위치를 지원합니다. app:menu 속성은 내비게이션 항목이 있는 XML 메뉴를 가리킵니다. NavigationUI는 자동으로 활성 항목을 강조 표시하고 NavController와 상태를 동기화합니다.

iOS의 사이드 메뉴

iOS에는 기본 제공 "Drawer" 구성 요소가 없습니다—Apple은 iPhone에서 사이드 메뉴를 권장하지 않습니다(HIG, 2026). 그러나 iPad의 경우 기본 및 보조 패널이 있는 UISplitViewController가 사용됩니다. iPhone의 경우 사이드 메뉴는 타사 라이브러리(SideMenu, SwiftUI-side-menu) 또는 콘텐츠 오프셋이 있는 커스텀 솔루션을 통해 구현됩니다. SwiftUI에서는 오프셋 애니메이션이 있는 ZStack을 통해 사이드 메뉴가 생성됩니다.

swift
import SwiftUI

struct DrawerView<Content: View, Menu: View>: View {
    let menuWidth: CGFloat = 280

    @Binding var isOpen: Bool
    @ViewBuilder let content: Content
    @ViewBuilder let menu: Menu

    var body: some View {
        ZStack(alignment: .leading) {
            content
                .offset(x: isOpen ? menuWidth : 0)
                .animation(.easeInOut, value: isOpen)

            if isOpen {
                menu
                    .frame(width: menuWidth)
                    .transition(.move(edge: .leading))

                Color.black.opacity(0.3)
                    .ignoresSafeArea()
                    .onTapGesture { isOpen = false }
            }
        }
    }
}

// 사용법
struct ContentView: View {
    @State private var showDrawer = false

    var body: some View {
        DrawerView(isOpen: $showDrawer) {
            NavigationStack {
                HomeView()
                    .toolbar {
                        ToolbarItem(placement: .navigationBarLeading) {
                            Button(action: { showDrawer.toggle() }) {
                                Image(systemName: "line.horizontal.3")
                            }
                        }
                    }
            }
        } menu: {
            DrawerMenuView()
        }
    }
}

프로덕션 iOS 프로젝트에서는 SideMenu 라이브러리가 자주 사용됩니다(GitHub, 8k+ 스타). 제스처 지원, 배경 블러, 커스텀 너비 및 애니메이션을 갖춘 준비된 UIViewController를 제공합니다. SideMenu는 왼쪽 및 오른쪽 메뉴, 여러 레벨 및 UINavigationController를 통한 UIKit 통합을 지원합니다. 대안은 iPad의 UISplitViewController(시스템, 커스텀 애니메이션 없음)입니다.

Drawer 커스터마이징: 헤더, 아이콘, 섹션

Drawer는 광범위한 커스터마이징이 가능합니다. Android에서 NavigationView는 headerLayout을 지원합니다—메뉴 항목 위에 배치되는 커스텀 레이아웃입니다. 아바타, 사용자 이름, 이메일 및 커버 이미지를 포함할 수 있습니다. 메뉴 항목은 부제목, 구분선 및 스위치가 있는 <menu>를 통해 그룹화됩니다. iOS에서 SideMenu 커스터마이징에는 배경색, 블러, 너비 및 모서리 반경 설정이 포함됩니다.

kotlin
// NavigationView용 커스텀 헤더
val headerView = binding.navView.inflateHeaderView(R.layout.nav_header)
headerView.findViewById<ImageView>(R.id.iv_avatar)
    .setImageResource(R.drawable.avatar)
headerView.findViewById<TextView>(R.id.tv_name)
    .text = "John Doe"

// 메뉴 항목 구성
val menuItem = binding.navView.menu.findItem(R.id.nav_notifications)
menuItem.isChecked = true

// 배지 추가
val badge = binding.navView.getOrCreateBadge(R.id.nav_notifications)
badge.number = 15
badge.isVisible = true

Material Design은 다음 Drawer 구조를 권장합니다: 헤더(이름, 아바타), 기본 내비게이션 항목(5~8개), 구분선, 보조 항목(설정, 도움말), 푸터(앱 정보, 버전). Material 3에서 NavigationView는 itemShape 및 itemBackground를 통한 커스텀 활성 항목 강조 표시도 지원합니다.

Drawer 사용 시기: UX 권장 사항

Drawer는 6개 이상의 섹션, 설정 및 도움말 페이지가 있는 앱에 효과적입니다. 섹션에 대한 빠른 접근이 중요한 앱에는 적합하지 않습니다—이러한 경우 Bottom Navigation이 더 좋습니다. Material Design은 Drawer와 Bottom Navigation을 결합할 것을 권장합니다: 기본 내비게이션 — Bottom(3~5개 탭), 추가 — Drawer(설정, 도움말, 앱 정보).

Drawer 구현 시 일반적인 실수: 과부하된 메뉴(그룹화 없이 15개 이상 항목), 접힘 아래에 중요한 섹션 숨김, 아이콘 부족(아이콘 없는 텍스트는 스캔 속도가 30% 느림), 지연이 있는 애니메이션(200 ms 이하여야 함). 모범 사례: 사용자 이름이 있는 헤더, 각 항목의 아이콘, 그룹 간 구분선, 활성 섹션 강조, 열기를 위한 스와이프 제스처 지원.

  • 6+ 섹션 — Drawer가 적합, 더 적으면 Bottom Navigation 사용
  • 아이콘 — 각 항목에 필수, 시각적 검색 속도 향상
  • 그룹화 — 기본 항목과 보조 항목 사이의 구분선
  • 헤더 — 개인화를 위한 아바타, 이름 및 이메일(소셜 앱)
  • 스와이프 제스처 — 열기에 필수, 햄버거 버튼으로 대체

자주 묻는 질문

Drawer와 Bottom Navigation의 차이점은?

Drawer는 제스처로 열리는 숨겨진 사이드 메뉴로, 6개 이상의 섹션과 깊은 계층 구조에 적합합니다. Bottom Navigation은 3~5개 섹션을 위한 항상 표시되는 하단 바입니다. Drawer는 화면 공간을 절약하지만 열기 위한 추가 작업이 필요하여 내비게이션 시간이 40% 증가합니다.

SwiftUI에 Drawer를 추가하는 방법은?

SwiftUI에는 기본 제공 Drawer가 없습니다. 위 예제와 같이 콘텐츠 오프셋과 애니메이션이 있는 ZStack을 사용하세요. 프로덕션의 경우 SideMenu(Swift Package) 또는 UISplitViewController의 커스텀 래퍼와 같은 라이브러리가 사용됩니다. iPad에서는 preferredDisplayMode .oneBesideSecondary와 함께 UISplitViewController를 사용하세요.

Apple이 iPhone에서 Drawer를 권장하지 않는 이유는?

Apple HIG(2026)는 사이드 메뉴가 콘텐츠를 숨기고 직접 조작 원칙을 위반한다고 명시합니다. iOS는 내비게이션에 Tab Bar를 권장합니다. iPhone의 Drawer는 기본 내비게이션이 아닌 설정 및 추가 작업에만 사용됩니다. iPad에서는 Drawer가 시스템 표준인 UISplitViewController로 대체됩니다.

Drawer의 스와이프 제스처를 처리하는 방법은?

Android에서 DrawerLayout은 왼쪽 가장자리에서의 스와이프를 자동으로 처리합니다. iOS에서 커스텀 Drawer에는 UIPanGestureRecognizer 또는 Edge Pan Gesture(SwiftUI — DragGesture가 있는 .gesture)가 필요합니다. 중요: 스와이프는 시스템 "뒤로" 제스처와 충돌해야 합니다—iOS에서 왼쪽 가장자리는 시스템 제스처가 차지하고 있습니다.

Drawer를 오른쪽에 만들 수 있나요?

네. Android에서 NavigationView에 android:layout_gravity="end"를 지정하세요. iOS에서 edge: .trailing으로 메뉴를 만드세요. 오른쪽 Drawer는 추가 옵션, 필터 또는 채팅에 덜 자주 사용됩니다. 기본 내비게이션은 Material Design 및 사용자 기대에 따라 왼쪽에 유지됩니다.

요약

  • Drawer — 6개 이상 섹션용 사이드 내비게이션 메뉴, 스와이프 또는 햄버거 탭으로 슬라이드
  • DrawerLayout(Android) — NavigationUI를 통한 Navigation Component 통합이 있는 표준 ViewGroup
  • SideMenu(iOS) — Apple이 기본 제공 구성 요소를 제공하지 않으므로 커스텀 Drawer용 인기 라이브러리
  • Modal vs Standard — Modal은 콘텐츠 오버레이(전화), Standard는 콘텐츠 밀어냄(태블릿 900+ dp)
  • 커스터마이징 — 아바타가 있는 헤더, 항목 그룹화, 배지, 활성 섹션 강조
  • UX — Drawer는 Bottom Navigation보다 40% 느리지만 깊은 계층 구조의 앱에 필요
  • Material 3 — NavigationView는 스타일, 아이콘, 배지 및 커스텀 헤더 레이아웃 지원

턴키 방식의 모바일 애플리케이션을 개발해 드립니다

IT Sectr는 2017년부터 스타트업과 기업을 위한 iOS 및 Android 애플리케이션을 만듭니다. 저희가 상담해 드리고 최적의 솔루션을 제안하겠습니다.

프로젝트 논의

더 읽어보기