Problem with using coroutine to animate a view

I have a game that show a mouse running around the screen.
I am using a coroutine to launch a looping routine that either stops the animation or starts it with a new image set.
The problem is that I get an error when trying to start the animation which states its not a looping thread.
code snippet here:
run = true
startAnim = true
CoroutoneScope(Dispatchers.Default).launch{ loopAnim() }
private fun loopAnim(){
while(run) {
if (stopAnim) {
println(“loopAnim: stopAnim”)
if (mouseAnim != null)
if (mouseAnim.isRunning) mouseAnim.stop()
mouse.clearAnimation()
mouse.visibility = View.INVISIBLE
startAnim = false
animRunning = false
println(“loopAnim: anim stopped”)
stopAnim = false
}
if (startAnim) {
startAnim = false;
println(“loopAnim: startAnim id=” + animID)
if (mouseAnim.isRunning) mouseAnim.stop()
mouse.setBackgroundResource(animID)
mouseAnim = mouse.background as AnimationDrawable
mouse.animate().scaleX(myMouseScale.x)
mouse.animate().scaleY(myMouseScale.y)
mouse.animate().duration = 1000
mouse.animate().withEndAction(::loopAnim)
mouseAnim.start()
mouse.animate().start() // this line errors
animRunning = true
println(“loopAnim: anim running”)
}
Thread.sleep(10)
}
}

You’re running your code on a background thread. Animations need to run on the main thread. Try using Dispatchers.Main.

I tried that but it holds up the main thread so decided i needed a separate thread and am now using

CoroutineScope(newSingleThreadContext("loopAnim")).launch{loopAnim()}

I am still getting the problem with the line identified in my original post.

Use Dispatchers.Main and replace Thread.sleep with delay. You will also need to mark loopAnim as a suspend function.

1 Like

Used those but now I have a problem with the line
mouse.animate().withEndAction(::loopAnim)
I believe I need this so the animation loops infinitely.

Please make sure your code is properly formatted, because otherwise it is very hard to read it. If you call the same operation at the end, then I guess you need to again launch the function to get into the coroutine context.

1 Like

I commented out the line withEndAction and changed the duration to 0 and it all works ok now.
.