Андроидная анимация не завершена inAnimationEnd
Кажется, что анимация андроида действительно не закончена, когда событие onAnimationEnd
запущено, хотя для параметра animation.hasEnded
установлено значение true.
Я хочу, чтобы мое представление меняло его фоном на конец его ScaleAnimation
, который он делает, но вы можете ясно видеть, что он изменил некоторые миллисекунды, прежде чем он закончит. Проблема в том, что он мерцает, потому что новый фон появляется (= is) масштабируется в течение короткого времени, пока анимация не закончится.
Есть ли способ получить либо реальный конец анимации, либо просто предотвратить новый масштаб от этого короткого периода времени?
Спасибо!
//EDIT: я использую AnimationListener
, чтобы получить следующий вызов:
@Override
public void onAnimationEnd(Animation animation)
{
View view = (MyView) ((ExtendedScaleAnimation) animation).getView();
view.clearAnimation();
view.requestLayout();
view.refreshBackground(); // <-- this is where the background gets changed
}
Ответы
Ответ 1
Вот фактическая ошибка, связанная с этой проблемой http://code.google.com/p/android-misc-widgets/issues/detail?id=8
В основном это означает, что метод onAnimationEnd не работает хорошо, когда AnimationListener подключен к анимации
Обходной путь заключается в прослушивании событий анимации в представлении, к которому вы применяли анимацию, чтобы
Например, если изначально вы добавляли прослушиватель анимации к анимации, подобной этой
mAnimation.setAnimationListener(new AnimationListener() {
@Override
public void onAnimationEnd(Animation arg0) {
//Functionality here
}
});
а затем применительно к анимации к ImageView, подобному этому
mImageView.startAnimation(mAnimation);
Чтобы обойти эту проблему, вы должны теперь создать собственный ImageView
public class MyImageView extends ImageView {
а затем переопределить метод onAnimationEnd
класса View и предоставить все функции там
@Override
protected void onAnimationEnd() {
super.onAnimationEnd();
//Functionality here
}
Это правильное решение этой проблемы, обеспечивающее функциональность в методе over-riden View → onAnimationEnd, в отличие от метода onAnimationEnd AnimationListener, связанного с анимацией.
Это работает правильно, и в конце анимации больше не мерцает. Надеюсь, это поможет.
Ответ 2
Я решил устранить это, вызвав clearAnimation() в анимированном представлении внутри onAnimationEnd, что убрало мерцание
Странно, почему кто-то должен это делать, так как onAnimationEnd callback должен был быть вызван только в том случае, если анимация уже закончилась. Но я думаю, что ответ кроется в глубине Framework о том, как view/layout обрабатывает обратный вызов анимации.
Пока что считать это решением без взлома, это просто работает.
animation.setAnimationListener(new AnimationListener() {
public void onAnimationEnd(Animation anim) {
innerView.clearAnimation(); // to get rid of flicker at end of animation
RelativeLayout.LayoutParams lp = new RelativeLayout.LayoutParams
(innerBlockContainer.getWidth(), innerBlockContainer.getHeight());
/* Update lp margin, left/top to update layout after end of Translation */
ViewGroup parent_ofInnerView = (ViewGroup)innerView.getParent();
vp.updateViewLayout(innerBlockContainer, lp);
}
public void onAnimationRepeat(Animation arg0) {}
public void onAnimationStart(Animation arg0) {
}
});
innerView.startAnimation(animation);
Ответ 3
У меня была аналогичная проблема, и я использовал решение Soham с пользовательским классом вида.
Это сработало отлично, но в конце я нашел более простое решение, которое сработало для меня.
После вызова view.StartAnimation(animation)
и до следующего шага в моей программе, я добавил небольшую задержку, которая будет достаточно длинной, чтобы завершить анимацию, но достаточно короткой, чтобы пользователь был незаметным:
new Handler().postDelayed(new Runnable() {
@Override
public void run() {
nextStepInMyProgram();
}
}, 200);// delay in milliseconds (200)
Ответ 4
У меня была такая же проблема и она была решена с помощью
view.clearAnimation();
перед
view.startAnimation(anim);
Ответ 5
По какой-то причине onAnimationStart работает правильно, а onAnimationEnd не работает. Так вот как я изначально сделал это и что я изменил:
Попытка 1 (мерцание):
a) Перенести изображение с 0px на 80px
b) В onAnimationEnd задайте местоположение изображения 80px
Попытка 2 (без мерцания):
a) В onAnimationStart установите местоположение изображения на 80 пикселей
b) Переместите изображение с -80px на 0px
Надеюсь, что это имело смысл. В основном я перевернул то, как я это сделал.
Ответ 6
Попробуйте использовать getAnimation() из вашего объекта:
public void onShowListBtnClick(View view)
{
rightPanel.startAnimation(AnimationUtils.loadAnimation(MainActivity.this, R.anim.slide_left));
rightPanel.getAnimation().setAnimationListener(new Animation.AnimationListener() {
@Override
public void onAnimationStart(Animation animation) {
// TODO Auto-generated method stub
}
@Override
public void onAnimationRepeat(Animation animation) {
// TODO Auto-generated method stub
}
@Override
public void onAnimationEnd(Animation animation) {
// write your code here
}
});
}
Ответ 7
Легкое исправление заключается в добавлении одной строки в AnimationListener.onAnimationEnd()
:
@Override
public void onAnimationEnd(Animation a) {
a.setAnimationListener(null);
…
}
Ответ 8
annimation также может быть остановлена при вращении экрана. в этом случае onAnimationEnd() не вызывается. мой обход:
animation.setDuration(animationDuration);
animation.setAnimationListener(new AnimationListenerAdapter() {...});
view.startAnimation(animation);
handler.postDelayed(new Runnable() {
@Override
public void run() {
if(!animation.hasEnded()) {
// here you can handle this case
}
}
}, animationDuration + 100);
Ответ 9
У меня была эта проблема, потому что мой Animation
не был запущен в основном потоке.
Это привело к duration
0.
Тем не менее, Animation
сыграл правильно - он просто вызвал onAnimationEnd()
сразу после выполнения.
Ответ 10
Это сработало для меня:
@Override
public void onAnimationUpdate(ValueAnimator animation) {
if (Float.compare(animation.getAnimatedFraction(),1.0f)) {
// animation ended;
//do stuff post animation
}
}