问题描述
我正在使用Android Drag& Drop API,并尝试将拖动阴影的锚点设置为在视图
中进行触摸的位置。 dafault行为是将锚定在 View
的中间。
I am using Android Drag&Drop API and am trying to set the anchor of the drag shadow to the point where the touch was made in the View
. The dafault behavior is to have the anchor the middle of the View
.
我做了一些研究,似乎这可以通过覆盖方法。从我的理解,如果我更改x,y坐标 shadowTouchPoint
,它应该修改拖动锚点的坐标。
I did some research and it seems this can be done by overriding the onProvideShadowMetrics (Point shadowSize, Point shadowTouchPoint)
method in the DragShadowBuilder
class. From what I understood, if I change the x,y coordinates of shadowTouchPoint
it should modify the coordinates of the drag anchor.
我所做的是如下扩展 DragShadowBuilder
类:
What I did was to extend the DragShadowBuilder
class like so:
class EventDragShadowBuilder extends DragShadowBuilder {
int touchPointXCoord, touchPointYCoord;
public EventDragShadowBuilder() {
super();
}
public EventDragShadowBuilder(View view, int touchPointXCoord,
int touchPointYCoord) {
super(view);
this.touchPointXCoord = touchPointXCoord;
this.touchPointYCoord = touchPointYCoord;
}
@Override
public void onProvideShadowMetrics(Point shadowSize,
Point shadowTouchPoint) {
shadowTouchPoint.set(touchPointXCoord, touchPointYCoord);
super.onProvideShadowMetrics(shadowSize, shadowTouchPoint);
}
}
在 Fragment
我使用drag& drop我创建了两个监听器为
查看
启动拖动事件:
mEventLongClickListener = new OnLongClickListener() {
@Override
public boolean onLongClick(View view) {
EventDragShadowBuilder shadowBuilder = new EventDragShadowBuilder(
view, mEventTouchXCoord, mEventTouchYCoord);
view.startDrag(null, shadowBuilder, view, 0);
return true;
}
};
// We need this listener in order to get the corect coordinates for the
// drag shadow
mEventTouchListener = new OnTouchListener() {
@Override
public boolean onTouch(View view, MotionEvent event) {
final int action = event.getAction();
switch (action & MotionEvent.ACTION_MASK) {
case MotionEvent.ACTION_DOWN: {
mEventTouchXCoord = (int) event.getX();
mEventTouchYCoord = (int) event.getY();
break;
}
}
return false;
}
};
我设置了拖曳听众:
itemView.setOnLongClickListener(mEventLongClickListener);
itemView.setOnTouchListener(mEventTouchListener);
一切都可以到这里。但是,当我测试应用程序并开始拖动过程时,拖动阴影将集中在触摸点下方。所以它使用默认行为。我尝试调试,我看到 mEventTouchXCoord
和 mEventTouchYCoord
设置正确。方法 shadowTouchPoint.set(touchPointXCoord,touchPointYCoord);
获取正确的坐标,但仍然将阴影居中。
Everything ok up to here. But when I test the app and start the drag process, the drag shadow is centered under the touch point. So it uses the default behavior. I tried debugging and I see that mEventTouchXCoord
and mEventTouchYCoord
are set correctly. The method shadowTouchPoint.set(touchPointXCoord, touchPointYCoord);
gets the correct coordinates but still it centers the shadow.
我不知道我做错了什么。也许我误解了API。任何帮助或提示将不胜感激。
I don't know what I'm doing wrong. Maybe I misunderstood the API. Any help with or hint would be much appreciated.
推荐答案
好的,所以像Scoup说的问题是在$ c> onProvideShadowMetrics()方法。事实是,如果我删除超级构造函数 super.onProvideShadowMetrics(shadowSize,shadowTouchPoint);
,它不会再显示拖动阴影。
Ok, so like Scoup said the problem was in the onProvideShadowMetrics()
method. The fact is, if I remove the super constructor, super.onProvideShadowMetrics(shadowSize, shadowTouchPoint);
, it will not show the drag shadow anymore.
仔细观察API方法,这是我发现的:
Taking a closer look at the API method this is what I found:
public void onProvideShadowMetrics(Point shadowSize, Point shadowTouchPoint) {
final View view = mView.get();
if (view != null) {
shadowSize.set(view.getWidth(), view.getHeight());
shadowTouchPoint.set(shadowSize.x / 2, shadowSize.y / 2);
} else {
Log.e(View.VIEW_LOG_TAG, "Asked for drag thumb metrics but no view");
}
}
确实,它会重置 shadowTouchPoint
到拖动的视图
中间。但它也将拖动阴影初始化为正确的尺寸。虽然我想要拖动阴影尺寸设置正确我不想重置 shadowTouchPoint
。
So indeed, it resets the shadowTouchPoint
to the middle of the dragged View
. But it also initializes the drag shadow to the correct dimensions. While I want the drag shadow dimensions to be set correctly I don't want to reset shadowTouchPoint
.
最简单要实现这一点的方法是调用超级构造函数之前使用自定义值初始化 shadowTouchPoint
,如下所示:
The easiest way to acheive this is to call the super constructor before initializing the shadowTouchPoint
with the custom values, like so:
@Override
public void onProvideShadowMetrics(Point shadowSize,
Point shadowTouchPoint) {
super.onProvideShadowMetrics(shadowSize, shadowTouchPoint);
shadowTouchPoint.set(touchPointXCoord, touchPointYCoord);
}
另一个解决方案是处理拖动阴影查看
自己并跳过超级构造函数。我会收到一个详细的更新。
Another solution is to deal with the drag shadow View
yourself and skip the super constructor altogether. I will get back with a detailed update.
这篇关于拖动视图时设置自定义锚点的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!