Now a days most of the Android application are using Navigation Drawer/Sliding Drawer like view.
Some of them are using library for doing this. Android has also provided Navigation Drawer to achieve this.
http://developer.android.com/training/implementing-navigation/nav-drawer.html
In this above link we can find demo app to add navigation drawer in our app. But we have to use fragment for achieving this and it is recommend to use fragment.
But in case if we don't want to use fragment or we want to add Navigation Drawer in already existing app which contain activities and we don't want to replace them with fragment.
We can achieve same Navigation Drawer with activities too....I am going to add here demo app to add Navigation Drawer with multiple activities.
First of all we have to create on BaseActivity which will contain layout and all the code related to navigation drawer and then we will use this BaseActivity as parent activity to other activities.
We will extends this BaseActivity to all the other activities rather than directly extending Activity class in our activities. This way our all the activities will contain same Navigation Drawer without adding any extra code in every activity.
About Code:::
First of all we have to create XML file for adding navigation drawer, we will use this layout xml file in our BaseActivity.
navigation_drawer_base_layout.xml
<android.support.v4.widget.DrawerLayout
xmlns:android="http://schemas.android.com/apk/res/android"
android:id="@+id/drawer_layout"
android:layout_width="match_parent"
android:layout_height="match_parent" >
<FrameLayout
android:id="@+id/content_frame"
android:layout_width="match_parent"
android:layout_height="match_parent" />
<ListView
android:id="@+id/left_drawer"
android:layout_width="240dp"
android:layout_height="match_parent"
android:layout_gravity="start"
android:background="#111"
android:choiceMode="singleChoice"
android:divider="@android:color/transparent"
android:dividerHeight="0dp" />
</android.support.v4.widget.DrawerLayout>
As we are already adding layout in BaseActivity we can not add layout in child activity..otherwise it will not work properly so we will add our own layout for the child activity in FrameLayout of above XML.
/* Layout Inflater to add view in frame layout*/
Code Example :: getLayoutInflater().inflate(R.layout.activity_main, frameLayout);
This way we will get our own layout in child activity. Now we can use this as any other normal activity.
BaseActivity.java:
package com.navigation.drawer.activity;
import android.app.Activity;
import android.content.Intent;
import android.os.Bundle;
import android.support.v4.app.ActionBarDrawerToggle;
import android.support.v4.widget.DrawerLayout;
import android.view.Menu;
import android.view.MenuItem;
import android.view.View;
import android.widget.AdapterView;
import android.widget.AdapterView.OnItemClickListener;
import android.widget.ArrayAdapter;
import android.widget.FrameLayout;
import android.widget.ListView;
import android.widget.Toast;
/**
* @author dipenp
*
* This activity will add Navigation Drawer for our application and all the code related to navigation drawer.
* We are going to extend all our other activites from this BaseActivity so that every activity will have Navigation Drawer in it.
* This activity layout contain one frame layout in which we will add our child activity layout.
*/
public class BaseActivity extends Activity {
/**
* Frame layout: Which is going to be used as parent layout for child activity layout.
* This layout is protected so that child activity can access this
* */
protected FrameLayout frameLayout;
/**
* ListView to add navigation drawer item in it.
* We have made it protected to access it in child class. We will just use it in child class to make item selected according to activity opened.
*/
protected ListView mDrawerList;
/**
* List item array for navigation drawer items.
* */
protected String[] listArray = { "Item 1", "Item 2", "Item 3", "Item 4", "Item 5" };
/**
* Static variable for selected item position. Which can be used in child activity to know which item is selected from the list.
* */
protected static int position;
/**
* This flag is used just to check that launcher activity is called first time
* so that we can open appropriate Activity on launch and make list item position selected accordingly.
* */
private static boolean isLaunch = true;
/**
* Base layout node of this Activity.
* */
private DrawerLayout mDrawerLayout;
/**
* Drawer listner class for drawer open, close etc.
*/
private ActionBarDrawerToggle actionBarDrawerToggle;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.navigation_drawer_base_layout);
frameLayout = (FrameLayout)findViewById(R.id.content_frame);
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, listArray));
mDrawerList.setOnItemClickListener(new OnItemClickListener() {
@Override
public void onItemClick(AdapterView<?> parent, View view,
int position, long id) {
openActivity(position);
}
});
// enable ActionBar app icon to behave as action to toggle nav drawer
getActionBar().setDisplayHomeAsUpEnabled(true);
getActionBar().setHomeButtonEnabled(true);
// ActionBarDrawerToggle ties together the the proper interactions between the sliding drawer and the action bar app icon
actionBarDrawerToggle = new ActionBarDrawerToggle(
this, /* host Activity */
mDrawerLayout, /* DrawerLayout object */
R.drawable.ic_launcher, /* nav drawer image to replace 'Up' caret */
R.string.open_drawer, /* "open drawer" description for accessibility */
R.string.close_drawer) /* "close drawer" description for accessibility */
{
@Override
public void onDrawerClosed(View drawerView) {
getActionBar().setTitle(listArray[position]);
invalidateOptionsMenu(); // creates call to onPrepareOptionsMenu()
super.onDrawerClosed(drawerView);
}
@Override
public void onDrawerOpened(View drawerView) {
getActionBar().setTitle(getString(R.string.app_name));
invalidateOptionsMenu(); // creates call to onPrepareOptionsMenu()
super.onDrawerOpened(drawerView);
}
@Override
public void onDrawerSlide(View drawerView, float slideOffset) {
super.onDrawerSlide(drawerView, slideOffset);
}
@Override
public void onDrawerStateChanged(int newState) {
super.onDrawerStateChanged(newState);
}
};
mDrawerLayout.setDrawerListener(actionBarDrawerToggle);
/**
* As we are calling BaseActivity from manifest file and this base activity is intended just to add navigation drawer in our app.
* We have to open some activity with layout on launch. So we are checking if this BaseActivity is called first time then we are opening our first activity.
* */
if(isLaunch){
/**
*Setting this flag false so that next time it will not open our first activity.
*We have to use this flag because we are using this BaseActivity as parent activity to our other activity.
*In this case this base activity will always be call when any child activity will launch.
*/
isLaunch = false;
openActivity(0);
}
}
/**
* @param position
*
* Launching activity when any list item is clicked.
*/
protected void openActivity(int position) {
/**
* We can set title & itemChecked here but as this BaseActivity is parent for other activity,
* So whenever any activity is going to launch this BaseActivity is also going to be called and
* it will reset this value because of initialization in onCreate method.
* So that we are setting this in child activity.
*/
// mDrawerList.setItemChecked(position, true);
// setTitle(listArray[position]);
mDrawerLayout.closeDrawer(mDrawerList);
BaseActivity.position = position; //Setting currently selected position in this field so that it will be available in our child activities.
switch (position) {
case 0:
startActivity(new Intent(this, Item1Activity.class));
break;
case 1:
startActivity(new Intent(this, Item2Activity.class));
break;
case 2:
startActivity(new Intent(this, Item3Activity.class));
break;
case 3:
startActivity(new Intent(this, Item4Activity.class));
break;
case 4:
startActivity(new Intent(this, Item5Activity.class));
break;
default:
break;
}
Toast.makeText(this, "Selected Item Position::"+position, Toast.LENGTH_LONG).show();
}
@Override
public boolean onCreateOptionsMenu(Menu menu) {
getMenuInflater().inflate(R.menu.main, menu);
return super.onCreateOptionsMenu(menu);
}
@Override
public boolean onOptionsItemSelected(MenuItem item) {
// The action bar home/up action should open or close the drawer.
// ActionBarDrawerToggle will take care of this.
if (actionBarDrawerToggle.onOptionsItemSelected(item)) {
return true;
}
switch (item.getItemId()) {
case R.id.action_settings:
return true;
default:
return super.onOptionsItemSelected(item);
}
}
/* Called whenever we call invalidateOptionsMenu() */
@Override
public boolean onPrepareOptionsMenu(Menu menu) {
// If the nav drawer is open, hide action items related to the content view
boolean drawerOpen = mDrawerLayout.isDrawerOpen(mDrawerList);
menu.findItem(R.id.action_settings).setVisible(!drawerOpen);
return super.onPrepareOptionsMenu(menu);
}
/* We can override onBackPressed method to toggle navigation drawer*/
@Override
public void onBackPressed() {
if(mDrawerLayout.isDrawerOpen(mDrawerList)){
mDrawerLayout.closeDrawer(mDrawerList);
}else {
mDrawerLayout.openDrawer(mDrawerList);
}
}
}
package com.navigation.drawer.activity;
import android.os.Bundle;
import android.widget.ImageView;
/**
* @author dipenp
*
*/
public class Item1Activity extends BaseActivity {
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
/**
* We will not use setContentView in this activty
* Rather than we will use layout inflater to add view in FrameLayout of our base activity layout*/
/**
* Adding our layout to parent class frame layout.
*/
getLayoutInflater().inflate(R.layout.activity_main, frameLayout);
/**
* Setting title and itemChecked
*/
mDrawerList.setItemChecked(position, true);
setTitle(listArray[position]);
((ImageView)findViewById(R.id.image_view)).setBackgroundResource(R.drawable.image1);
}
}
Final view of our demo app:::
You can download demo code from below url:
https://drive.google.com/file/d/0B0mH97AUwQqhNUlxdmkwZ1JsNW8/edit?usp=sharing
------------------------------------------------------------------------------------------------------------
Attaching another demo example here as lots of visitors are getting confused how to add different layout on different activity and how to add icon on navigation list view.
As well as added header on listview to make it little bit attractive.
------------------------------------------------------------------------------------------------------------
Attaching another demo example here as lots of visitors are getting confused how to add different layout on different activity and how to add icon on navigation list view.
As well as added header on listview to make it little bit attractive.
You can download demo code from below url:
This comment has been removed by the author.
ReplyDeleteThank you for this helpful tutorial.I use it in my app.
ReplyDeleteAfter selecting option from navigation drawer it adds corresponding activity into activity stack,and as per my app requiement i had to avoid it.Normally activity was being popped out by pressing back button.
To avoid this i added noHistory=true in manifest and now it is working well,can you think of or suggest alternative way or above way is good?
hi bro, i am facing same problem ans noHistory not work. plz help me.
DeleteHi Hardik, Your solution seems fine....I will update you if find some other way to do the same...
ReplyDeleteI have problem for this , my AEID creater says direct running error ...help me ...truly
ReplyDeletedirect running permission is granted by superSU ...other project doing well but what happen to this .download file have same error
ReplyDeleteThis comment has been removed by the author.
ReplyDeleteI have a splashscreen and a home_activity.
ReplyDeleteIn both don't want to have the menu bar.
So, my splashcreen navigates with intent to home_activity and now, from home_activity i try to navigate with intent to BaseActivity as your example, in which BaseActivity is the launcher activity.
But when i press the button in home_activity, before it opens the BaseActivity i get a NullPointerException.
I get this error even if I changed the launcher activity in manifest to be BaseActivity, as you did.
Can you help me after I post my code of BaseActivity here maybe ?
Hi, If you are still facing same issue, please send me your code, I will check it.
DeleteI made it work.Thank you
DeleteHow Can I Put Images With Naigationbar with Activity....
ReplyDeleteHi, If I am not wrong...you need image with listview of navigation drawer.....for that, you can have custom listview with custom adapter in your code.....
DeleteThis comment has been removed by the author.
ReplyDeleteThanx for such a gr8 tutorial , it works.
ReplyDeleteHi , I have implemented Nav Drawer in my app. I use fragments to switch screens and it works just fine. But the problem is I want to add clickable buttons in my fragments (or activities, I might say). When clicked, the button should change screen to specific activity but I'm unable to add that code to fragment files. So what happens is : when I click on a button, the app crashes. Can you suggest a way to keep both ways of navigating within the app (i.e. using Nav Drawer & Buttons) ? Thanks in advance.
ReplyDeleteHey Nickforya did you solve your problem? I have the same problem with you. I'm a total newbie in Android.
DeleteHi. It's not navigating to any other activities. (from item 1 to item 2 or 3 or 4 or 5).any help would be appreciated.
ReplyDeletethanks.
Thanks you for that!
ReplyDeleteHere, the drawer is recreated and reconfigured in each activities.
Is there a way to have a clean implementation, only 1 instance of the drawer shared between all activities ?
Thank you for very nice tutuorial.
ReplyDeleteBut how to use different layouts for different activities, not just setBackgroundResource() ?
I need different layouts with different buttons etc. on different activities
You can create your own layout and add it on parent class frame layout like this.
DeletegetLayoutInflater().inflate(R.layout.activity_main, frameLayout);
You can find this line on every activity of our demo.
could you please elaborate a bit? I mean how do i add a separate layout for each of the other activities???
DeleteOn every activity you have this line :
DeletegetLayoutInflater().inflate(R.layout.activity_main, frameLayout);
Add your own layout on first parameter... that is "R.layout.activity_main"....add your own layout id in this place.
This comment has been removed by the author.
ReplyDeleteThanks mate.. All other tutorials show nav drawer with fragments but I was looking for this use case :)
ReplyDeleteOne question, Instead of listview if I use navigationView provided in design support library for nav drawer menu, would your solution still work or do you see any problem?
hey.. i wanted to know if i could have separate view for each of the 'item3activity' besides its main layout ...
ReplyDeleteOn every activity you have this line :
DeletegetLayoutInflater().inflate(R.layout.activity_main, frameLayout);
Add your own layout on first parameter... that is "R.layout.activity_main"....add your own layout id in this place.
Thanks Dipen.. useful tutorial. but i want to drawer should cover status bar too. is it possile in thhis with fragment
ReplyDeletehi i tried ur code but wen i run the app and select 2 or 3 option in the menu the aplication crash
ReplyDeleteFATAL EXCEPTION: main
Process: com.navigation.drawer.activity, PID: 11914
java.lang.OutOfMemoryError
the app spend alot of memory i tink
Hi, I have used some high resolution images to render on activity layout.....replace those images with low resolution (less size image) and it will work fine.
DeleteHii thanks for this tutorial,
ReplyDeleteI am trying to use image icons along with the text in the navigation drawer listview, but then the application shows errors at runtime, could you help me with that.
Thank You
You can use "custom list view" to render on navigation drawer list view.
DeleteWhere you can render any kind of layout you want.
Excelente, el codigo funciona de 10... me sirve mucho para una aplicación que estoy desarrollando... excelente aporte
ReplyDeletenice thanku
ReplyDeleteThis comment has been removed by the author.
ReplyDeleteHi this a good one. Im still learning about android programming, how do i have separate an activity, for example, a register activity before the whole thinng?
ReplyDeleteHello..I'm newbie in Android and I've find this tutorial really easy and I've learn quickly about the navDrawer. But I'm facing some issue regarding the NULLPOINTEREXCEPTION at getActionBar.setDisplayShowHomeEnabled(true).. please help I'm trying to sor this issue myself but no progress..
ReplyDeleteTry to increase the Android api version of your project...check if it works
ReplyDeleteit worked thanks.. :)
DeleteI have the same issue but increase the android api version of my project don't work. i have change the theme so it's work but it's not very beautifull
Deletehey,i too got the same problem wat should i do??i tried increaseing the api version bt it did nt work
Deletethis error shows on kitkat
ReplyDeleteCaused by: java.lang.reflect.InvocationTargetException
Caused by: android.view.InflateException: Binary XML file line #2: Error inflating class android.support.design.widget.NavigationView
Thank you, it work well!
ReplyDeleteBut about BackPress, if I remove onBackPressed() of BaseActivity , it seem more logical ? Because in an actvity, when Hard-Back-Press, it should be back to previous activity rather than show NavigationBar ?
Thank you, it work well!
ReplyDeleteBut about BackPress, if I remove onBackPressed() of BaseActivity , it seem more logical ? Because in an actvity, when Hard-Back-Press, it should be back to previous activity rather than show NavigationBar ?
Patel mara project ma 1 locho thayo che, mare navigation drawer toolbar na niche joiche pan ae thatu nathi. toolbar ouverlap thai che maro. if possible help me if you want i can share my code and my files
ReplyDeleteHi I am a student and new to Android developing.Y our tutorial is exactly what I've been looking for, but I am facing one serious problem.
ReplyDeleteWhen I extend one of my activities with BaseActivity, it also replaces the layout of the activity instead of just adding the navigation drawer. How do i fix that?
Thank you very much in advance
best wishes
This comment has been removed by the author.
DeleteIt shows the image1.jpg instead of the layout of my child activity
DeleteNvm, I think i fixed it by changing the layout in the itemActitivites getLayoutInflater().inflate(R.layout.yourlayouhere, frameLayout);
DeleteThis comment has been removed by the author.
ReplyDeletegetActionBar().setDisplayHomeAsUpEnabled(true);
ReplyDeletegetActionBar().setHomeButtonEnabled(true);
nullpointerexception
Increase your App API version or try to add support library in your project.
Deleteyour tutorial is amazing....sir.....
ReplyDeleteThis comment has been removed by the author.
ReplyDeleteThank you for your tutorial. I'm making an app that uses Activities with a DrawerLayout. When you click an item on the drawer menu, it's supposed to show the next screen while closing the drawer. However, when you click on an item, the Activity launches immediately and it cuts off the closing of the drawer. Is there any way to remedy this?
ReplyDeleteThanks for the tutorial, it was a good starting point, but do you know of any RECENT examples with current Android SDK codebases ? A lot of things in this code are deprecated. If you set up a new DrawerLayout project in Android Studio 2.2, the sample app has a lot less code, and I've got it working with multiple activities, the only problem is that once you go past the first activity, the navigationview is put onto a second line (like a second actionbar)
ReplyDeleteThanks alot.Worked Perfectly for me.
ReplyDeleteCan you send me the complete code in android studio I am not able to use the following github code
ReplyDeleteCan you send me the complete code in android studio I am not able to use the following github code to this email id tarigonda9sekhar123@gmail.com
ReplyDeleteHere is a complete working example that SO did not want:
ReplyDeletehttps://github.com/jj30/MyApp
ENJOY
Hi Dipen , I have a query that when i write the line in the my item_activity1 class that is
ReplyDeletegetLayoutInflater().inflate(R.layout.tabs, frameLayout);
mDrawerList.setItemChecked(position, true);
setTitle(listArray[position]);
it shows error bcoz it that class in my project aleready extended from another class
that is Tabactivity like as follows .
public class ItemActivity1 extends Tabactivity{
then what should i have to do...?
I can nor understand this.please, change navigation icon....and this apps can not exit
ReplyDeleteI was looking for Quality Personal Statement Writing Help before I landed on this page. Although I did not find the exact services that I was looking for, I have found important information that has enlighten me. Thanks for sharing this information with us, we are looking forward to reading more new posts.
ReplyDeleteI have been developing a lot of interest in android development and thus I find this blog to be very useful to me. Navigations are found in all the user interfaces and thus learning about them is very crucial. Android navigation should be set into an extent that the user elements will be visible. Where to get Essay Topic Ideas
ReplyDeletehow i tried your project but i get error on during runtime. it just crashes the moment i run it. can you help me? i simply copied everything so there is no way there is an error in the codes.
ReplyDeleteStop putting message that is irrelevant to my blog...I or my viewer dont want your quickbook or slowbook.
ReplyDeleteSTOP SPAMMING
QuickBooks Payroll has emerged among the best accounting software which has had changed the meaning of payroll. Quickbooks Payroll Support contact number will be the team that provide you QuickBooks Payroll Support Number
ReplyDeleteAgain your message on my blog.
DeleteYou are shameless