我在活动的根级别上有一个 ViewPager。
寻呼机的每个页面都包含一个 ListFragment(由 FragmentPagerAdapter 支持)。
一些列表视图项目应该包含额外的 ViewPagers 以支持滑动这些项目的内容(例如列表项目内的水平画廊)。
如何嵌套视图寻呼机?ViewPager -> ListView(在页面中) -> ViewPager(在列表项中)
我可以在 ListFragments 之间水平滑动,也可以垂直滑动整个列表,但不能在列表项内滑动。
我在活动的根级别上有一个 ViewPager。
寻呼机的每个页面都包含一个 ListFragment(由 FragmentPagerAdapter 支持)。
一些列表视图项目应该包含额外的 ViewPagers 以支持滑动这些项目的内容(例如列表项目内的水平画廊)。
如何嵌套视图寻呼机?ViewPager -> ListView(在页面中) -> ViewPager(在列表项中)
我可以在 ListFragments 之间水平滑动,也可以垂直滑动整个列表,但不能在列表项内滑动。
我OnTouchListener
在内部添加了一个ViewPager
:
private OnTouchListener mSuppressInterceptListener = new OnTouchListener() {
@Override
public boolean onTouch(View v, MotionEvent event) {
if(
event.getAction() == MotionEvent.ACTION_DOWN &&
v instanceof ViewGroup
) {
((ViewGroup) v).requestDisallowInterceptTouchEvent(true);
}
return false;
}
};
这只是检测内部的 ACTION_DOWN 触摸事件ViewPager
并防止外部拦截它。因为它返回 false,所以应该只触发 ACTION_DOWN 事件;所有其他事件将被忽略。您可以将此侦听器添加到您想要“保护”免受外部ViewPager
滚动的每个元素,但显然如果您想在这些元素上获取任何其他触摸行为,您需要在触摸侦听器内部处理它们,并且可能实现一个更好的监听器。
感谢@Rodja,他首先给了我这个想法。
虽然它不是最好的交互设计,但可以通过覆盖根级 Activity的dispatchTouchEvent(MotionEvent ev)方法并在 mainPager 和当前 ListView 上使用requestDisallowInterceptTouchEvent(true)来防止其他滚动来实现这一点。看这个例子:
@Override
public boolean dispatchTouchEvent(MotionEvent ev) {
Fragment listFragment = getSupportFragmentManager().findFragmentByTag(
"android:switcher:" + R.id.pager + ":" + (mainPager.getCurrentItem()));
mainPager.getChildAt(mainPager.getCurrentItem());
if (listFragment == null)
return super.dispatchTouchEvent(ev);
ViewPager embeddedPager = (ViewPager) listFragment.getView().findViewById(R.id.videopager);
if (embeddedPager != null) {
int[] position = new int[2];
embeddedPager.getLocationOnScreen(position);
if (ev.getY() > position[1] && ev.getY() < position[1] + embeddedPager.getHeight()) {
mainPager.requestDisallowInterceptTouchEvent(true);
if (embeddedPager.getScrollX() % embeddedPager.getWidth() != 0) {
ListView listView = (ListView) listFragment.getView().findViewById(
android.R.id.list);
listView.requestDisallowInterceptTouchEvent(true);
}
}
}
return super.dispatchTouchEvent(ev);
}
您不能真正嵌套需要相同手势来控制它们的元素。由于视图寻呼机已经在捕获水平运动,因此您的嵌套元素将无法获得它。你可能会做很多工作来通过管理焦点等来解决这个问题——但最终你的应用程序会让用户感到困惑。最好不要嵌套使用相同交互的元素……在这种情况下,两个视图寻呼机都在观察左右运动。