Android Kotlin-动画后重置位置

Android Kotlin-动画后重置位置,android,kotlin,android-animation,Android,Kotlin,Android Animation,我正在制作一个滑动动画,这是onCreate内的: val distance = swipe.left.toFloat() anim = swipe.animate().rotationBy(-30f).setDuration(1000) // SWIPE TO LEFT .translationX(-distance) .setInterpolator(AccelerateDecelerateInterpolator()) anim!!.setListener(object

我正在制作一个滑动动画,这是onCreate内的:

val distance = swipe.left.toFloat()

anim = swipe.animate().rotationBy(-30f).setDuration(1000) // SWIPE TO LEFT
    .translationX(-distance)
    .setInterpolator(AccelerateDecelerateInterpolator())

anim!!.setListener(object : Animator.AnimatorListener {
    override fun onAnimationRepeat(animation: Animator?) {}
    override fun onAnimationCancel(animation: Animator?) {}
    override fun onAnimationStart(animation: Animator?) {}

    override fun onAnimationEnd(animation: Animator?) {
        swipe.animate().rotationBy(30f).setDuration(300)
            .translationX(distance)
            .setInterpolator(AccelerateDecelerateInterpolator()).start() // RESET THE POSITION BY SWIPING BACK TO RIGHT

        Log.d("pikaboo", "wth")
    }
})

anim!!.start()
如您所见,我尝试在NimationEnd中重置它,但随后我得到每秒打印多次的
wth
,滑动视图消失


这里怎么了?如何重置和重复动画?

当您在
视图上调用
动画
时,它将返回与该
视图
关联的
ViewPropertyAnimator
实例,即只有一个,每次调用
动画

该类不是由调用方构造的,而是由它将设置其属性动画的视图构造的。调用
View.animate()
将返回对该视图的相应ViewPropertyAnimator对象的引用

因此,您可以调用
animate
,并将
ViewPropertyAnimator
结果保存为
anim
,然后在此基础上设置动画侦听器。您的侦听器有其
onAnimationEnd
功能,该功能在同一视图上启动新动画,这意味着它使用相同的
ViewPropertyAnimator
anim
),该功能设置了侦听器,可在该动画结束时启动新动画。。。看到我要去哪里了吗?你有一个永无止境的循环

您最好的选择可能是使用单镜头结束动画,不管怎样,您都可以使用流畅的
动画
语法!不需要倾听者。试试这个:

anim = swipe.animate().rotationBy(-30f).setDuration(1000) // SWIPE TO LEFT
    .translationX(-distance)
    .setInterpolator(AccelerateDecelerateInterpolator())
    .withEndAction {
        swipe.animate().rotationBy(30f).setDuration(300)
            .translationX(distance)
        
       .setInterpolator(AccelerateDecelerateInterpolator()).start()
    }
无法修复那里的格式(对于一个关于编程的网站来说,在这些答案中使用代码真的很难),但是,是的,你可以通过将其中的一部分转换成函数来清理它(因为这是同一件事,只是负值)



另外,您可能应该将
anim
设置为
lateinit var
,而不是设置为null并执行
无论在哪里,这都是一个坏兆头,它最终总是会带来麻烦

当动画结束时,另一个动画开始,以便再次触发侦听器。尝试将其删除或将侦听器设置为null.lateint在这种情况下是一个坏主意,因为当活动在初始化动画之前关闭时,必要的动画将被删除!!。onFinish中的cancel()将导致崩溃。否则,您的解决方案有效,谢谢!如果(::anim.isInitialized)anim.cancel()
在这种情况下,您可以执行
,我只是尝试阻止人们使用
(特别是对于这样的东西,它基本上就是为
lateinit
创建的!)因为它总是会导致问题,而且它是一种处理使非null属性为null的后果的黑客,只是为了让你可以晚些初始化它,你知道吗?我用艰苦的方式学会了这一点:(
withEndAction
这是一个适用于许多用例的极好的解决方案,请记住。它非常棒!特别是如果你不想乱搞
动画集
的话。你唯一需要注意的是动画中断(就像因为用户再次点击而重新启动整个程序)