Reputation: 95
I have the current layout (obviously simplified here):
<SwipeRefreshLayout>
<MapFragment/>
<ListView/>
</SwipeRefreshLayout>
To solve the issue of having the downward swipe triggering the refresh, I tried doing the following:
mMap.setOnCameraChangeListener(new GoogleMap.OnCameraChangeListener() {
@Override
public void onCameraChange(CameraPosition cameraPosition) {
mSwipeRefreshLayout.setEnabled(false);
}
});
And then enabling back in the listview:
listView.setOnScrollListener(new AbsListView.OnScrollListener() {
@Override
public void onScrollStateChanged(AbsListView view, int scrollState) {
mSwipeRefreshLayout.setEnabled(true);
}
// Prevents the downward swipe from triggering refresh unless the
@Override
public void onScroll(AbsListView view, int firstVisibleItem, int visibleItemCount, int totalItemCount) {
int topRowVerticalPosition = (listView == null || listView.getChildCount() == 0) ? 0 : listView.getChildAt(0).getTop();
mSwipeRefreshLayout.setEnabled((topRowVerticalPosition >= 0));
}
});
However, for some reason, this only works if I swipe two times on the listview, which breaks user experience.
I do not want the move the map fragment out of the SwipeRefreshLayout view because that would move the animation out of place.
Can someone point me on the right direction please?
Upvotes: 1
Views: 1118
Reputation: 402
I found the solution to this problem. Extended SwipeRefreshLayout and overrode onInterceptTouchEvent.
public class OverviewSwipeRefreshLayout extends SwipeRefreshLayout {
public OverviewSwipeRefreshLayout(Context context) {
super(context);
}
public OverviewSwipeRefreshLayout(Context context, AttributeSet attrs) {
super(context, attrs);
}
@Override
public boolean onInterceptTouchEvent(MotionEvent ev) {
final int action = ev.getAction();
switch (action) {
case MotionEvent.ACTION_DOWN:
super.onTouchEvent(ev);
break;
case MotionEvent.ACTION_MOVE:
return false;
case MotionEvent.ACTION_CANCEL:
super.onTouchEvent(ev);
break;
case MotionEvent.ACTION_UP:
return false;
default:
break;
}
return false;
}
@Override
public boolean onTouchEvent(MotionEvent ev) {
super.onTouchEvent(ev);
return true;
}
}
Upvotes: 0