您的位置:首页 > 其它

我的ViewGroup

2013-11-21 10:14 375 查看
public class MyViewGroup extends ViewGroup implements OnGestureListener{

private static final String TAG = "sxy";

private int mCellWidth = 60;
private int mCellHeight = 60;

private float mLastMotionY;// 最后点击的点
private GestureDetector detector;
int move = 0;// 移动距离
int MAXMOVE = 850;// 最大允许的移动距离
private Scroller mScroller;
int up_excess_move = 0;// 往上多移的距离
int down_excess_move = 0;// 往下多移的距离
private final static int TOUCH_STATE_REST = 0;
private final static int TOUCH_STATE_SCROLLING = 1;
private int mTouchSlop;
private int mTouchState = TOUCH_STATE_REST;
Context mContext;

public MyViewGroup(Context context) {
super(context);
// TODO Auto-generated constructor stub
init(context);
}

public MyViewGroup(Context context, AttributeSet attrs) {
super(context, attrs);
// TODO Auto-generated constructor stub
init(context);
}

public MyViewGroup(Context context, AttributeSet attrs,
int defStyle) {
super(context, attrs, defStyle);
// TODO Auto-generated constructor stub
init(context);
}

private void init(Context context){

mContext = context;
// TODO Auto-generated constructor stub
//        setBackgroundResource(R.drawable.pic);
mScroller = new Scroller(context);
detector = new GestureDetector(this);

final ViewConfiguration configuration = ViewConfiguration.get(context);
// 获得可以认为是滚动的距离
mTouchSlop = configuration.getScaledTouchSlop();
}

//设置单元格宽度
public void setCellWidth(int w) {
mCellWidth = w;
requestLayout();
}

//设置单元格高度
public void setCellHeight(int h) {
mCellHeight = h;
requestLayout();
}

@Override
protected void dispatchDraw(Canvas canvas) {
// TODO Auto-generated method stub

//		//获取布局控件宽高
//		int width = getWidth();
//		int height = getHeight();
//		//创建画笔
//		Paint mPaint = new Paint();
//		//设置画笔的各个属性
//		mPaint.setColor(Color.BLUE);
//		mPaint.setStyle(Paint.Style.STROKE);
//		mPaint.setStrokeWidth(10);
//		mPaint.setAntiAlias(true);

//最后必须调用父类的方法
super.dispatchDraw(canvas);
}

@Override
protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
// TODO Auto-generated method stub

//创建测量参数
int cellWidthSpec = MeasureSpec.makeMeasureSpec(mCellWidth, MeasureSpec.AT_MOST);
int cellHeightSpec = MeasureSpec.makeMeasureSpec(mCellHeight, MeasureSpec.AT_MOST);

//记录ViewGroup中Child的总个数
int count = getChildCount();

//设置子空间Child的宽高
for (int i = 0; i < count; i++) {
View childView = getChildAt(i);
childView.measure(cellWidthSpec, cellHeightSpec);
}

//设置容器控件所占区域大小
setMeasuredDimension(resolveSize(mCellWidth * count, widthMeasureSpec), resolveSize(mCellHeight * count, heightMeasureSpec));
}

@Override
protected void onLayout(boolean changed, int l, int t, int r, int b) {
// TODO Auto-generated method stub

int cellWidth = mCellWidth;
int cellHeight = mCellHeight;
int columns = (r - l) / cellWidth;

if(columns < 0) {
columns = 1;
}

int x = 0;
int y = 0;
int i = 0;
int count = getChildCount();

for (int j = 0; j < count; j++) {
final View childView = getChildAt(j);
//获取子控件Child的宽高
int w = childView.getMeasuredWidth();
int h = childView.getMeasuredHeight();
//计算子控件的顶点坐标
int left = x + ((cellWidth - w)/2);
int top = y + ((cellHeight - h)/2);
//int left = x;
//int top = y;
//布局子控件
childView.layout(left, top, left + w, top + h);

if(i >= (columns - 1)) {
i = 0;
x = 0;
y += cellHeight;
} else {
i++;
x += cellWidth;

}

}

}

@Override
public boolean onDown(MotionEvent e) {
// TODO Auto-generated method stub
return true;
}

@Override
public void onShowPress(MotionEvent e) {
// TODO Auto-generated method stub

}

@Override
public boolean onSingleTapUp(MotionEvent e) {
// TODO Auto-generated method stub
return false;
}

@Override
public boolean onScroll(MotionEvent e1, MotionEvent e2, float distanceX,
float distanceY) {
// TODO Auto-generated method stub
return false;
}

@Override
public void onLongPress(MotionEvent e) {
// TODO Auto-generated method stub

}

@Override
public void computeScroll() {
if (mScroller.computeScrollOffset()) {
// 返回当前滚动X方向的偏移
scrollTo(0, mScroller.getCurrY());
postInvalidate();
}
}

@Override
public boolean onInterceptTouchEvent(MotionEvent ev) {
final int action = ev.getAction();

final float y = ev.getY();
switch (ev.getAction())
{
case MotionEvent.ACTION_DOWN:

mLastMotionY = y;
mTouchState = mScroller.isFinished() ? TOUCH_STATE_REST
: TOUCH_STATE_SCROLLING;
break;
case MotionEvent.ACTION_MOVE:
final int yDiff = (int) Math.abs(y - mLastMotionY);
boolean yMoved = yDiff > mTouchSlop;
// 判断是否是移动
if (yMoved) {
mTouchState = TOUCH_STATE_SCROLLING;
}
break;
case MotionEvent.ACTION_UP:
mTouchState = TOUCH_STATE_REST;
break;
}
return mTouchState != TOUCH_STATE_REST;
}

@Override
public boolean onTouchEvent(MotionEvent ev) {

// final int action = ev.getAction();

final float y = ev.getY();
switch (ev.getAction())
{
case MotionEvent.ACTION_DOWN:
if (!mScroller.isFinished()) {
mScroller.forceFinished(true);
move = mScroller.getFinalY();
}
mLastMotionY = y;
break;
case MotionEvent.ACTION_MOVE:
if (ev.getPointerCount() == 1) {

// 随手指 拖动的代码
int deltaY = 0;
deltaY = (int) (mLastMotionY - y);
mLastMotionY = y;
Log.d("move", "" + move);
if (deltaY < 0) {
// 下移
// 判断上移 是否滑过头
if (up_excess_move == 0) {
if (move > 0) {
int move_this = Math.max(-move, deltaY);
move = move + move_this;
scrollBy(0, move_this);
} else if (move == 0) {// 如果已经是最顶端 继续往下拉
Log.d("down_excess_move", "" + down_excess_move);
down_excess_move = down_excess_move - deltaY / 2;// 记录下多往下拉的值
scrollBy(0, deltaY / 2);
}
} else if (up_excess_move > 0)// 之前有上移过头
{
if (up_excess_move >= (-deltaY)) {
up_excess_move = up_excess_move + deltaY;
scrollBy(0, deltaY);
} else {
up_excess_move = 0;
scrollBy(0, -up_excess_move);
}
}
} else if (deltaY > 0) {
// 上移
if (down_excess_move == 0) {
if (MAXMOVE - move > 0) {
int move_this = Math.min(MAXMOVE - move, deltaY);
move = move + move_this;
scrollBy(0, move_this);
} else if (MAXMOVE - move == 0) {
if (up_excess_move <= 100) {
up_excess_move = up_excess_move + deltaY / 2;
scrollBy(0, deltaY / 2);
}
}
} else if (down_excess_move > 0) {
if (down_excess_move >= deltaY) {
down_excess_move = down_excess_move - deltaY;
scrollBy(0, deltaY);
} else {
down_excess_move = 0;
scrollBy(0, down_excess_move);
}
}
}
}
break;
case MotionEvent.ACTION_UP:
// 多滚是负数 记录到move里
if (up_excess_move > 0) {
// 多滚了 要弹回去
scrollBy(0, -up_excess_move);
invalidate();
up_excess_move = 0;
}
if (down_excess_move > 0) {
// 多滚了 要弹回去
scrollBy(0, down_excess_move);
invalidate();
down_excess_move = 0;
}
mTouchState = TOUCH_STATE_REST;
break;
}
return this.detector.onTouchEvent(ev);
}

int Fling_move = 0;
@Override
public boolean onFling(MotionEvent e1, MotionEvent e2, float velocityX,
float velocityY) {
//随手指 快速拨动的代码
Log.d("onFling", "onFling");
if (up_excess_move == 0 && down_excess_move == 0) {

int slow = -(int) velocityY * 3 / 4;
mScroller.fling(0, move, 0, slow, 0, 0, 0, MAXMOVE);
move = mScroller.getFinalY();
computeScroll();
}
return false;
}
}

继承自ViewGroup的类写好后,就可以像普通控件一样使用


                                            
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: