Чтобы избежать повторяющегося кода, вы можете создать подкласс AnimatorListenerAdapter и создать свой собственный класс AnimatorListener, в который вы повторно присоединяете представление после анимации, а затем используете его везде, где это необходимо, вместо AnimatorListener по умолчанию.
Класс:
import android.animation.Animator;
import android.animation.AnimatorListenerAdapter;
import android.view.View;
import android.view.ViewGroup;
import android.widget.FrameLayout;
import android.widget.RelativeLayout;
public class PersistViewAnimatorListener extends AnimatorListenerAdapter {
private View view; // keep a reference to the view
public PersistViewAnimatorListener(View view) {
this.view = view;
}
@Override public void onAnimationEnd(Animator animation) {
super.onAnimationEnd(animation);
// re-attach the view to its parent at its new location
if (view == null) { return; } // defensive, the view may have been removed while it was animated, do nothing in this case
ViewGroup parent = (ViewGroup) view.getParent(); // get the parent
if (parent == null) { return; } // defensive
int index = parent.indexOfChild(view); // get the index of the view
parent.removeView(view); // remove the view
if (parent.getClass().equals(RelativeLayout.class)) { // RELATIVE LAYOUT
RelativeLayout.LayoutParams layoutParams = new RelativeLayout.LayoutParams(view.getLayoutParams()); // add the view back at its index with new layout parameters
layoutParams.setMargins(Math.round(view.getX()), Math.round(view.getY()), 0, 0); // left, top, right, bottom; round the float to int
parent.addView(view, index, layoutParams);
} else if (parent.getClass().equals(FrameLayout.class)) { // FRAME LAYOUT
FrameLayout.LayoutParams layoutParams = new FrameLayout.LayoutParams(view.getLayoutParams()); // the same for FrameLayout
layoutParams.setMargins(Math.round(view.getX()), Math.round(view.getY()), 0, 0);
parent.addView(view, index, layoutParams);
} else { // currently no further layouts supported, implement these here
throw new UnsupportedOperationException("PersistViewAnimatorListener is currently only supported where the parent is either RelativeLayout or FrameLayout.");
}
view.setTranslationX(0); view.setTranslationY(0); // reset translated values from the animation
}
}
И как вы его используете:
view.animate().yBy(height).setListener(new PersistViewAnimatorListener(view)); // call your custom listener in .setListener() and pass in the view
В этом решении предполагается, что вы используете RelativeLayout или FrameLayout для родителя.Кроме того, он просто заботится о позиции, а не о размере или других свойствах, которые также можно анимировать.