Home > Net >  Unexpected behavior when trying to change progress bar value every second
Unexpected behavior when trying to change progress bar value every second

Time:11-15

I want to increment progress bar value every second, but every time I increment variable, value start incrementing faster then I defined.

Here is an example:

var progress by remember { mutableStateOf(0.00f) }
val animatedProgress by animateFloatAsState(
    targetValue = progress,
    animationSpec = ProgressIndicatorDefaults.ProgressAnimationSpec
)

val mainHandler = Handler(Looper.getMainLooper())
mainHandler.post(object : Runnable {
    override fun run() {
        progress  = 0.01f
        println(progress)
        mainHandler.postDelayed(this, 1000)
    }
})

LinearProgressIndicator(progress = animatedProgress)

I don't know what to do. I tried the same thing with normal float and it works.

var i = 0.00f
val mainHandler = Handler(Looper.getMainLooper())
mainHandler.post(object : Runnable {
    override fun run() {
        i  = 0.01f
        println(i)
        mainHandler.postDelayed(this, 1000)
    }
})

CodePudding user response:

You can use something like:

val state = remember { ProgressState() }

DisposableEffect(Unit) {
    state.start()
    onDispose {
        state.stop()
    }
}

CircularProgressIndicator(progress = state.progress)

with:

private class ProgressState {
    var progress by mutableStateOf(0f)

    fun start() {
        handler.postDelayed(updateProgress, 500)
    }

    fun stop() {
        handler.removeCallbacks(updateProgress)
    }

    val handler = Handler(Looper.getMainLooper())
    val updateProgress: Runnable = object : Runnable {
        override fun run() {
            if (progress < 1f) {
                progress  = 0.10f
            }
            handler.postDelayed(this, 1000)
        }
    }
}

enter image description here

CodePudding user response:

you already use jetpack-compose so use jetpack-compose power with LaunchedEffect to get CoroutineScope instead of Handler for your delay. Code example:

 var progress by remember { mutableStateOf(0.00f) }
    val animatedProgress by animateFloatAsState(
        targetValue = progress,
        animationSpec = ProgressIndicatorDefaults.ProgressAnimationSpec
    )

    LaunchedEffect(key1 = progress, block = {
        delay(1_000)
        if (progress < 1f) {
            progress  = 0.1f
        }
    })

    LinearProgressIndicator(
        modifier = Modifier.fillMaxWidth(),
        progress = animatedProgress
    )
  • Related