본문 바로가기

안드로이드

바로가기 메뉴, Navigation Drawer

반응형

새 프로젝트를 만들 때 Nagivation Drawer Activity를 선택할 수 있다

 

 

/app/manifests/AndroidManifest.xml

<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
    package="com.example.a36_navigationdrawer">

    <application
        android:allowBackup="true"
        android:icon="@mipmap/ic_launcher"
        android:label="@string/app_name"
        android:roundIcon="@mipmap/ic_launcher_round"
        android:supportsRtl="true"
        android:theme="@style/Theme.A36_NavigationDrawer">
        <activity
            android:name=".MainActivity"
            android:label="@string/app_name"
            android:theme="@style/Theme.A36_NavigationDrawer.NoActionBar">
            <intent-filter>
                <action android:name="android.intent.action.MAIN" />

                <category android:name="android.intent.category.LAUNCHER" />
            </intent-filter>
        </activity>
    </application>

</manifest>

 

activity 태그 안에 theme 속성이 설정되어 있다. 기본으로 제공되는 테마가 아니라 직접 만든 테마를 설정하기 위한 것이다

 

/app/res/values/themes 폴더 안에 themes.xml 파일이다

기본 제공 테마가 아니라 상단의 액션바가 없는 스타일로 설정된다

    <style name="Theme.A36_NavigationDrawer.NoActionBar">
        <item name="windowActionBar">false</item>
        <item name="windowNoTitle">true</item>
    </style>

 

activity_main.xml에서 AppBarLayout 태그로 화면 상단에 액션바를 보여줄 수 있다

activity_main에서 직접 하지않고 app_bar_main.xml 파일로 분리되어있다

    <include
        android:id="@+id/app_bar_main"
        layout="@layout/app_bar_main"
        android:layout_width="match_parent"
        android:layout_height="match_parent" />

 

NavigationView가 바로가기 메뉴를 위한 뷰이다

축소 아이콘을 눌렀을 때만 보이게 하기 위해서 최상위 레이아웃은 DrawerLayout으로 되어있다

    <com.google.android.material.navigation.NavigationView
        android:id="@+id/nav_view"
        android:layout_width="wrap_content"
        android:layout_height="match_parent"
        android:layout_gravity="start"
        android:fitsSystemWindows="true"
        app:headerLayout="@layout/nav_header_main"
        app:menu="@menu/activity_main_drawer" />

 

 

activity_main.xml에 통합하고, FloatingActionButton 제거

<?xml version="1.0" encoding="utf-8"?>
<androidx.drawerlayout.widget.DrawerLayout 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:id="@+id/drawer_layout"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:fitsSystemWindows="true"
    tools:openDrawer="start">

    <androidx.coordinatorlayout.widget.CoordinatorLayout
        android:layout_width="match_parent"
        android:layout_height="match_parent">

        <com.google.android.material.appbar.AppBarLayout
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:theme="@style/Theme.A36_NavigationDrawer.AppBarOverlay">

            <androidx.appcompat.widget.Toolbar
                android:id="@+id/toolbar"
                android:layout_width="match_parent"
                android:layout_height="?attr/actionBarSize"
                android:background="?attr/colorPrimary"
                app:popupTheme="@style/Theme.A36_NavigationDrawer.PopupOverlay" />

        </com.google.android.material.appbar.AppBarLayout>

        <FrameLayout
            android:id="@+id/container"
            android:layout_width="match_parent"
            android:layout_height="match_parent"
            app:layout_behavior="@string/appbar_scrolling_view_behavior"></FrameLayout>

    </androidx.coordinatorlayout.widget.CoordinatorLayout>

    <com.google.android.material.navigation.NavigationView
        android:id="@+id/nav_view"
        android:layout_width="wrap_content"
        android:layout_height="match_parent"
        android:layout_gravity="start"
        android:fitsSystemWindows="true"
        app:headerLayout="@layout/nav_header_main"
        app:menu="@menu/activity_main_drawer" />
</androidx.drawerlayout.widget.DrawerLayout>

FrameLayout의 속성으로 app:layout_behavior 속성이 부여되었는데, CoordinatorLayout 안에서 해당 레이아웃이 스크롤 등의 작업이 진행 될 때 차지할 면적을 자동으로 계산하도록 한다

 

NavigationView 객체에는 headerLayout 속성과 menu 속성이 있다

headerLayout은 바로가기 메뉴의 상단에 표시되면서 사용자 프로필 등을 보여줄 수 있도록 하고

menu 속성은 그 아래에 메뉴를 보여줄 수 있도록 한다

 

이전의 fragment1.xml, fragment2.xml, fragment3.xml과 Fragment1, Fragment2, Fragment3 자바 파일을 복사해온다

 

FragmentCallback.java

package com.example.a36_navigationdrawer;

import android.os.Bundle;

public interface FragmentCallback {

    public void onFragmentSelected(int position, Bundle bundle);
}

 

MainAcitivity

package com.example.a36_navigationdrawer;

import android.os.Bundle;
import android.view.MenuItem;
import android.view.View;
import android.view.Menu;
import android.widget.Toast;

import com.google.android.material.snackbar.Snackbar;
import com.google.android.material.navigation.NavigationView;

import androidx.annotation.NonNull;
import androidx.appcompat.app.ActionBarDrawerToggle;
import androidx.appcompat.widget.Toolbar;
import androidx.core.view.GravityCompat;
import androidx.fragment.app.Fragment;
import androidx.fragment.app.FragmentHostCallback;
import androidx.navigation.NavController;
import androidx.navigation.Navigation;
import androidx.navigation.ui.AppBarConfiguration;
import androidx.navigation.ui.NavigationUI;
import androidx.drawerlayout.widget.DrawerLayout;
import androidx.appcompat.app.AppCompatActivity;

import com.example.a36_navigationdrawer.databinding.ActivityMainBinding;

import org.jetbrains.annotations.NotNull;

public class MainActivity extends AppCompatActivity implements NavigationView.OnNavigationItemSelectedListener, FragmentCallback {

    Fragment1 fragment1;
    Fragment2 fragment2;
    Fragment3 fragment3;

    DrawerLayout drawer;
    Toolbar toolbar;


    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        toolbar = findViewById(R.id.toolbar);
        setSupportActionBar(toolbar);

        drawer = findViewById(R.id.drawer_layout);
        ActionBarDrawerToggle toggle = new ActionBarDrawerToggle(this, drawer, toolbar, R.string.navigation_drawer_open, R.string.navigation_drawer_close);
        drawer.addDrawerListener(toggle);
        toggle.syncState();

        NavigationView navigationView = findViewById(R.id.nav_view);
        navigationView.setNavigationItemSelectedListener((NavigationView.OnNavigationItemSelectedListener) this);

        fragment1 = new Fragment1();
        fragment2 = new Fragment2();
        fragment3 = new Fragment3();

        getSupportFragmentManager().beginTransaction().add(R.id.container, fragment1).commit();
    }

    //    시스템 [BACK] 키를 눌렀을 때 호출되는 메소드
    @Override
    public void onBackPressed() {
        if (drawer.isDrawerOpen(GravityCompat.START)) {
            //    바로가기 메뉴가 열려있을 때 닫음
            drawer.closeDrawer(GravityCompat.START);
        } else {
            super.onBackPressed();
        }
    }

    @Override
    public boolean onNavigationItemSelected(MenuItem item) {
        int id = item.getItemId();

//        /app/res/menu/activity_main_drawer.xml
        if (id == R.id.nav_home) {
            Toast.makeText(this, "첫 번째 메뉴", Toast.LENGTH_SHORT).show();
            onFragmentSelected(0, null);
        } else if (id == R.id.nav_gallery) {
            Toast.makeText(this, "두 번째 메뉴", Toast.LENGTH_SHORT).show();
            onFragmentSelected(1, null);
        } else if (id == R.id.nav_slideshow) {
            Toast.makeText(this, "세 번째 메뉴", Toast.LENGTH_SHORT).show();
            onFragmentSelected(2, null);
        }

        drawer.closeDrawer(GravityCompat.START);

        return true;
    }

    @Override
    public void onFragmentSelected(int position, Bundle bundle) {
        Fragment currentFragment = null;

        if (position == 0) {
            currentFragment = fragment1;
            toolbar.setTitle("첫 번째 화면");
        } else if (position == 1) {
            currentFragment = fragment2;
            toolbar.setTitle("두 번째 화면");
        } else if (position == 2) {
            currentFragment = fragment3;
            toolbar.setTitle("세 번째 화면");
        }

        getSupportFragmentManager().beginTransaction().replace(R.id.container, currentFragment).commit();

    }
}
반응형

'안드로이드' 카테고리의 다른 글

브로드캐스트  (0) 2021.10.22
서비스  (0) 2021.10.22
ViewPager2로 여러 프래그먼트 간 슬라이드  (0) 2021.10.21
하단 탭 만들기  (0) 2021.10.20
상단 탭 만들기  (0) 2021.10.20