AnimatedVectorDrawableCompat цикл анимации с помощью обратного вызова
Я пытаюсь реализовать анимацию в своем приложении для Android, используя AnimatedVectorDrawableCompat, для совместимости для API >= 21.
Я хочу, чтобы анимация зациклилась на время действия. Я могу воспроизводить анимацию, и она также прекрасно зацикливается на API >= 25. Но когда я запускаю ее на устройствах или эмуляторах с API с 21 по 24, я вижу анимацию только один раз. Если я устанавливаю точку останова внутри метода обратного вызова, я вижу, что он также выполняет обратный вызов, но анимация не повторяется.
Я считаю, что анимация выполняется в другом потоке, так как она не блокирует пользовательский интерфейс.
Это метод:
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
imageView = findViewById(R.id.image_view1);
final AnimatedVectorDrawableCompat anim = AnimatedVectorDrawableCompat.create(this, R.drawable.avd_pass_inside);
imageView.setImageDrawable(anim);
anim.registerAnimationCallback(new Animatable2Compat.AnimationCallback() {
@Override
public void onAnimationEnd(Drawable drawable) {
anim.start();
}
});
anim.start();
}
Из того, что я прочитал, использование библиотеки Compat должно сделать эту работу для всех уровней API от 14 и выше, но мне даже не нужно идти туда, поскольку у остальной части моего приложения есть требования, которые ставят его как минимум на 21.
Есть ли какой-нибудь (желательно не хакерский:)) способ заставить эту работу согласованно работать на всех уровнях API? Это ошибка? Я что-то пропустил?
1 ответ
Насколько я вижу, это тонкая разница между системной и компатной версиями. Кажется, что Compat вызывает обратный вызов до того, как анимация была помечена как завершенная. Так что призыв к start()
игнорируется, потому что думает, что это еще не конец.
Решение обычного взлома: опубликовать Runnable
чтобы запустить его, когда анимация закончилась.
new Animatable2Compat.AnimationCallback() {
@NonNull
private final Handler fHandler = new Handler(Looper.getMainLooper());
@Override
public void onAnimationEnd(@NonNull Drawable drawable) {
Animatable2Compat avd = (Animatable2Compat) drawable;
fHandler.post(avd::start);
}
};