Android Navigation Drawer(Sliding Menu) Kullanımı

20-03-2014
Navigation drawer ekranın sol tarafından bulunan, uygulamanın ana navigasyon seçeneklerini içeren bir paneldir. Çoğu zaman gizlidir, fakat kullanıcı parmağını ekranın sol kenarından sağa doğru kaydırdığı zaman veya uygulamanın en üstünde bulunan uygulama ikonuna bastığında ortaya çıkartabilir.
Sliding menü olarak geçen bu yapı Android 3 ile gelmiştir. Navigation drawer ile genelde ekran boyutu küçük olan cihazlara yönelik geliştirilen uygulamalarda çok rahat kullanım sağlamaktadır. Çünkü bu paneli dilediğimiz zaman açıp gizleyebiliriz.

Android 3.0(API Level 11) gelen bu özelliği Android 2.1 (API Level 7) ve üst versiyonlarda kullanabilmek için gereken işlemleri detaylı bir şekilde inceleyelim.

Öncelikle şunu hatırlatmakta fayda var: Android'te yeni versiyonlarda çıkmış bir özelliğin önceki versiyonlarda kullanılabilmesi için destek kütüphaneleri(support library) kullanılmaktadır. Bundan dolayı bu uygulamamızda biz de support library kullanacağız.

Şimdi uygulamayı geliştirmeye başlayalım:

res/layout/activity_main.xml dosyası

<android.support.v4.widget.drawerlayout xmlns:android="
        android:id="@+id/drawer_layout"
        android:layout_width="match_parent"
        android:layout_height="match_parent">
        
    <EditText
            android:id="@+id/txtMain"
            android:inputType="textMultiLine"
            android:minLines="6"
            android:gravity="top|left"
            android:layout_height="wrap_content"
            android:layout_width="fill_parent"
            android:scrollbars="vertical"/>
        
    <ListView
            android:id="@+id/left_drawer"
            android:layout_width="240dp"
            android:layout_height="match_parent"
            android:layout_gravity="start"
            android:choiceMode="singleChoice"
            android:divider="@android:color/transparent"
            android:dividerHeight="0dp"
            android:background="#111"/>
</android.support.v4.widget.DrawerLayout >


XML dosyalarında sıralama z-index sıralamasını ima eder. activity_main dosyası bir xml dosyası olduğu için ikinci sırada bulunan ListView EditText'in z-index'inden daha büyüktür. Bundan dolayı ListView açılıp kapandığında EditText ListView ekranda gösterildiğinde altta kalacaktır, ListView ise üstte kalacaktır.

android:layout_gravity="start" ile DrawerLayout'un soldan sağa doğru okunan dillerde sliding drawer'in sol tarafta, sağdan sola doğru okunan dillerde ise sağdan sola doğru açılır. Türkçe veya İngilizce dilinde cihazınızı kullanıyorsanız soldan sağa doğru, Arapça olarak kullanıyorsanız sağdan sola doğru açılır.

android:layout_width="240dp" ile DrawerLayout'un kaç dp genişliğe sahip olacağını ifade ediyoruz.


res/layout/drawer_list_item.xml dosyası

<TextView xmlns:android="
    android:id="@android:id/text1"
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:textAppearance="@android:style/TextAppearance.Medium"
    android:gravity="center_vertical"
    android:paddingLeft="16dp"
    android:paddingRight="16dp"
    android:textColor="#fff"
    android:background="@drawable/list_selector_activated_holo_dark"
    android:minHeight="48dip"/>


Bu dosyada bulunan TextView nesnesi Activity sınıfının onCreate metodunda ArrayAdapter ile kullanılacaktır. Navigation drawer uygulamamızda sliding menüdeki elemanlar textview olarak gösterilmesi bu dosya ila sağlanacaktır.

android:background= "@drawable/list_selector_activated_holo_dark" değeri ile sliding menünün arka plan renginin ne olacağını ifade ediyoruz. Bu dosyayı projenize eklediğiniz zaman android:background değeri altı çizili olarak gösteriliyorsa, res/drawable-hdpi dosyasına bu resmi indirip kopyalamanız gerekir.

Eğer Android 3.1 ve üstü sürümler için uygulama geliştiriyorsanız aşağıdaki kodları kullanınız:

<TextView xmlns:android="
    android:id="@android:id/text1"
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:textAppearance="?android:attr/textAppearanceListItemSmall"
    android:gravity="center_vertical"
    android:paddingLeft="16dp"
    android:paddingRight="16dp"
    android:textColor="#fff"
    android:background="?android:attr/activatedBackgroundIndicator"
    android:minHeight="?android:attr/listPreferredItemHeightSmall"/>



AndroidManifest.xml dosyası

<?xml version="1.0"encoding="utf-8"?>
<manifest xmlns:android="
          package="mucayufa.android.navigationDrawer.android7"
          android:versionCode="1"
          android:versionName="1.0">
    <uses-sdk android:minSdkVersion="7"/>
    <application android:label="@string/app_name"android:icon="@drawable/icon">
        <activity android:name=".MainActivity"
                  android:label="@string/app_name"
                  android:theme="@style/Theme.AppCompat.Light.DarkActionBar"
                  android:launchMode="singleTop"> <!--alt sinifta up ikonuna basildiginda ana activity sinifina doner-->
            <intent-filter >
                <action android:name="android.intent.action.MAIN"/>
                <category android:name="android.intent.category.LAUNCHER"/>
            </intent-filter >
        </activity >
    </application >
</manifest >


Görüldüğü gibi android minSdkVersion 7 olarak belirtildi. Burada dikkat edilmesi gereken en önemli husus şudur: android:theme ifadesinin aldığı değer android.support_compatibility-v7-appcompat_19 kütüphanesinin res/values/themes.xml dosyası içinde tanımlanmıştır.

Android 3 ve üstü sürümlerde android:theme tanımlamaya gerek yoktur. Ayrıca minSdkVersion 11 olarak değiştirilmelidir.

Android support kütüphanelerini eklemek için maven kullanıcıları aşağıdaki dependency'leri eklemelidir:

<dependency>
    <groupId>android.support</groupId>
    <artifactId>compatibility-v4</artifactId>
    <version>19</version>
</dependency>
<dependency>
    <groupId>android.support</groupId>
    <artifactId>compatibility-v7-appcompat</artifactId>
    <version>19</version>
    <type>apklib</type>
</dependency>
<dependency>
    <groupId>android.support</groupId>
    <artifactId>compatibility-v7-appcompat</artifactId>
    <version>19</version>
    <type>jar</type>
</dependency>


Bu dependency'ler mvnrepository sitesinde bulunmadığı için maven-android-sdk-deployer-master dosyasını indirip açtıktan sonra o dizinde

mvn install -P 2.2


komutunu çalıştırmaları gerekmektedir(Burada 2.2 Android versiyonunu temsil etmektedir. Örneğin Android 4.3 versiyonu için uygulama geliştiriyorsanız 2.2 yerine 4.3 yazmanız yeterlidir). Daha sonra bu dizinde bulunan extras/compatibility-v7-appcompat dizinine giderek şu komutu çalıştırmalıyız:
mvn clean install


Tüm bu işlemler tamamlandıktan sonra maven kullanıcıları sorunsuz bir şekilde compatibility paketlerini kullanabilir. Eclipse Ide ile proje geliştiren kullanıcılar ise sırasıyla şu işlemleri yapmalıdır:
File >> Import…  >> Android (folder)  >> Existing Android Code Into Workspace
Browse to your sdk directory <sdk>/extras/android/support/v7/appcompat/
Click Finish
Right-click on the application -> properties...
Select Android from the left menu
Under Library section Click Add… button
Select android-support-v7-appcompat
Click OK


MainActivity Sınıfı

package mucayufa.android.navigationDrawer.android7;
       
import android.content.res.Configuration;
import android.os.Bundle;
import android.support.v4.app.ActionBarDrawerToggle;
import android.support.v4.view.GravityCompat;
import android.support.v4.widget.DrawerLayout;
import android.support.v7.app.ActionBarActivity;
import android.view.MenuItem;
import android.view.View;
import android.widget.*;
       
public class MainActivity extends ActionBarActivity {
    private DrawerLayout mDrawerLayout;
    private ListView mDrawerList;
    private ActionBarDrawerToggle mDrawerToggle;
       
    private CharSequence mDrawerTitle;
    private CharSequence mTitle;
    private String[] mOperationList;
    private EditText mTxtMain;
       
       
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super .onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
       
        mTxtMain = (EditText) findViewById(R.id.txtMain);
        mTitle = mDrawerTitle = getTitle();
        mOperationList = getResources().getStringArray(R.array.operation_list);
        mDrawerLayout = (DrawerLayout) findViewById(R.id.drawer_layout);
        mDrawerList = (ListView) findViewById(R.id.left_drawer);
       
        // set a custom shadow that overlays the main content when the drawer opens
        mDrawerLayout.setDrawerShadow(R.drawable.drawer_shadow, GravityCompat.START);
        // set up the drawer's list view with items and click listener
        mDrawerList.setAdapter(new ArrayAdapter<String>(this ,
                R.layout.drawer_list_item, mOperationList));
        mDrawerList.setOnItemClickListener(new DrawerItemClickListener());
       
        // enable ActionBar app icon to behave as action to toggle nav drawer
        getSupportActionBar().setDisplayHomeAsUpEnabled(true );
        getSupportActionBar().setHomeButtonEnabled(true );
       
        //ActionBarDrawerToggle sinifi sliding drawer ile
        //action bar uygulama ikonu arasinda uyumlu bir entegrasyon saglar
        mDrawerToggle = new ActionBarDrawerToggle(
                this ,                  //uzerinde islem yapacagi Activity sinifi 
                mDrawerLayout,         //DrawerLayout nesnesi 
                R.drawable.ic_drawer,   // 'Up' caret ile yer degisecek ikon 
                R.string.drawer_open,   // "open drawer" erisim icin tanim 
                R.string.drawer_close   // "close drawer" erisim icin tanim 
        ) {
            public void onDrawerClosed(View view) {
                getSupportActionBar().setTitle(mTitle);
                invalidateOptionsMenu(); // onPrepareOptionsMenu() metodunu cagrir
            }
       
            public void onDrawerOpened(View drawerView) {
                getSupportActionBar().setTitle(mDrawerTitle);
                invalidateOptionsMenu(); // onPrepareOptionsMenu() metodunu cagrir
            }
        };
        mDrawerLayout.setDrawerListener(mDrawerToggle);
       
        if (savedInstanceState == null ) {
            selectItem(0);
        }
       
    }
    //The click listner for ListView in the navigation drawer 
    private class DrawerItemClickListener implements ListView.OnItemClickListener {
        @Override
        public void onItemClick(AdapterView<?> parent, View view, int position, long id) {
            selectItem(position);
        }
    }
       
    /**
     * Navigation Drawer'da App icona basildiginda acilmasi icin gerekli metodtur
     * @param item
     * @return
     */
    @Override
    public boolean onOptionsItemSelected(MenuItem item) {
        //ActionBarDrawerToggle'a meydana gelen eventi aktarir. Bu metodtan donen deger true olursa
        //uygulama ikonunun tıklama eventi tarafindan handle edilir
        if (mDrawerToggle.onOptionsItemSelected(item)) {
            return true ;
        }
        return super .onOptionsItemSelected(item);
    }
    private void selectItem(int position) {
        String toBeAdded = "";
        switch (position) {
            case 0:
                toBeAdded="Hello World";
                break ;
            case 1:
                toBeAdded = "";
                break ;
       
        }
        mTxtMain.setText(toBeAdded);
        // update selected item and title, then close the drawer
        mDrawerList.setItemChecked(position, true );
        setTitle(mOperationList[position]);
        mDrawerLayout.closeDrawer(mDrawerList);
    }
       
    @Override
    public void setTitle(CharSequence title) {
        mTitle = title;
        getSupportActionBar().setTitle(mTitle);
    }
       
    /**
     * When using the ActionBarDrawerToggle, you must call it during
     * onPostCreate() and onConfigurationChanged()...
     */
    @Override
    protected void onPostCreate(Bundle savedInstanceState) {
        super .onPostCreate(savedInstanceState);
        // Sync the toggle state after onRestoreInstanceState has occurred.
        mDrawerToggle.syncState();
    }
       
    @Override
    public void onConfigurationChanged(Configuration newConfig) {
        super .onConfigurationChanged(newConfig);
        // Pass any configuration change to the drawer toggls
        mDrawerToggle.onConfigurationChanged(newConfig);
    }
}


Dikkat edersek MainActivity sınıfı Activity sınıfını extend etmemiş, bunun yerine ActionBarActivity sınıfını extend etmiş. Çünkü onCreate() metodu içerisinde bulunan

//enable ActionBar app icon to behave as action to toggle nav drawer
getSupportActionBar().setDisplayHomeAsUpEnabled(true );
getSupportActionBar().setHomeButtonEnabled(true );


satırlardaki getSupportActionBar() metodu ActionBarActivity sınıfından gelmektedir. API Level 11'e göre uygulama geliştiriyor olsaydık Activity sınıfını extend ettikten sonra getSupportActionBar() metodu yerine getActionBar() metodu kullanmamız gerekecekti.

© 2019 Tüm Hakları Saklıdır. Codesenior.COM