[안드로이드] 네비게이션 드로어 사용법
[안드로이드] 네비게이션 드로어 (Navigation drawer) 사용법
네비게이션 드로어는 화면 왼쪽 가장자리에 위치해 있고 앱을 탐색할 수 있는 하나의 패널입니다.
이걸 잘 활용한다면 특정 메뉴를 찾기 위해 클릭이 많이 일어나는 (Deep depth) 문제를 해결할 수 있습니다.
평상시에는 화면 밖에 가려져 있지만 왼쪽 스와이프나 왼쪽 상단 메뉴 버튼을 클릭하면 위 사진처럼 나옵니다.
그럼 네비게이션 드로어를 어떻게 구현하는지 알아보겠습니다.
1. Result
이번 포스팅에서 진행한 네비게이션 드로어 결과 화면
2. Step by Step
2-1. 안드로이드 서포트 라이브러리 추가
진행에 앞서 네비게이션 드로어는 서포트 라이브러리에 포함되어 있기 때문에 App Gradle 에 의존성 라이브러리를 넣어줘야합니다.
최근 안드로이드 스튜디오에서 새 프로젝트를 만들면 기본으로 서포트 라이브러리들이 들어가 있지만, 혹시 확인해보고 없으시다면 아래 라이브러리를 Gradle 에 추가해주세요.
build.gradle (app)
implementation 'com.android.support:design:27.1.1'
2-2. 네비게이션 메뉴 추가
네비게이션 드로어에서 보여줄 메뉴들을 추가합니다.
메뉴들에 포함되는 아이콘은 미리 /res/drawable/ 에 준비해주세요. ( New > Vector Asset 으로 추가하면 편합니다.)
_/res/menu/main_navigationmenu.xml
<?xml version="1.0" encoding="utf-8"?>
<menu xmlns:android="http://schemas.android.com/apk/res/android">
<group android:checkableBehavior="single">
<item
android:id="@+id/account"
android:icon="@drawable/ic_account_circle_black_24dp"
android:title="계정"
/>
<item
android:id="@+id/star"
android:icon="@drawable/ic_star_black_24dp"
android:title="즐겨찾기"
/>
<item
android:id="@+id/cart"
android:icon="@drawable/ic_shopping_cart_black_24dp"
android:title="장바구니"
/>
</group>
<group android:checkableBehavior="single">
<item
android:id="@+id/bug_report"
android:icon="@drawable/ic_bug_report_black_24dp"
android:title="버그 리포트"
/>
<item
android:id="@+id/setting"
android:icon="@drawable/ic_settings_black_24dp"
android:title="설정"
/>
<item
android:id="@+id/logout"
android:icon="@drawable/ic_exit_to_app_white_24dp"
android:title="로그아웃"
/>
</group>
</menu>
2-3. 네비게이션 헤더 추가 (Optional)
네비게이션 헤더 부분은 하셔도 되고, 내가 만들 앱에 필요 없으시면 굳이 안넣으셔도 됩니다.
헤더는 레이아웃이기 때문에 /res/layout 에 파일을 만들어주시면됩니다.
나중에 DrawerLayout 에서 헤더를 설정할 때 사용됩니다.
_/res/layout/main_navheader.xml
<?xml version="1.0" encoding="utf-8"?>
<android.support.constraint.ConstraintLayout
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto" xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="230dp"
android:background="@color/colorPrimary">
<ImageView
android:layout_width="wrap_content"
android:layout_height="150dp" tools:srcCompat="@tools:sample/avatars"
android:id="@+id/imageView"
app:layout_constraintStart_toStartOf="parent" android:layout_marginStart="24dp"
android:layout_marginTop="4dp" app:layout_constraintTop_toTopOf="parent"/>
<TextView
android:text="Charlie Park"
android:layout_width="wrap_content"
android:layout_height="0dp"
android:id="@+id/textView" app:layout_constraintStart_toStartOf="parent" android:layout_marginStart="24dp"
android:layout_marginTop="12dp" app:layout_constraintTop_toBottomOf="@+id/imageView"
android:textColor="#fff"/>
<TextView
android:text="kiwinam@test.com"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:id="@+id/textView2" android:textSize="10sp"
android:layout_marginTop="8dp" app:layout_constraintTop_toBottomOf="@+id/textView"
android:layout_marginStart="24dp" app:layout_constraintStart_toStartOf="parent" android:textColor="#fff"/>
</android.support.constraint.ConstraintLayout>
2-4. 메인 레이아웃 수정
네비게이션 드로어를 사용할 메인 레이아웃을 수정합니다.
여기서 포인트는 메인 레이아웃의 최상단 레이아웃이 DrawerLayout 이여야 네비게이션 드로어 가 정상적으로 동작합니다.
DrawerLayout 의 자식 레이아웃으로 NavigationView 를 설정해주시면 됩니다.
NavigationView 에서 방금 만든 메뉴와 헤더를 설정합니다.
_/res/layout/activitymain.xml
<?xml version="1.0" encoding="utf-8"?>
<!--parent layout-->
<android.support.v4.widget.DrawerLayout
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
android:id="@+id/drawerLayout"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:fitsSystemWindows="true"
>
<!-- main layout-->
<RelativeLayout
android:layout_width="match_parent" android:layout_height="match_parent"
android:background="#fff">
<android.support.v7.widget.Toolbar
android:id="@+id/toolbar"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:background="@color/colorPrimary"
app:contentInsetStart="0dp"
android:theme="@style/ThemeOverlay.AppCompat.Dark.ActionBar"
app:popupTheme="@style/ThemeOverlay.AppCompat.Dark.ActionBar"
/>
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="test"
android:layout_centerInParent="true"/>
</RelativeLayout>
<!--navigation drawer-->
<android.support.design.widget.NavigationView
android:id="@+id/navigationView"
android:layout_width="wrap_content"
android:layout_height="match_parent"
android:layout_gravity="start"
app:headerLayout="@layout/main_nav_header"
app:menu="@menu/main_navigation_menu"
/>
</android.support.v4.widget.DrawerLayout>
2-4. Activity 수정
네비게이션 드로어는 레이아웃 설정이 대부분이고 실제 코틀린이나 자바 코드는 많이 사용하지 않아도 구현 가능합니다.
이번 예제에서도 (1)메뉴 버튼을 눌렀을 때 네비게이션이 나오도록 처리하거나 (2)버튼 클릭 리스너를 설정해주는 코드만 넣어보겠습니다.
(1) 메뉴 버튼 클릭 시 네비게이션 드로어 열기
MainActivity.kt
// 툴바 메뉴 버튼이 클릭 됐을 때 콜백
override fun onOptionsItemSelected(item: MenuItem?): Boolean {
// 클릭된 메뉴 아이템의 아이디 마다 when 구절로 클릭시 동작을 설정한다.
when(item!!.itemId){
android.R.id.home->{ // 메뉴 버튼
drawerLayout.openDrawer(GravityCompat.START) // 네비게이션 드로어 열기
}
R.id.menu_search-> Snackbar.make(toolbar,"Search menu pressed",Snackbar.LENGTH_SHORT).show()
R.id.menu_account-> Snackbar.make(toolbar,"Account menu pressed",Snackbar.LENGTH_SHORT).show()
R.id.menu_logout-> Snackbar.make(toolbar,"Logout menu pressed",Snackbar.LENGTH_SHORT).show()
}
return super.onOptionsItemSelected(item)
}
- 메뉴 버튼이 클릭되면
drawerLayout.openDrawer(GravityCompat.START)
를 호출하여 네비게이션 드로어를 열어줍니다.
(2) 네비게이션 메뉴 버튼 클릭 리스너 설정
- 먼저 네비게이션 메뉴 클릭 리스너를 클래스에 implement 하겠습니다.
MainActivity.kt
class MainActivity : AppCompatActivity(), NavigationView.OnNavigationItemSelectedListener {
- 그런 다음 onNavigationItemSelected 메서드를 오버라이드하여 클릭 시 어떤 처리를 해줄지 설정합니다.
MainActivity.kt
// 네비게이션 드로어 메뉴 클릭 리스너
override fun onNavigationItemSelected(item: MenuItem): Boolean {
when(item.itemId){ // 네비게이션 메뉴가 클릭되면 스낵바가 나타난다.
R.id.account->Snackbar.make(toolbar,"Navigation Account pressed",Snackbar.LENGTH_SHORT).show()
R.id.setting->Snackbar.make(toolbar,"Navigation Setting pressed",Snackbar.LENGTH_SHORT).show()
}
drawerLayout.closeDrawers() // 기능을 수행하고 네비게이션을 닫아준다.
return false
}
이번 예제에서는 스낵바만 표시하도록 하였습니다.
스낵바를 표시한 다음 네비게이션 드로어를 닫아줌으로써 사용자 경험을 매끄럽게 해줍니다.
여기까지 구현 하였으면 기본적인 네비게이션 드로어 사용법은 다 알수 있습니다.
2-5. 뒤로가기 클릭 시 네비게이션 닫기 (Optional)
보통 사용자들이 네비게이션 드로어가 열려있을 때 뒤로가기 버튼을 누르면 네비게이션이 닫힐 것을 기대하는데, 이대로 코드를 진행하면 그렇게 동작하지 않습니다.
추가적으로 뒤로가기 버튼을 눌렀을 때 네비게이션 드로어를 닫아보겠습니다.
MainActivity.kt
/*
* 뒤로가기 버튼으로 네비게이션 닫기
*
* 네비게이션 드로어가 열려 있을 때 뒤로가기 버튼을 누르면 네비게이션을 닫고,
* 닫혀 있다면 기존 뒤로가기 버튼으로 작동한다.
*/
override fun onBackPressed() {
if(drawerLayout.isDrawerOpen(GravityCompat.START)){
drawerLayout.closeDrawers()
}else{
super.onBackPressed()
}
}
뒤로가기 버튼을 눌렀을 때 닫히는 네비게이션 드로어
3. Source Code
전체 소스코드는 GitHub 에 연동해놓았습니다.
읽어주셔서 감사합니다.
제 글이 도움 되길 바랄게요.
androidNavigation drawer네비게이션네비게이션 드로어안드로이드안드로이드 네비게이션 드로어
2018-12-29 10:35 +0900