Skip to content
Open
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -18,9 +18,14 @@
import android.animation.Animator;
import android.animation.AnimatorSet;
import android.animation.ValueAnimator;
import android.os.Build;
import androidx.annotation.NonNull;
import androidx.annotation.RequiresApi;
import androidx.annotation.RestrictTo;
import androidx.annotation.RestrictTo.Scope;

import java.util.ArrayList;
import java.util.Collection;
import java.util.List;

/**
Expand All @@ -33,17 +38,35 @@ public class AnimatorSetCompat {

/** Sets up this AnimatorSet to play all of the supplied animations at the same time. */
public static void playTogether(@NonNull AnimatorSet animatorSet, @NonNull List<Animator> items) {
// Fix for pre-M bug where animators with start delay are not played correctly in an
// AnimatorSet.
long totalDuration = 0;
for (int i = 0, count = items.size(); i < count; i++) {
Animator animator = items.get(i);
totalDuration = Math.max(totalDuration, animator.getStartDelay() + animator.getDuration());
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) {
Api23Impl.playTogether(animatorSet, items);
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think we can just inline the system call to be more accurate in semantics? (Like, it's not a "compat" impl.)

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

From a semantic standpoint, there is no significant difference between "for API ≥ 23, we invoke the platform implementation" and "for API ≥ 23, we invoke the implementation for API ≥ 23 (Api23Impl), which is the platform implementation". Even in the sample from the official guidelines, the platform method is called through an intermediate class.

But if you really want to, sure, you can edit my implementation and inline the platform call directly. Moreover, you can even remove all Api*Impl entirely and just use the platform call, like this:

@RestrictTo(Scope.LIBRARY_GROUP)
public class AnimatorSetCompat {

  public static void playTogether(@NonNull AnimatorSet animatorSet, @NonNull List<Animator> items) {
    animatorSet.playTogether(items);
  }
}

since the library no longer supports platforms prior to Marshmallow.

} else {
Api21Impl.playTogether(animatorSet, items);
}
Animator fix = ValueAnimator.ofInt(0, 0);
fix.setDuration(totalDuration);
items.add(0, fix);
}

animatorSet.playTogether(items);
@RequiresApi(Build.VERSION_CODES.M)
static class Api23Impl {
static void playTogether(@NonNull AnimatorSet animatorSet, @NonNull Collection<Animator> items) {
animatorSet.playTogether(items);
}
}

static class Api21Impl {
static void playTogether(@NonNull AnimatorSet animatorSet, @NonNull Collection<Animator> items) {
// Fix for pre-M bug where animators with start delay are not played correctly in an
// AnimatorSet.
long totalDuration = 0;
for (Animator animator : items) {
totalDuration = Math.max(totalDuration, animator.getStartDelay() + animator.getDuration());
}
Animator fix = ValueAnimator.ofInt(0, 0);
fix.setDuration(totalDuration);

List<Animator> animators = new ArrayList<>(items.size() + 1);
animators.add(fix);
animators.addAll(items);
animatorSet.playTogether(animators);
}
}
}