package com.android.launcher;
import android.content.Context;
import android.content.res.TypedArray;
import android.graphics.drawable.RotateDrawable;
import android.util.AttributeSet;
import android.util.Log;
import android.view.GestureDetector;
import android.view.Gravity;
import android.view.MotionEvent;
import android.view.View;
import android.view.GestureDetector.OnGestureListener;
import android.view.View.OnClickListener;
import android.view.animation.Animation;
import android.view.animation.TranslateAnimation;
import android.view.animation.Animation.AnimationListener;
import android.widget.FrameLayout;
import android.widget.LinearLayout;
public class DockBar extends LinearLayout implements OnClickListener {
public static final int TOP=0;
public static final int BOTTOM=1;
public static final int LEFT=2;
public static final int RIGHT=3;
private static final int OPEN=0;
private static final int CLOSED=1;
private static final int ANIM_DURATION = 250;
private int mHandleId;
private int mContentId;
private View mHandle;
private int mState=CLOSED;
private int mPosition=TOP;
private boolean mFirstLayout=true;
//private View mContent;
private GestureDetector mGestureDetector;
private DockbarGestureListener mGestureListener;
public boolean mInterceptClicks=false;
private DockBarListener mDockBarListener;
public DockBar(Context context) {
super(context);
// TODO Auto-generated constructor stub
}
public DockBar(Context context, AttributeSet attrs) {
super(context, attrs);
// TODO Auto-generated constructor stub
TypedArray a = context.obtainStyledAttributes(attrs, R.styleable.DockBar);
RuntimeException e = null;
mHandleId = a.getResourceId(R.styleable.DockBar_handle, 0);
/*if (mHandleId == 0) {
e = new IllegalArgumentException(a.getPositionDescription() +
": The handle attribute is required and must refer to a valid child.");
}*/
mContentId = a.getResourceId(R.styleable.DockBar_content, 0);
if (mContentId == 0) {
e = new IllegalArgumentException(a.getPositionDescription() +
": The content attribute is required and must refer to a valid child.");
}
mPosition = a.getInt(
R.styleable.DockBar_position, mPosition);
a.recycle();
mGestureListener = new DockbarGestureListener();
//mGestureDetector = new GestureDetector(mGestureListener);
mGestureDetector = new GestureDetector(context, mGestureListener);
}
@Override
protected void onFinishInflate() {
super.onFinishInflate();
if(mHandleId!=0){
mHandle = findViewById(mHandleId);
/*if (mHandle == null) {
String name = getResources().getResourceEntryName(mHandleId);
throw new RuntimeException("Your DockBar must have a child View whose id attribute is 'R.id." + name + "'");
}*/
if(mHandle!=null)
mHandle.setOnClickListener(this);
}
setVisibility(VISIBLE);
}
@Override
protected void onLayout(boolean changed, int l, int t, int r, int b) {
// TODO Auto-generated method stub
super.onLayout(changed, l, t, r, b);
if(mFirstLayout){
setVisibility(GONE);
mFirstLayout=false;
}
}
public void open(){
dispatchDockBarEvent(true);
setClickable(false);
mState=OPEN;
setVisibility(View.VISIBLE);
int x=0;
int y=0;
switch (mPosition) {
case LEFT:
x=getWidth();
break;
case RIGHT:
x=getWidth();
break;
case TOP:
y=-getHeight();
break;
case BOTTOM:
y=getHeight();
break;
}
TranslateAnimation anim=new TranslateAnimation(x, 0,y, 0);
anim.setDuration(ANIM_DURATION);
startAnimation(anim);
}
public void close(){
dispatchDockBarEvent(false);
mState=CLOSED;
int x=0;
int y=0;
switch (mPosition) {
case LEFT:
x=-getWidth();
break;
case RIGHT:
x=getWidth();
break;
case TOP:
y=-getHeight();
break;
case BOTTOM:
y=getHeight();
break;
}
TranslateAnimation anim=new TranslateAnimation(0, x, 0,y);
anim.setDuration(ANIM_DURATION);
anim.setAnimationListener(new AnimationListener() {
//@Override
public void onAnimationStart(Animation animation) {
// TODO Auto-generated method stub
}
//@Override
public void onAnimationRepeat(Animation animation) {
// TODO Auto-generated method stub
}
//@Override
public void onAnimationEnd(Animation animation) {
// TODO Auto-generated method stub
setVisibility(View.GONE);
}
});
startAnimation(anim);
}
public boolean isOpen(){
return (mState==OPEN);
}
public int getSize(){
if(mPosition==TOP || mPosition==BOTTOM){
return getHeight();
}else{
return getWidth();
}
}
@Override
public boolean onInterceptTouchEvent(MotionEvent ev) {
if (mGestureDetector.onTouchEvent(ev)) {
return true;
}
if(!mInterceptClicks){
return super.onInterceptTouchEvent(ev);
}
return true;
}
@Override
public boolean onTouchEvent(MotionEvent ev) {
if (mGestureDetector.onTouchEvent(ev)) {
return true;
}
if(!mInterceptClicks){
return super.onTouchEvent(ev);
}
return false;
}
class DockbarGestureListener implements OnGestureListener {
public boolean onDown(MotionEvent e) {
mInterceptClicks=false;
return false;
}
public boolean onFling(MotionEvent e1, MotionEvent e2, float velocityX, float velocityY) {
float velocity=0;
switch (mPosition) {
case LEFT:
if(velocityX<0 && Math.abs(velocityY)<Math.abs(velocityX))
velocity=Math.abs(velocityX);
break;
case RIGHT:
if(velocityX>0 && Math.abs(velocityY)<Math.abs(velocityX))
velocity=Math.abs(velocityX);
break;
case TOP:
if(velocityY<0 && Math.abs(velocityY)>Math.abs(velocityX))
velocity=Math.abs(velocityY);
break;
case BOTTOM:
if(velocityY>0 && Math.abs(velocityY)>Math.abs(velocityX))
velocity=Math.abs(velocityY);
break;
}
if(velocity>0){
close();
mInterceptClicks=true;
return true;
}
return false;
}
public void onLongPress(MotionEvent e) {
//not used
}
public boolean onScroll(MotionEvent e1, MotionEvent e2, float distanceX, float distanceY) {
//not used
return false;
}
public void onShowPress(MotionEvent e) {
//not used
}
public boolean onSingleTapUp(MotionEvent e) {
//not used
return false;
}
}
//@Override
public void onClick(View v) {
// TODO Auto-generated method stub
if(v==mHandle){
close();
}
}
public void setDockBarListener(DockBarListener listener) {
mDockBarListener = listener;
}
/**
* Dispatches a trigger event to listener. Ignored if a listener is not set.
* @param whichHandle the handle that triggered the event.
*/
private void dispatchDockBarEvent(boolean open) {
if (mDockBarListener != null) {
if(open){
mDockBarListener.onOpen();
}else{
mDockBarListener.onClose();
}
}
}
/**
* Interface definition for a callback to be invoked when a tab is triggered
* by moving it beyond a threshold.
*/
public interface DockBarListener {
void onOpen();
void onClose();
}
}