Simple Sliding Menu Example in Android

Simple Sliding Menu Example in Android
As of now we know that sliding menu is a simple dragging menu from any one side.

Complete code:

MainActivity.java
package com.android.slidingmenuexample;

import android.os.Bundle;
import android.support.v4.app.Fragment;
import android.support.v4.app.FragmentActivity;
import android.support.v4.app.FragmentManager;
import android.support.v4.app.FragmentTransaction;
import android.view.Menu;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.AdapterView;
import android.widget.ArrayAdapter;
import android.widget.Button;
import android.widget.ListView;
import android.widget.AdapterView.OnItemClickListener;
import android.widget.TextView;

public class MainActivity extends FragmentActivity {

MainLayout mLayout;
private ListView lvMenu;
private String[] lvMenuItems;
Button btMenu;
TextView tvTitle;

@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
mLayout = (MainLayout) this.getLayoutInflater().inflate(
R.layout.activity_main, null);
setContentView(mLayout);

lvMenuItems = getResources().getStringArray(R.array.menu_items);
lvMenu = (ListView) findViewById(R.id.menu_listview);
lvMenu.setAdapter(new ArrayAdapter<String>(this,
android.R.layout.simple_list_item_1, lvMenuItems));
lvMenu.setOnItemClickListener(new OnItemClickListener() {
@Override
public void onItemClick(AdapterView<?> parent, View view,
int position, long id) {
onMenuItemClick(parent, view, position, id);
}

});

btMenu = (Button) findViewById(R.id.button_menu);
btMenu.setOnClickListener(new OnClickListener() {
@Override
public void onClick(View v) {
// Show/hide the menu
toggleMenu(v);
}
});

tvTitle = (TextView) findViewById(R.id.activity_main_content_title);

FragmentManager fm = MainActivity.this.getSupportFragmentManager();
FragmentTransaction ft = fm.beginTransaction();
Layout1 fragment = new Layout1();
ft.add(R.id.activity_main_content_fragment, fragment);
ft.commit();

}

@Override
public boolean onCreateOptionsMenu(Menu menu) {
getMenuInflater().inflate(R.menu.main, menu);
return true;
}

public void toggleMenu(View v) {
mLayout.toggleMenu();
}

private void onMenuItemClick(AdapterView<?> parent, View view,
int position, long id) {
String selectedItem = lvMenuItems[position];
String currentItem = tvTitle.getText().toString();
if (selectedItem.compareTo(currentItem) == 0) {
mLayout.toggleMenu();
return;
}

FragmentManager fm = MainActivity.this.getSupportFragmentManager();
FragmentTransaction ft = fm.beginTransaction();
Fragment fragment = null;

if (selectedItem.compareTo(“Layout 1”) == 0) {
fragment = new Layout1();
} else if (selectedItem.compareTo(“Layout 2”) == 0) {
fragment = new Layout2();
}

if (fragment != null) {
ft.replace(R.id.activity_main_content_fragment, fragment);
ft.commit();
tvTitle.setText(selectedItem);
}
mLayout.toggleMenu();
}

@Override
public void onBackPressed() {
if (mLayout.isMenuShown()) {
mLayout.toggleMenu();
} else {
super.onBackPressed();
}
}
}
MainLayout.java
package com.android.slidingmenuexample;

import android.content.Context;
import android.os.Handler;
import android.util.AttributeSet;
import android.util.Log;
import android.view.MotionEvent;
import android.view.View;
import android.view.animation.Interpolator;
import android.widget.LinearLayout;
import android.widget.Scroller;

public class MainLayout extends LinearLayout {

private static final int SLIDING_DURATION = 500;
private static final int QUERY_INTERVAL = 16;
int mainLayoutWidth;
private View menu;
private View content;
private static int menuRightMargin = 15;

private enum MenuState {
HIDING, HIDDEN, SHOWING, SHOWN,
};

private int contentXOffset;
private MenuState currentMenuState = MenuState.HIDDEN;
private Scroller menuScroller = new Scroller(this.getContext(),
new EaseInInterpolator());
private Runnable menuRunnable = new MenuRunnable();
private Handler menuHandler = new Handler();
int prevX = 0;
boolean isDragging = false;
int lastDiffX = 0;

public MainLayout(Context context, AttributeSet attrs) {
super(context, attrs);
}

public MainLayout(Context context) {
super(context);
}

@Override
protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
super.onMeasure(widthMeasureSpec, heightMeasureSpec);

mainLayoutWidth = MeasureSpec.getSize(widthMeasureSpec);
menuRightMargin = mainLayoutWidth * 10 / 100;
}

@Override
protected void onAttachedToWindow() {
super.onAttachedToWindow();

menu = this.getChildAt(0);
content = this.getChildAt(1);
content.setOnTouchListener(new OnTouchListener() {
@Override
public boolean onTouch(View v, MotionEvent event) {
return MainLayout.this.onContentTouch(v, event);
}
});
menu.setVisibility(View.GONE);
}

@Override
protected void onLayout(boolean changed, int left, int top, int right,
int bottom) {
if (changed) {
LayoutParams contentLayoutParams = (LayoutParams) content
.getLayoutParams();
contentLayoutParams.height = this.getHeight();
contentLayoutParams.width = this.getWidth();
LayoutParams menuLayoutParams = (LayoutParams) menu
.getLayoutParams();
menuLayoutParams.height = this.getHeight();
menuLayoutParams.width = this.getWidth() – menuRightMargin;
}
menu.layout(left, top, right – menuRightMargin, bottom);
content.layout(left + contentXOffset, top, right + contentXOffset,
bottom);

}

public void toggleMenu() {

if (currentMenuState == MenuState.HIDING
|| currentMenuState == MenuState.SHOWING)
return;

switch (currentMenuState) {
case HIDDEN:
currentMenuState = MenuState.SHOWING;
menu.setVisibility(View.VISIBLE);
menuScroller.startScroll(0, 0, menu.getLayoutParams().width, 0,
SLIDING_DURATION);
break;
case SHOWN:
currentMenuState = MenuState.HIDING;
menuScroller.startScroll(contentXOffset, 0, -contentXOffset, 0,
SLIDING_DURATION);
break;
default:
break;
}
menuHandler.postDelayed(menuRunnable, QUERY_INTERVAL);
this.invalidate();
}

protected class MenuRunnable implements Runnable {
@Override
public void run() {
boolean isScrolling = menuScroller.computeScrollOffset();
adjustContentPosition(isScrolling);
}
}

private void adjustContentPosition(boolean isScrolling) {
int scrollerXOffset = menuScroller.getCurrX();

content.offsetLeftAndRight(scrollerXOffset – contentXOffset);

contentXOffset = scrollerXOffset;
this.invalidate();
if (isScrolling)
menuHandler.postDelayed(menuRunnable, QUERY_INTERVAL);
else
this.onMenuSlidingComplete();
}

private void onMenuSlidingComplete() {
switch (currentMenuState) {
case SHOWING:
currentMenuState = MenuState.SHOWN;
break;
case HIDING:
currentMenuState = MenuState.HIDDEN;
menu.setVisibility(View.GONE);
break;
default:
return;
}
}

protected class EaseInInterpolator implements Interpolator {
@Override
public float getInterpolation(float t) {
return (float) Math.pow(t – 1, 5) + 1;
}

}

public boolean isMenuShown() {
return currentMenuState == MenuState.SHOWN;
}

public boolean onContentTouch(View v, MotionEvent event) {
if (currentMenuState == MenuState.HIDING
|| currentMenuState == MenuState.SHOWING)
return false;
int curX = (int) event.getRawX();
int diffX = 0;

switch (event.getAction()) {
case MotionEvent.ACTION_DOWN:

prevX = curX;
return true;

case MotionEvent.ACTION_MOVE:
if (!isDragging) {
isDragging = true;
menu.setVisibility(View.VISIBLE);
}
diffX = curX – prevX;
if (contentXOffset + diffX <= 0) {
diffX = -contentXOffset;
} else if (contentXOffset + diffX > mainLayoutWidth
– menuRightMargin) {
diffX = mainLayoutWidth – menuRightMargin – contentXOffset;
}
content.offsetLeftAndRight(diffX);
contentXOffset += diffX;
this.invalidate();

prevX = curX;
lastDiffX = diffX;
return true;

case MotionEvent.ACTION_UP:
Log.d(“MainLayout.java onContentTouch()”, “Up lastDiffX ”
+ lastDiffX);

if (lastDiffX > 0) {
currentMenuState = MenuState.SHOWING;
menuScroller.startScroll(contentXOffset, 0,
menu.getLayoutParams().width – contentXOffset, 0,
SLIDING_DURATION);
} else if (lastDiffX < 0) {
currentMenuState = MenuState.HIDING;
menuScroller.startScroll(contentXOffset, 0, -contentXOffset, 0,
SLIDING_DURATION);
}
menuHandler.postDelayed(menuRunnable, QUERY_INTERVAL);
this.invalidate();
isDragging = false;
prevX = 0;
lastDiffX = 0;
return true;

default:
break;
}

return false;
}
}
Layout1.java
package com.android.slidingmenuexample;

import android.os.Bundle;
import android.support.v4.app.Fragment;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;

public class Layout1 extends Fragment {

@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
View view = inflater.inflate(R.layout.fragment_layout1, null);
return view;
}
}
Layout2.java
package com.android.slidingmenuexample;

import android.os.Bundle;
import android.support.v4.app.Fragment;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;

public class Layout2 extends Fragment {

@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
View view = inflater.inflate(R.layout.fragment_layout2, null);
return view;
}
}
activity_main.xml

<com.android.slidingmenuexample.MainLayout xmlns:android=”http://schemas.android.com/apk/res/android”
android:layout_width=”match_parent”
android:layout_height=”match_parent” >

<LinearLayout
xmlns:android=”http://schemas.android.com/apk/res/android”
android:layout_width=”match_parent”
android:layout_height=”match_parent”
android:orientation=”vertical” >

<ListView
android:id=”@+id/menu_listview”
android:layout_width=”wrap_content”
android:layout_height=”match_parent”
android:background=”@android:color/holo_purple”
android:cacheColorHint=”#00000000″ >
</ListView>
</LinearLayout>

<LinearLayout
xmlns:android=”http://schemas.android.com/apk/res/android”
android:layout_width=”match_parent”
android:layout_height=”match_parent”
android:orientation=”vertical” >

<!– This acts as Actionbar –>
<LinearLayout
android:layout_width=”match_parent”
android:layout_height=”wrap_content”
android:background=”@android:color/darker_gray”
android:orientation=”horizontal” >

<Button
android:layout_width=”wrap_content”
android:layout_height=”wrap_content”
android:onClick=”toggleMenu”
android:text=”Menu”
android:id=”@+id/button_menu” />

<TextView
android:layout_width=”0dp”
android:layout_height=”wrap_content”
android:text=”Layout 1″
android:gravity=”center”
android:id=”@+id/activity_main_content_title”
android:layout_weight=”1″ />

</LinearLayout>

<!– This is where fragment will show up –>
<FrameLayout
android:id=”@+id/activity_main_content_fragment”
android:layout_width=”match_parent”
android:layout_height=”match_parent” >

</FrameLayout>

</LinearLayout>

</com.android.slidingmenuexample.MainLayout>
fragment_layout1.xml

<?xml version=”1.0″ encoding=”utf-8″?>
<RelativeLayout xmlns:android=”http://schemas.android.com/apk/res/android”
android:layout_width=”match_parent”
android:layout_height=”match_parent”
android:background=”@android:color/holo_blue_dark” >

<TextView
android:layout_width=”match_parent”
android:layout_height=”wrap_content”
android:layout_centerInParent=”true”
android:gravity=”center”
android:text=”Layout 1″
android:textColor=”@android:color/black”
android:textSize=”20sp” />

</RelativeLayout>
fragment_layout2.xml

<?xml version=”1.0″ encoding=”utf-8″?>
<RelativeLayout xmlns:android=”http://schemas.android.com/apk/res/android”
android:layout_width=”match_parent”
android:layout_height=”match_parent”
android:background=”@android:color/holo_green_dark”
android:orientation=”vertical” >

<TextView
android:layout_width=”wrap_content”
android:layout_height=”wrap_content”
android:layout_centerInParent=”true”
android:text=”Layout2″
android:textColor=”@android:color/black”
android:textSize=”20sp” />

</RelativeLayout>
res/values/menu_items.xml

<?xml version=”1.0″ encoding=”utf-8″?>
<resources>
<string-array name=”menu_items”>
<item >Layout 1</item>
<item >Layout 2</item>
</string-array>
</resources>

Scroll to Top

Discover more from CODE t!ps

Subscribe now to keep reading and get access to the full archive.

Continue reading