所以我有一个自定义视图小部件,我允许用户用手指拖动。他们将它拖到一个基于 FrameLayout 的自定义滚动视图中(这里的代码:http: //blog.gorges.us/2010/06/android-two-dimensional-scrollview/),其中包含一个 RelativeLayout,以便他们可以放置它可以放在他们想要的地方,并且有足够的空间在屏幕上不可见,也可以放置物品。
我想要发生的是,如果用户将小部件移动到可见滚动区域的边缘附近,就是在适当的方向滚动该区域,直到他们松开(ACTION_UP,在这种情况下无论如何都不会发生更多事件)或已远离边缘。现在的代码有两个问题:
1) 我的手机 (T-Mobile G2) 会继续触发 ACTION_MOVE,即使我的手指还在,因为我的 Nexus 7 平板电脑在移动之前不会继续触发。我需要可靠地继续触发此事件,直到 ACTION_UP。
2)该区域滚动,但仅当我将手指移向屏幕边缘时。换句话说,我希望一个静止的手指在靠近边缘时继续滚动和移动对象,但这并没有发生。
我错过了什么?这是处理小部件移动的 onTouchEvent
@Override
public boolean onTouchEvent(MotionEvent event) {
if (event.getAction() == MotionEvent.ACTION_MOVE
&& this.getParent() != null) {
getParent().requestDisallowInterceptTouchEvent(true);
}
// mScrollParent gets set in a setter and points to the TwoDScrollView
// mOffsetX/Y is based on where the user touches versus the position of the custom view
// mWidth/mHeight gets set once in the GestureDetector based on the custom view's getWidth()/getHeight()
// mTitleBarHeight gets set once in the GestureDetctor onDown event
// lp is a ViewGroup.LayoutParams type
if (!mGestureDetector.onTouchEvent(event)) {
if (event.getAction() == MotionEvent.ACTION_MOVE) {
int finalX = (int) (event.getRawX() - mOffsetX);
int finalY = (int) (event.getRawY() - mOffsetY - (mTitleBarHeight > 0 ? mTitleBarHeight * 2
: 0));
if (finalX < 0 || finalY < 0)
return false;
int scrollLeft = (int) Math.ceil(mScrollParent.getScrollX() * 1.05);
int scrollTop = (int) Math.ceil(mScrollParent.getScrollY() * 1.05);
int scrollRight = (int) Math.floor((scrollLeft + mScrollParent.getRight()) * 0.95);
int scrollBottom = (int) Math.floor((scrollTop + mScrollParent.getBottom()) * 0.95);
int scrollX = 0;
int scrollY = 0;
if (scrollLeft > finalX)
scrollX = finalX - scrollLeft;
if (scrollRight < (finalX + mWidth))
scrollX = (finalX + mWidth)- scrollRight;
if (scrollTop > finalY)
scrollY = finalY - scrollTop;
if (scrollBottom < (finalY + mHeight))
scrollY = (finalY + mHeight) - scrollBottom;
if (scrollX != 0 || scrollY != 0)
mScrollParent.scrollBy(scrollX * 4, scrollY * 4);
lp.setMargins(finalX + scrollX, finalY + scrollY, 0, 0);
setLayoutParams(lp);
return true;
}
} else if (event.getAction() == MotionEvent.ACTION_UP) {
return true;
} else {
return super.onTouchEvent(event);
}
} else {
return true;
}
}