Saturday, January 5, 2013

Android-Sliding Drawer

SlidingDrawer hides content out of the screen and allows the user to drag a handle to bring the content on screen. SlidingDrawer can be used vertically or horizontally. A special widget composed of two children views: the handle, that the users drags, and the content, attached to the handle and dragged with it. SlidingDrawer should be used as an overlay inside layouts. This means SlidingDrawer should only be used inside of a FrameLayout or a RelativeLayout for instance. The size of the SlidingDrawer defines how much space the content will occupy once slid out so SlidingDrawer should usually use match_parent for both its dimensions.

Note:-Sliding Drawer wont work inside Scroll View


To implement sliding drawer take a sliding drawer component in your xml like this:-

<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent" >

    <TextView
        android:id="@+id/textView1"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_centerHorizontal="true"
        android:layout_centerVertical="true"
        android:text="@string/hello_world"
        tools:context=".MainActivity" />

    <SlidingDrawer
        android:id="@+id/slidingDrawer1"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:layout_alignParentBottom="true"
        android:content="@+id/content"
        android:handle="@+id/handle" >

        <Button
            android:id="@+id/handle"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:text="Handle" />

        <LinearLayout
            android:id="@+id/content"
            android:layout_width="match_parent"
            android:layout_height="match_parent"
            android:background="@android:color/darker_gray"
            android:orientation="vertical" >
            <Button android:layout_width="fill_parent"
                android:layout_height="50dp"
                android:text="Button1"/>
            <Button android:layout_width="fill_parent"
                android:layout_height="50dp"
                android:text="Button2"/>
            <Button android:layout_width="fill_parent"
                android:layout_height="50dp"
                android:text="Button3"/>
            <Button android:layout_width="fill_parent"
                android:layout_height="50dp"
                android:text="Button4"/>
            <Button android:layout_width="fill_parent"
                android:layout_height="50dp"
                android:text="Button5"/>
            <Button android:layout_width="fill_parent"
                android:layout_height="50dp"
                android:text="Button6"/>
            <Button android:layout_width="fill_parent"
                android:layout_height="50dp"
                android:text="Button7"/>
        </LinearLayout>
    </SlidingDrawer>

</RelativeLayout>


and do whatever action you want to do up on click of buttons.

Here the sliding drawer will occupy the entire screen because in API's onMeasure method it was designed to occupy the entire screen.In order to avoid that take a custom class which extend sliding Drawer and override onmeasure method to occupy wrapcontent like this



package com.example.testslidingdrawer;

import android.content.Context;
import android.util.AttributeSet;
import android.view.View;
import android.widget.SlidingDrawer;

/**
 * TODO Class description goes here.
 * @version
 */
public class MenuSlidingDrawer extends SlidingDrawer{

/**
* @param context Context
* @param attrs AttributeSet
* @param defStyle int
*/
public MenuSlidingDrawer(Context context, AttributeSet attrs, int defStyle) {
super(context, attrs, defStyle);

int orientation = attrs.getAttributeIntValue("android", "orientation", ORIENTATION_VERTICAL);
mTopOffset = attrs.getAttributeIntValue("android", "topOffset", 0);
mVertical = (orientation == SlidingDrawer.ORIENTATION_VERTICAL);
}

/**
* @param context Context
* @param attrs AttributeSet
*/
public MenuSlidingDrawer(Context context, AttributeSet attrs) {
super(context, attrs);

int orientation = attrs.getAttributeIntValue("android", "orientation", ORIENTATION_VERTICAL);
mTopOffset = attrs.getAttributeIntValue("android", "topOffset", 0);
mVertical = (orientation == SlidingDrawer.ORIENTATION_VERTICAL);
}

/**
* TODO Method Description as a Single Sentence.
*
* @param widthMeasureSpec int
* @param heightMeasureSpec int
*/
@Override
protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {

int widthSpecMode = MeasureSpec.getMode(widthMeasureSpec);
int widthSpecSize =  MeasureSpec.getSize(widthMeasureSpec);

int heightSpecMode = MeasureSpec.getMode(heightMeasureSpec);
int heightSpecSize =  MeasureSpec.getSize(heightMeasureSpec);

if (widthSpecMode == MeasureSpec.UNSPECIFIED || heightSpecMode == MeasureSpec.UNSPECIFIED) {
throw new RuntimeException("SlidingDrawer cannot have UNSPECIFIED dimensions");
}

final View handle = getHandle();
final View content = getContent();
measureChild(handle, widthMeasureSpec, heightMeasureSpec);

if (mVertical) {
int height = heightSpecSize - handle.getMeasuredHeight() - mTopOffset;

content.measure(widthMeasureSpec, MeasureSpec.makeMeasureSpec(height, heightSpecMode));
heightSpecSize = handle.getMeasuredHeight() + mTopOffset + content.getMeasuredHeight();
widthSpecSize = content.getMeasuredWidth();
if (handle.getMeasuredWidth() > widthSpecSize){ widthSpecSize = handle.getMeasuredWidth();}
}
else {
int width = widthSpecSize - handle.getMeasuredWidth() - mTopOffset;
getContent().measure(MeasureSpec.makeMeasureSpec(width, widthSpecMode), heightMeasureSpec);
widthSpecSize = handle.getMeasuredWidth() + mTopOffset + content.getMeasuredWidth();
heightSpecSize = content.getMeasuredHeight();
if (handle.getMeasuredHeight() > heightSpecSize){ heightSpecSize = handle.getMeasuredHeight();}
}

setMeasuredDimension(widthSpecSize, heightSpecSize);
}
private boolean mVertical;
private int mTopOffset;
}

and in the xml change the SlidingDrawer to packagename.MenuSlidingDrawer you will get it.



 

No comments:

Post a Comment