I'd like to create a navigation drawer effect, but rather than the drawer sliding out from the right.I Created code and my code working perfect when my slide menu is left side.this is a my java code.
DrawerLayout drawerLayout;
View drawerView;
View drawerContent;
View mainContent;
ActionBarDrawerToggle toggle;
#Override
protected void onCreate(Bundle savedInstanceState)
{
super.onCreate(savedInstanceState);
setContentView(R.layout.main_activity);
drawerLayout = (DrawerLayout) findViewById(R.id.drawer_layout);
drawerView = findViewById(R.id.drawer_view);
drawerContent = findViewById(R.id.drawer_content);
mainContent = findViewById(R.id.main_content);
toggle = new ActionBarDrawerToggle(
TestLayout.this,
drawerLayout,
R.drawable.ic_drawer,
R.string.u_drawer_call_center,
R.string.u_drawer_call_center
) {
#Override
public void onDrawerSlide(View drawer, float slideOffset)
{
super.onDrawerSlide(drawer, slideOffset);
drawerContent.setX(drawerView.getWidth() * (1 - slideOffset));
mainContent.setX(drawerView.getWidth() * slideOffset);
}
public void onDrawerClosed(View view) {
}
public void onDrawerOpened(View drawerView) {
}
};
drawerLayout.setDrawerListener(toggle);
drawerLayout.closeDrawer(drawerView);
drawerContent.setX(drawerView.getWidth());
}
}
as i said i can move main content when my slide menu is left side.but now i want slide menu right side.i rewrited my xml code but i can't move main content
this is a my xml code
<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"
android:background="#000000">
<FrameLayout android:id="#+id/main_content"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:background="#cccccc" />
<LinearLayout android:id="#+id/drawer_view"
android:layout_width="240dp"
android:layout_height="match_parent"
android:layout_gravity="right">
<LinearLayout android:id="#+id/drawer_content"
android:layout_width="match_parent"
android:layout_height="match_parent">
<ImageView android:id="#+id/image"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:src="#drawable/ic_launcher" />
</LinearLayout>
</LinearLayout>
i also changed source code
drawerContent.setX(drawerLayout.getWidth() - (drawerView.getWidth() * (1 - slideOffset)));
mainContent.setX(drawerLayout.getWidth() - (drawerView.getWidth() * slideOffset));
but this code not working.I don't know how to use my code when i have slide menu right side.
if anyone knows solution please help me
thanks everyone
Other than changing the layout_gravity on the drawer_view as you've already done, the necessary changes are minor. In my original code, negate every occurrence of drawerView.getWidth(). That is:
toggle = new ActionBarDrawerToggle(...) {
...
#Override
public void onDrawerSlide(View drawer, float slideOffset) {
super.onDrawerSlide(drawer, slideOffset);
drawerContent.setX(-drawerView.getWidth() * (1 - slideOffset));
mainContent.setX(-drawerView.getWidth() * slideOffset);
...
}
};
...
drawerContent.setX(-drawerView.getWidth());
You will then need to override MainActivity's onOptionsItemSelected() method as follows:
#Override
public boolean onOptionsItemSelected(MenuItem item) {
if (item.getItemId() == android.R.id.home) {
if(drawerLayout.isDrawerOpen(Gravity.END)) {
drawerLayout.closeDrawer(Gravity.END);
}
else {
drawerLayout.openDrawer(Gravity.END);
}
return true;
}
...
return super.onOptionsItemSelected(item);
}
Related
I want my floating action button to appear when navigation drawer is open and will disappear when navigation drawer is closed, how do I do this? Here is a image for you to see what I am talking about. Here is the image.
Here is my code for the activity.xml
<?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:layout_width="match_parent"
android:layout_height="match_parent"
android:id="#+id/drawer_layout"
>
<com.google.android.material.navigation.NavigationView
android:id="#+id/drawerNavigationView"
android:layout_width="wrap_content"
android:layout_height="match_parent"
android:layout_gravity="start"
app:headerLayout="#layout/navigation_drawer_header"
app:menu="#menu/navigation_drawer_menu"
android:fitsSystemWindows="true"
app:insetForeground="#android:color/transparent">
<RelativeLayout
android:layout_width="match_parent"
android:layout_height="match_parent"
android:gravity="bottom"
android:paddingLeft="20dp"
android:paddingBottom="20dp"
android:paddingTop="40dp">
<ImageView
android:id="#+id/logoutNavigationDrawer"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:src ="#drawable/icon_logout"
android:layout_centerVertical="true"
/>
<TextView
android:id="#+id/logoutTxt"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:textColor="#color/orangeText"
android:paddingLeft="14dp"
android:textSize="16sp"
android:fontFamily="#font/century_gothic_bold"
android:text="Log out"
android:layout_toEndOf="#+id/logoutNavigationDrawer"
android:layout_toRightOf="#+id/logoutNavigationDrawer"
android:layout_centerVertical="true"/>
</RelativeLayout>
</com.google.android.material.navigation.NavigationView>
<androidx.constraintlayout.widget.ConstraintLayout
android:layout_width="match_parent"
android:layout_height="match_parent">
<com.google.android.material.floatingactionbutton.FloatingActionButton
android:id="#+id/emergencyCallFAB"
android:layout_width="wrap_content"
app:tint="#color/white"
android:layout_height="wrap_content"
android:layout_centerVertical="true"
android:src="#drawable/emergency_call_button_round"
app:backgroundTint="#color/red"
android:layout_marginStart="370dp"
android:layout_marginEnd="50dp"
android:layout_marginTop="800dp"
android:layout_marginBottom="50dp"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent" />
</androidx.constraintlayout.widget.ConstraintLayout>
</androidx.drawerlayout.widget.DrawerLayout>
Here is my java code in where I implemented the NavigationDrawer
//Setting Emergency Floating Action Button
emergenyCallFABBtn = findViewById(R.id.emergencyCallFAB);
//Will open the menu, once hamburger button has been clicked
hamburgerMenuButton = findViewById(R.id.hamburgerMenuIcon);
hamburgerMenuButton.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
drawerLayout.openDrawer(GravityCompat.START);
}
});
drawerLayout.setScrimColor(Color.parseColor("#00000000")); // set screen color behind navigation , this is what makes screen behind navigation looks as same color
//NavigationDrawer Function
navigationView.bringToFront();
ActionBarDrawerToggle actionBarDrawerToggle = new ActionBarDrawerToggle(Location.this, drawerLayout,
R.string.navigation_drawer_open, R.string.navigation_drawer_close){
public void onDrawerOpened(View drawerView){
super.onDrawerClosed(drawerView);
emergenyCallFABBtn.setVisibility(View.VISIBLE); // make it visible and bring to front
emergenyCallFABBtn.bringToFront();
}
#Override
public void onDrawerSlide(View drawerView, float slideOffset) {
super.onDrawerSlide(drawerView, slideOffset);
emergenyCallFABBtn.setVisibility(View.VISIBLE);
emergenyCallFABBtn.setAlpha(slideOffset); // makes it visible it animation , as drawer opens button becomes less faded and vice versa in case of close
}
public void onDrawerClosed(View view){
super.onDrawerClosed(view);
emergenyCallFABBtn.setVisibility(View.GONE); // hide button on drawer close
}
};
actionBarDrawerToggle.setDrawerIndicatorEnabled(false);
drawerLayout.addDrawerListener(actionBarDrawerToggle);
actionBarDrawerToggle.syncState();
navigationView.setItemIconTintList(null);
navigationView.setNavigationItemSelectedListener(Location.this);
emergenyCallFABBtn.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
Intent intent = new Intent(Location.this, EmergencyCall.class);
startActivity(intent);
Toast.makeText(Location.this, "Clicked on Emergency Call", Toast.LENGTH_SHORT).show();
}
});
Here is my onNavigationItemSelected and my onBackPressed function
//Case switch function for the hamburger menu.
#Override
public boolean onNavigationItemSelected(#NonNull MenuItem menuItem) {
switch (menuItem.getItemId()) {
case R.id.homeNavigationDrawer:
Intent homeNavDrawer = new Intent(Location.this, TrackActivity.class);
startActivity(homeNavDrawer);
break;
case R.id.profileNavigationDrawer:
Intent profileNavDrawer = new Intent(Location.this, Profile.class);
startActivity(profileNavDrawer);
break;
case R.id.changeCityNavigationDrawer:
Intent changeCityNavDrawer = new Intent(Location.this, NCR.class);
startActivity(changeCityNavDrawer);
break;
// case R.id.nav_logout:
// try {
// auth.signOut();
// Intent i = new Intent(getApplicationContext(), Location.class);
// startActivity(i);
// // signed out
// } catch (Exception e) {
// // Error handling!
// }
// break;
}
return true;
}
#Override
public void onBackPressed() {
if (drawerLayout.isDrawerOpen(GravityCompat.START)) {
drawerLayout.closeDrawer(GravityCompat.START);
} else {
super.onBackPressed();
}
}
#Override
public boolean dispatchTouchEvent(MotionEvent event) {
if (event.getAction() == MotionEvent.ACTION_UP) {
if (drawerLayout.isDrawerOpen(navigationView)) {
View content = findViewById(R.id.emergencyCallFAB); // find the id of the view you want to check for clicable
int[] contentLocation = new int[2];
content.getLocationOnScreen(contentLocation);
Rect rect = new Rect(contentLocation[0],
contentLocation[1],
contentLocation[0] + content.getWidth(),
contentLocation[1] + content.getHeight());
if ((rect.contains((int) event.getX(), (int) event.getY()))) { // your view is clicked , perform you action
emergenyCallFAB.performClick();
isOutSideClicked = false;
} else { // clicked outside the button
isOutSideClicked = true;
}
}
}
return super.dispatchTouchEvent(event);
}
Update: There is Error now.
I have made changes to your code to make fab focus, and added comments where I made a change , let me know if anything still unclear.
activity_main.xml
<?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"
android:id="#+id/drawer_layout"
android:layout_width="match_parent"
android:layout_height="match_parent">
<com.google.android.material.navigation.NavigationView
android:id="#+id/drawerNavigationView"
android:layout_width="wrap_content"
android:layout_height="match_parent"
android:layout_gravity="start"
android:fitsSystemWindows="true"
app:headerLayout="#layout/navigation_drawer_header"
app:insetForeground="#android:color/transparent"
app:menu="#menu/navigation_drawer_menu">
<RelativeLayout
android:layout_width="match_parent"
android:layout_height="match_parent"
android:gravity="bottom"
android:paddingLeft="20dp"
android:paddingTop="40dp"
android:paddingBottom="20dp">
<ImageView
android:id="#+id/logoutNavigationDrawer"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_centerVertical="true"
android:src="#drawable/ic_launcher_background" />
<TextView
android:id="#+id/logoutTxt"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_centerVertical="true"
android:layout_toEndOf="#+id/logoutNavigationDrawer"
android:layout_toRightOf="#+id/logoutNavigationDrawer"
android:paddingLeft="14dp"
android:text="Log out"
android:textColor="#color/colorPrimaryDark"
android:textSize="16sp" />
</RelativeLayout>
</com.google.android.material.navigation.NavigationView>
<!-- added relative layout as you didn't have any view group using UI to distort in different devices-->
<RelativeLayout
android:layout_width="match_parent"
android:layout_height="match_parent">
<!-- removed extra params , set visiblity gone to hide first time -->
<com.google.android.material.floatingactionbutton.FloatingActionButton
android:id="#+id/emergencyCallFAB"
android:layout_width="100dp"
android:layout_height="100dp"
android:layout_alignParentEnd="true"
android:layout_alignParentBottom="true"
android:layout_centerVertical="true"
android:layout_marginEnd="20dp"
android:visibility="gone"
android:layout_marginBottom="20dp"
android:src="#android:drawable/sym_call_incoming"/>
</RelativeLayout>
</androidx.drawerlayout.widget.DrawerLayout>
MainActivity
drawerLayout = findViewById(R.id.drawer_layout);
drawerLayout.setScrimColor(Color.parseColor("#00000000")); // set screen color behind navigation , this is what makes screen behind navigation looks as same color
navigationView = findViewById(R.id.drawerNavigationView);
emergenyCall = findViewById(R.id.emergencyCallFAB);
//NavigationDrawer Function
navigationView.bringToFront();
ActionBarDrawerToggle actionBarDrawerToggle = new ActionBarDrawerToggle(this, drawerLayout,
R.string.navigation_drawer_open, R.string.navigation_drawer_close){
public void onDrawerOpened(View drawerView){
super.onDrawerClosed(drawerView);
emergenyCall.setVisibility(View.VISIBLE); // make it visible and bring to front
emergenyCall.bringToFront();
}
#Override
public void onDrawerSlide(View drawerView, float slideOffset) {
super.onDrawerSlide(drawerView, slideOffset);
emergenyCall.setVisibility(View.VISIBLE);
emergenyCall.setAlpha(slideOffset); // makes it visible in animation , as drawer opens button becomes less faded and vice versa in case of close.
}
public void onDrawerClosed(View view){
super.onDrawerClosed(view);
emergenyCall.setVisibility(View.GONE); // hide button on drawer close
}
};
actionBarDrawerToggle.setDrawerIndicatorEnabled(false);
drawerLayout.addDrawerListener(actionBarDrawerToggle);
actionBarDrawerToggle.syncState();
navigationView.setItemIconTintList(null);
Update : To make FAB clickable to need to override dispatchTouchEvent and detect the touch on your button
#Override
public boolean dispatchTouchEvent(MotionEvent event) {
if (event.getAction() == MotionEvent.ACTION_UP) {
if (drawerLayout.isDrawerOpen(navigationView)) {
View content = findViewById(R.id.emergencyCallFAB); // find the id of the view you want to check for clicable
int[] contentLocation = new int[2];
content.getLocationOnScreen(contentLocation);
Rect rect = new Rect(contentLocation[0],
contentLocation[1],
contentLocation[0] + content.getWidth(),
contentLocation[1] + content.getHeight());
if ((rect.contains((int) event.getX(), (int) event.getY()))) { // your view is clicked , perform you action
emergenyCall.performClick();
isOutSideClicked = false;
} else { // clicked outside the button
isOutSideClicked = true;
}
}
}
return super.dispatchTouchEvent(event);
}
Final Result
I have two drawers on left and on right. Now right drawer is in the lock-closed state, but left drawer can be open and close. On opening drawer, I am pushing the middle content using drawer offset. Now I also want right drawer (which is opened by default) should move/adjust the content also but I am unable to do it. Because when the left drawer is opened it pushes the content under the right drawer. So what I want the right drawer on default opening should adjust the content and when I open left drawer content should adjust and should not move under the right drawer.
Here is my code:
<DrawerLayout
android:id="#+id/drawer_layout"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_alignParentLeft="true"
android:layout_alignParentStart="true"
android:layout_alignParentTop="true">
<RelativeLayout
android:id="#+id/main_screen"
android:layout_width="wrap_content"
android:layout_height="match_parent"
android:background="#drawable/bg">
<include
android:id="#+id/includedView"
layout="#layout/view" />
</RelativeLayout>
<!-- ======= side menu ====== -->
<RelativeLayout
android:id="#+id/leftMenu"
android:layout_width="wrap_content"
android:layout_height="match_parent"
android:layout_gravity="left">
<include
layout="#layout/leftmenuLayout"
android:layout_width="wrap_content"
android:layout_height="match_parent" />
</RelativeLayout>
<RelativeLayout
android:id="#+id/rightMenu"
android:layout_width="wrap_content"
android:layout_height="match_parent"
android:layout_gravity="right">
<include
layout="#layout/rightmenuLayout"
android:layout_width="wrap_content"
android:layout_height="match_parent" />
</RelativeLayout>
<!-- ======================= -->
</DrawerLayout>
DrawerAcivity:
mDrawerLayout = (DrawerLayout) findViewById(R.id.drawer_layout);
mDrawerLayout.setScrimColor(Color.parseColor("#00000000"));
main_screen = (RelativeLayout) findViewById(R.id.main_screen);
leftMenu= (RelativeLayout) findViewById(R.id.leftMenu);
rightMenu= (RelativeLayout)
findViewById(R.id.rightMenu);
Display display = getWindowManager().getDefaultDisplay();
size = new Point();
display.getSize(size);
mDrawerLayout.addDrawerListener(new CustomDrawerLayout.DrawerListener() {
#Override
public void onDrawerSlide(View drawerView, float slideOffset) {
float moveFactor = 0;
moveFactor = (drawerView.getWidth() * slideOffset);
main_screen.setTranslationX(moveFactor);
}
#Override
public void onDrawerOpened(View drawerView) {
invalidateOptionsMenu();
}
#Override
public void onDrawerClosed(View drawerView) {
invalidateOptionsMenu();
}
#Override
public void onDrawerStateChanged(int newState) {
}
});
mDrawerLayout.setDrawerLockMode(DrawerLayout.LOCK_MODE_LOCKED_CLOSED, rightMenu);
mDrawerLayout.openDrawer(GravityCompat.END);
mDrawerLayout.setDrawerLockMode(DrawerLayout.LOCK_MODE_LOCKED_CLOSED, leftMenu);
ViewGroup.LayoutParams params = leftMenu.getLayoutParams();
params.width = (((size.x / 2) / 4));
rl_slider_menu.setLayoutParams(params);
ViewGroup.LayoutParams paramsRight =
rightMenu.getLayoutParams();
paramsRight.width = ((size.x / 3));
rightMenu.setLayoutParams(paramsRight);
DrawerLayout.LayoutParams paramsContent = (DrawerLayout.LayoutParams) main_screen.getLayoutParams();
paramsContent.setMargins(0, 0, (((size.x / 2) / 4)), 0); //substitute parameters for left, top, right, bottom
main_screen.setLayoutParams(paramsContent);
main_screen.invalidate();
This actually turns out to be a pretty simple implementation, once you get your head wrapped around it.
We simply need to keep track of both drawers' inset measures, scale the content View to the remaining space, and then translate it by the difference of half of each inset. For example. building on the code in the question:
mDrawerLayout.addDrawerListener(new DrawerLayout.DrawerListener() {
private float leftInset, rightInset;
#Override
public void onDrawerSlide(View drawerView, float slideOffset) {
if (drawerView == leftMenu) {
leftInset = slideOffset * leftMenu.getWidth();
}
else {
rightInset = slideOffset * rightMenu.getWidth();
}
final float scale = 1 - (leftInset + rightInset) / main_screen.getWidth();
main_screen.setScaleX(scale);
final float translation = leftInset / 2 - rightInset / 2;
main_screen.setTranslationX(translation);
}
...
}
I just came across this app and saw this custom animation for a DrawerLayout.
I'm guessing it has to take a screenshot first, then draw a custom View in the Activity, but I'm not sure about that, nor the details.
Does anyone know how to do this?
You can do this by translating and scaling the content View in the onDrawerSlide() method of a DrawerListener on your DrawerLayout. Since the content View itself is resizing, and there's a separate TextView that appears in the bottom right corner, we'll stick both of these in another holder ViewGroup. If that label TextView isn't needed, the holder ViewGroup can be omitted, as well.
A basic DrawerLayout setup for the example:
<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"
android:background="#222222">
<RelativeLayout android:id="#+id/holder"
android:layout_width="match_parent"
android:layout_height="match_parent">
<LinearLayout android:id="#+id/content"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical">
<android.support.v7.widget.Toolbar
android:id="#+id/toolbar"
android:layout_width="match_parent"
android:layout_height="?attr/actionBarSize"
android:background="#E97411" />
<ImageView android:id="#+id/main_content"
android:layout_width="match_parent"
android:layout_height="0dp"
android:layout_weight="1"
android:background="#EEEEEE"
android:src="#drawable/ic_launcher" />
</LinearLayout>
<TextView android:id="#+id/label"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignParentBottom="true"
android:layout_alignParentRight="true"
android:visibility="gone"
android:textSize="26dp"
android:text="My App" />
</RelativeLayout>
<android.support.design.widget.NavigationView
android:id="#+id/navigation_view"
android:layout_width="240dp"
android:layout_height="match_parent"
android:layout_gravity="left"
android:background="#555555" />
</android.support.v4.widget.DrawerLayout>
The example Activity shows the standard View initializations, and the DrawerListener that is actually doing the work.
public class MainActivity extends AppCompatActivity {
private static final float END_SCALE = 0.7f;
private DrawerLayout drawerLayout;
private NavigationView navigationView;
private Toolbar toolbar;
private TextView labelView;
private View contentView;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
drawerLayout = (DrawerLayout) findViewById(R.id.drawer_layout);
navigationView = (NavigationView) findViewById(R.id.navigation_view);
toolbar = (Toolbar) findViewById(R.id.toolbar);
labelView = (TextView) findViewById(R.id.label);
contentView = findViewById(R.id.content);
toolbar.setNavigationIcon(new DrawerArrowDrawable(this));
toolbar.setNavigationOnClickListener(new OnClickListener() {
#Override
public void onClick(View v) {
if (drawerLayout.isDrawerOpen(navigationView)) {
drawerLayout.closeDrawer(navigationView);
}
else {
drawerLayout.openDrawer(navigationView);
}
}
}
);
drawerLayout.setScrimColor(Color.TRANSPARENT);
drawerLayout.addDrawerListener(new DrawerLayout.SimpleDrawerListener() {
#Override
public void onDrawerSlide(View drawerView, float slideOffset) {
labelView.setVisibility(slideOffset > 0 ? View.VISIBLE : View.GONE);
// Scale the View based on current slide offset
final float diffScaledOffset = slideOffset * (1 - END_SCALE);
final float offsetScale = 1 - diffScaledOffset;
contentView.setScaleX(offsetScale);
contentView.setScaleY(offsetScale);
// Translate the View, accounting for the scaled width
final float xOffset = drawerView.getWidth() * slideOffset;
final float xOffsetDiff = contentView.getWidth() * diffScaledOffset / 2;
final float xTranslation = xOffset - xOffsetDiff;
contentView.setTranslationX(xTranslation);
}
#Override
public void onDrawerClosed(View drawerView) {
labelView.setVisibility(View.GONE);
}
}
);
}
}
The example uses a SimpleDrawerListener, but the onDrawerSlide() method can be overridden similarly in an ActionBarDrawerToggle, if using that. The super method would need to be called, in that case, to preserve the hamburger-arrow animation.
Do note that DrawerLayout retains the drawer state during Activity recreation, so you might need to account for this when handing orientation changes, etc.
Drawer behavior is a library use Android DrawerLayout Support library as Parent Class [Easy to migrate], that provide an extra behavior on drawer, such as, move view or scaling view's height while drawer on slide.
If current project use Android DrawerLayout Support library and kinda boring with the effect. Then, just change the layout code and calling necessary method for animation/effect.
Check out github code
Gradle
dependencies {
implementation 'com.infideap.drawerbehavior:drawer-behavior:0.1.5'
}
if the gradle unable to sync, you may include this line in project level gradle,
repositories {
maven{
url "https://dl.bintray.com/infideap2/Drawer-Behavior"
}
}
I am implementing a Navigation Drawer for my android application. I got the drawer to work by dragging from the side, but the home/toggle button on the action bar doesn't change to the icon I want and doesn't respond to clicks, thou the onDrawerClosed and onDrawerOpened methods defined in it are called.
My code is as follows:
<?xml version="1.0" encoding="utf-8"?>
<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">
<fragment
android:layout_width="match_parent"
android:layout_height="match_parent"
android:id="#+id/loadingFragment"
android:name="com.whostr.clients.android.LoadingFragment" />
<fragment
android:layout_width="match_parent"
android:layout_height="match_parent"
android:id="#+id/eventFragment"
android:name="com.whostr.clients.android.EventDisplayFragment"/>
<fragment
android:layout_width="match_parent"
android:layout_height="match_parent"
android:id="#+id/emptyFragment"
android:name="com.whostr.clients.android.EmptyView"/>
<!-- Listview to display slider menu -->
<ListView android:id="#+id/left_drawer"
android:layout_width = "240dp"
android:layout_height = "match_parent"
android:layout_gravity = "start"
android:choiceMode = "singleChoice"
android:dividerHeight = "1dp"
android:divider = "#android:color/transparent"
android:background="#111"
/>
And in the activity I have the following code:
#Override
public void onCreate(Bundle savedDataInstace)
{
super.onCreate(savedDataInstace);
setContentView(R.layout.eventdisplay);
fm = getSupportFragmentManager();
//get fragments by id
fragments[EVENT_VIEW]= fm.findFragmentById(R.id.eventFragment);
fragments[LOADING] = fm.findFragmentById(R.id.loadingFragment);
fragments[EMPTY_VIEW] = fm.findFragmentById(R.id.emptyFragment);
menuList = getResources().getStringArray(R.array.menuArray);
mDrawerLayout = (DrawerLayout) findViewById(R.id.drawer_layout);
mDrawerList = (ListView) findViewById(R.id.left_drawer);
mDrawerToggle = new ActionBarDrawerToggle(this, mDrawerLayout, R.drawable.ic_drawer, R.string.drawwer_open, R.string.drawer_closed)
{
/*
* Called when a drawer has settled in a completely closed state
*/
public void onDrawerClosed(View view)
{
Log.d("drawerToggle", "Drawer closed");
super.onDrawerClosed(view);
getActionBar().setTitle(R.string.app_name);
invalidateOptionsMenu(); //Creates call to onPrepareOptionsMenu()
}
/*
* Called when a drawer has settled in a completely open state
*/
public void onDrawerOpened(View drawerView)
{
Log.d("drawerToggle", "Drawer opened");
super.onDrawerOpened(drawerView);
getActionBar().setTitle("NavigationDrawer");
invalidateOptionsMenu();
}
};
mDrawerLayout.setDrawerListener(mDrawerToggle);
//Set the adapter for the list view
mDrawerList.setAdapter(new ArrayAdapter<String>(this, R.layout.drawer_list_item, menuList));
mDrawerList.setOnItemClickListener(new OnItemClickListener() {
#Override
public void onItemClick(AdapterView<?> arg0, View view, int position,
long id) {
Log.d("navigationDrawer", "Clicked on an item");
}
});
FragmentTransaction transaction = fm.beginTransaction();
//Hide the event view
transaction.hide(fragments[EVENT_VIEW]);
transaction.hide(fragments[EMPTY_VIEW]);
transaction.commit();
AsyncTask<String, Void, EventResponseCollection> task = new GetEventsNearByAsyncTask().execute();
try {
if(task != null)
events = task.get().getItems();
} catch (InterruptedException | ExecutionException e) {
Log.d("viewEvent", "Error when retrieving task details " + e.getMessage());
}
if(events == null)
{
//show create your own event fragment
changeFragment(EMPTY_VIEW);
}
else
{
Log.d("viewEvent", "I have " + events.size());
//show proper fragment with the first event displayed
currentEvent = events.get(eventIndex);
((EventDisplayFragment) fragments[EVENT_VIEW]).updateFragment(currentEvent);
changeFragment(EVENT_VIEW);
}
}
#Override
public boolean onOptionsItemSelected(MenuItem item)
{
Log.d("onOptionsItemSelected", "In the on item select");
//Pass the event to ActionBarDrawerToggle, if it returns
//true, then it has handled the app icon touch event
if(mDrawerToggle.onOptionsItemSelected(item))
{
Log.d("onOptionsItemSelected", "Clicked on action bar item");
return true;
}
//Handle your other action bar items...
return super.onOptionsItemSelected(item);
}
Does anyone have any suggestion on what I can do? I've tried all solutions I found online to make this work, but apparently I'm out of luck and nothing seems to be working :(
You have to add something like this in your Activity
#Override
public boolean onOptionsItemSelected(android.view.MenuItem item) {
return drawerToggle.onOptionsItemSelected(item);
}
This worked for me, its almost like the previous post
public boolean onOptionsItemSelected(MenuItem item) {
// Handle presses on the action bar items
if (mDrawerToggle.onOptionsItemSelected(item)) {
return true;
} }
Ok, it was a small omission from my side, I forgot to include the following 2 lines of code:
getActionBar().setDisplayHomeAsUpEnabled(true);
getActionBar().setHomeButtonEnabled(true);
in the onCreate method.
I've faced the similar issue.
I hope this answer can help somebody facing similar problem.
Check for openDrawer attribute in your drawer layout
tools:openDrawer="start"
Also, check for drawer lock mode in your Activity and remove it, if you have accidentally locked drawer.
//drawerLayout.setDrawerLockMode(DrawerLayout.LOCK_MODE_LOCKED_CLOSED);
Years later but anyway..... it could help anyone, when you have a layout with a Drawerlayout, the Drawer assumes that the First child is the view to overlap when shown and the Second child is the navigation panel. So in your case you could do something like...
enter code here
<?xml version="1.0" encoding="utf-8"?>
<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">
<RelativeLayout
android:layout_width="match_parent"
android:layout_height="match_parent">
<fragment
android:layout_width="match_parent"
android:layout_height="match_parent"
android:id="#+id/loadingFragment"
android:name="com.whostr.clients.android.LoadingFragment" />
<fragment
android:layout_width="match_parent"
android:layout_height="match_parent"
android:id="#+id/eventFragment"
android:name="com.whostr.clients.android.EventDisplayFragment"/>
<fragment
android:layout_width="match_parent"
android:layout_height="match_parent"
android:id="#+id/emptyFragment"
android:name="com.whostr.clients.android.EmptyView"/>
</RelativeLayout>
<!-- Listview to display slider menu -->
<ListView android:id="#+id/left_drawer"
android:layout_width = "240dp"
android:layout_height = "match_parent"
android:layout_gravity = "start"
android:choiceMode = "singleChoice"
android:dividerHeight = "1dp"
android:divider = "#android:color/transparent"
android:background="#111"
/>
So in that way, the Drawer knows that the RelativeLayout is the view to overlap and the ListView is the left panel you want.
Also you have to do in the java code all the things you know.. setting up the toolbar, setting up the drawer indicating the toolbar, setting up the toogle etc... it's all in the comments.
How can I open Drawer Layout moving all the view and not just slide over?
The idea would be to make the menu like Facebook and not like GMail, for example. I've been looking for information and haven't found anything. It can be done? It's possible with Drawer Layout? How?
Thank you very much.
If you dont want to use third-party libraries, you can implement it yourself just overriding the onDrawerSlide from the ActionBarDrawerToggle. There you can translate your framelayout view based on the opening % of your drawer.
Example with code:
<?xml version="1.0" encoding="utf-8"?>
<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:choiceMode="singleChoice"
android:divider="#android:color/transparent"
android:dividerHeight="0dp"/>
</android.support.v4.widget.DrawerLayout>
And here, override onDrawerSlide:
public class ConfigurerActivity extends ActionBarActivity
{
private DrawerLayout mDrawerLayout;
private ListView mDrawerList;
private ActionBarDrawerToggle mDrawerToggle;
private FrameLayout frame;
private float lastTranslate = 0.0f;
public void onCreate(Bundle savedInstanceState)
{
super.onCreate(savedInstanceState);
setContentView(R.layout.main_layout);
mDrawerLayout = (DrawerLayout) findViewById(R.id.drawer_layout);
mDrawerList = (ListView) findViewById(R.id.left_drawer);
frame = (FrameLayout) findViewById(R.id.content_frame);
mDrawerToggle = new ActionBarDrawerToggle(this, mDrawerLayout, R.drawable.ic_drawer, R.string.acc_drawer_open, R.string.acc_drawer_close)
{
#SuppressLint("NewApi")
public void onDrawerSlide(View drawerView, float slideOffset)
{
float moveFactor = (mDrawerList.getWidth() * slideOffset);
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.HONEYCOMB)
{
frame.setTranslationX(moveFactor);
}
else
{
TranslateAnimation anim = new TranslateAnimation(lastTranslate, moveFactor, 0.0f, 0.0f);
anim.setDuration(0);
anim.setFillAfter(true);
frame.startAnimation(anim);
lastTranslate = moveFactor;
}
}
};
mDrawerLayout.setDrawerListener(mDrawerToggle);
// ... more of your code
}
}
Since setTranslationX is not available in pre-honeycomb android versions, i managed it using TranslateAnimation for lower version devices.
Hope it helps!
The thing you are using is navigation drawer but you have to use
menu drawer##
for the menu like facebook and gmail.
i have implemented it and this link will help you to do so.
Here's a link!
this will tell you all the steps for making menu drawer.
dont forget to Vote Up the answer if it is helfull.
thanks.