ObjectAnimator
есть свои странные моменты, но я наконец-то понял (по крайней мере, достаточно, чтобы решить мою собственную проблему).
Подвох в том, что в последовательности анимаций лучшевсегда указывать начальную и конечную позиции. В вопросе, который я написал, три ObjectAnimators
получили только конечную позицию. Это заставляет анимацию начинаться в странных местах.
Используя пример псевдокода, если вы хотите перейти от А к С, пройдя через В, вам нужно записать это так:
ObjectAnimator AtoB_X = ObjectAnimator.ofFloat(this.imageView, View.TRANSLATION_X, A.x, B.x - A.x);
ObjectAnimator BtoC_X = ObjectAnimator.ofFloat(this.imageView, View.TRANSLATION_X, B.x - A.x, C.x - A.x);
ObjectAnimator AtoB_Y = ObjectAnimator.ofFloat(this.imageView, View.TRANSLATION_Y, A.y, B.y - A.y);
ObjectAnimator BtoC_Y = ObjectAnimator.ofFloat(this.imageView, View.TRANSLATION_Y, B.y - A.y, C.y - A.y);
ВАЖНО: всегда используйте dp
измерения. Никогда не используйте px
измерения. Вот почему в моем коде я использую this.getResources().getDimensionPixelOffset()
. Он преобразует значение dp
в значение px
, соответствующее каждому разрешению экрана.
Теперь для моего рабочего кода:
private void vShapedAnimation() {
AnimatorSet upDownSet = new AnimatorSet();
AnimatorSet downUpSet = new AnimatorSet();
AnimatorSet finalSet = new AnimatorSet();
ObjectAnimator rightToHalf = ObjectAnimator.ofFloat(this.imageView, View.TRANSLATION_X, 0, this.getResources().getDimensionPixelOffset(R.dimen.translateLeft) / 2);
ObjectAnimator halfToLeft = ObjectAnimator.ofFloat(this.imageView, View.TRANSLATION_X, this.getResources().getDimensionPixelOffset(R.dimen.translateLeft) / 2, this.getResources().getDimensionPixelOffset(R.dimen.translateLeft));
ObjectAnimator upDown = ObjectAnimator.ofFloat(this.imageView, View.TRANSLATION_Y, 0, this.getResources().getDimensionPixelOffset(R.dimen.translateDown));
ObjectAnimator downUp = ObjectAnimator.ofFloat(this.imageView, View.TRANSLATION_Y, this.getResources().getDimensionPixelOffset(R.dimen.translateDown), 0);
upDownSet.playTogether(
rightToHalf,
upDown
);
downUpSet.playTogether(
halfToLeft,
downUp
);
finalSet.playSequentially(
upDownSet,
downUpSet
);
finalSet.setInterpolator(new LinearInterpolator());
finalSet.setDuration(300);
finalSet.start();
}