package net.avenwu.support.widget;
import net.avenwu.support.BuildConfig;
import net.avenwu.support.R;
import android.content.Context;
import android.util.AttributeSet;
import android.util.Log;
import android.util.TypedValue;
import android.view.MotionEvent;
import android.view.View;
import android.view.ViewConfiguration;
import android.view.ViewGroup;
import android.view.animation.Interpolator;
import android.widget.FrameLayout;
import android.widget.Scroller;
public class DrawerFrame extends FrameLayout {
FrameLayout left;
FrameLayout main;
Scroller scroller;
public DrawerFrame(Context context) {
this(context, null);
}
public DrawerFrame(Context context, AttributeSet attrs) {
this(context, attrs, 0);
}
public DrawerFrame(Context context, AttributeSet attrs, int defStyle) {
super(context, attrs, defStyle);
init(attrs, defStyle);
}
private void init(AttributeSet attrs, int defStyle) {
// final TypedArray a = getContext().obtainStyledAttributes(attrs, R.styleable.DrawerFrame, defStyle, 0);
// a.recycle();
scroller = new Scroller(getContext(), new Interpolator() {
@Override
public float getInterpolation(float input) {
return (float) (1.0D + Math.pow(input - 1.0D, 5.0D));
}
});
MENU_WIDTH = (int) TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_DIP, 200,
getResources().getDisplayMetrics());
main = new FrameLayout(getContext());
main.setId(R.id.main);
main.setLayoutParams(new FrameLayout.LayoutParams(ViewGroup.LayoutParams.MATCH_PARENT,
ViewGroup.LayoutParams.MATCH_PARENT));
main.setBackgroundColor(getResources().getColor(android.R.color.holo_blue_bright));
addView(main);
left = new FrameLayout(getContext());
left.setId(R.id.menu);
left.setLayoutParams(new FrameLayout.LayoutParams(MENU_WIDTH, ViewGroup.LayoutParams.MATCH_PARENT));
addView(left);
ViewConfiguration configuration = ViewConfiguration.get(getContext());
touchSlop = configuration.getScaledTouchSlop();
}
float mSrcX;
int MENU_WIDTH;
@Override
public boolean onInterceptTouchEvent(MotionEvent ev) {
if (!mSlidable) return false;
final int action = ev.getAction();
if (action != MotionEvent.ACTION_DOWN && isSliding) return true;
switch (action) {
case MotionEvent.ACTION_CANCEL:
case MotionEvent.ACTION_UP:
return false;
case MotionEvent.ACTION_MOVE:
if (Math.abs(ev.getX() - mSrcX) > touchSlop) {
mSrcX = ev.getX();
isSliding = true;
}
break;
case MotionEvent.ACTION_DOWN:
isSliding = false;
mSrcX = ev.getX();
break;
}
return isSliding;
}
boolean isSliding = false;
boolean mSlidable = true;
int touchSlop;
public void setSlide(boolean enable) {
mSlidable = enable;
}
@Override
public boolean onTouchEvent(MotionEvent event) {
d("UIView", "event:" + event.toString());
final int action = event.getAction();
switch (action) {
case MotionEvent.ACTION_DOWN:
mSrcX = event.getX();
break;
case MotionEvent.ACTION_MOVE:
int oldx = left.getScrollX();
float dx = mSrcX - event.getX();
if (dx != 0) {
left.setVisibility(VISIBLE);
float x = oldx + dx;
d("onTouchEvent", "move, oldx=" + oldx + ", dx=" + dx + ", mLeftView=" +
left.getLeft() + ", right=" + left.getRight() + ", getX=" + event.getX() + ", mSrcX=" + mSrcX);
d("onTouchEvent", "before x=" + x);
if (MENU_WIDTH < x) {
x = MENU_WIDTH;
}
if (0 > x) {
x = 0;
}
d("onTouchEvent", "after x=" + x);
left.scrollTo((int) x, 0);
mSrcX = event.getX();
}
break;
case MotionEvent.ACTION_UP:
int currentX = left.getScrollX();
if (currentX + mSrcX - event.getX() >= MENU_WIDTH / 2.0) {
int duration = (int) (Math.abs(MENU_WIDTH - currentX + 0.5f) / MENU_WIDTH * 1000);
scroller.startScroll(currentX, 0, MENU_WIDTH - currentX, 0, duration);
invalidate();
} else {
int duration = (int) (Math.abs(currentX + 0.5f) / MENU_WIDTH * 1000);
scroller.startScroll(currentX, 0, 0 - currentX, 0, duration);
invalidate();
}
break;
case MotionEvent.ACTION_CANCEL:
break;
}
return true;
}
@Override
protected void onLayout(boolean changed, int left, int top, int right, int bottom) {
int count = getChildCount();
for (int i = 0; i < count; i++) {
View child = getChildAt(i);
if (child.getVisibility() == GONE) continue;
final LayoutParams lp = (LayoutParams) child.getLayoutParams();
if (child.getId() == R.id.menu) {
final int childWidth = child.getMeasuredWidth();
final int childHeight = child.getMeasuredHeight();
int childLeft = 0;
child.layout(childLeft, lp.topMargin, childLeft + childWidth, lp.topMargin + childHeight);
child.scrollTo(MENU_WIDTH, 0);
} else if (child.getId() == R.id.main) {
child.layout(0, 0, child.getMeasuredWidth(), child.getMeasuredHeight());
}
}
}
public void showMenuSmoothly() {
scroller.startScroll(MENU_WIDTH, 0, -MENU_WIDTH, 0, 1000);
invalidate();
}
public void dismissSmoothly() {
int start = scroller.getCurrX();
scroller.startScroll(start, 0, MENU_WIDTH - start, 0, 1000);
invalidate();
}
public void setMenuView(View view) {
left.removeAllViews();
left.addView(view);
requestLayout();
}
public void setContentView(View view) {
main.removeAllViews();
main.addView(view);
requestLayout();
}
@Override
public void computeScroll() {
d("computeScroll", "computeScroll");
if (scroller.computeScrollOffset()) {
int oldx = left.getScrollX();
int x = scroller.getCurrX();
d("computeScroll", "try scroll, oldx=" + oldx + ", x=" + x);
if (oldx != x) {
//this can only effect on the content view inside of mLeftView
left.scrollTo(x, 0);
left.invalidate();
}
invalidate();
} else {
scroller.abortAnimation();
}
}
private void d(String tag, String text) {
if (BuildConfig.DEBUG) {
Log.d(tag, text);
}
}
}