SwipeListView only one item opened at a time
android, ontouchlistener, swipe, swipe-gesture
Solution
Cons: doesn't close the row opened by `openAnimate()`
BaseSwipeListViewListener swipeListViewListener = new BaseSwipeListViewListener() {
int openItem = -1;
@Override
public void onStartOpen(int position, int action, boolean right) {
super.onStartOpen(position, action, right);
if (openItem > -1)
swipeListView.closeAnimate(openItem);
openItem = position;
}
}
Or better way:
@Override
public void onStartOpen(int position, int action, boolean right) {
super.onStartOpen(position, action, right);
swipeListView.closeOpenedItems();
}
And set the listener to the listView:
swipeListView.setSwipeListViewListener(swipeListViewListener);
Problem
This question refers to the SwipeListView component found here: https://github.com/47deg/android-swipelistview After trying out several implementations and fixes I found on the web I decided to modify the sources a little. I will post this here since i know it's a known issue and all the versions I found proved to have some issues eventually. `SwipeListViewTouchListener.java` has suffered the following changes: ``` ... /** * Create reveal animation * * @param view affected view * @param swap If will change state. If "false" returns to the original * position * @param swapRight If swap is true, this parameter tells if movement is toward * right or left * @param position list position */ private void generateRevealAnimate(final View view, final boolean swap, final boolean swapRight, final int position) { int moveTo = 0; if (opened.get(position)) { if (!swap) { moveTo = openedRight.get(position) ? (int) (viewWidth - rightOffset) : (int) (-viewWidth + leftOffset); } } else { if (swap) { moveTo = swapRight ? (int) (viewWidth - rightOffset) : (int) (-viewWidth + leftOffset); } } final boolean aux = !opened.get(position); if(swap) { opened.set(position, aux); openedRight.set(position, swapRight); } animate(view).translationX(moveTo).setDuration(animationTime).setListener(new AnimatorListenerAdapter() { @Override public void onAnimationEnd(Animator animation) { swipeListView.resetScrolling(); if (swap) { if (aux) { swipeListView.onOpened(position, swapRight); } else { swipeListView.onClosed(position, openedRight.get(position)); } } // if (aux || !swap) { // resetCell(); // } } }); } ... /** * Close all opened items */ void closeOtherOpenedItems() { if (opened != null && downPosition != SwipeListView.INVALID_POSITION) { int start = swipeListView.getFirstVisiblePosition(); int end = swipeListView.getLastVisiblePosition(); for (int i = start; i <= end; i++) { if (opened.get(i) && i != downPosition) { closeAnimate(swipeListView.getChildAt(i - start).findViewById(swipeFrontView), i); } } } } ... /** * @see View.OnTouchListener#onTouch(android.view.View, * android.view.MotionEvent) */ @Override public boolean onTouch(View view, MotionEvent motionEvent) { ... closeOtherOpenedItems(); view.onTouchEvent(motionEvent); return true; } ``` The rest of the code not mentioned is the same. Any comments highly appreciated, this changes prevent you from having to implement the `SwipeListViewOnTouchListener` in the activity which inflates the list.