Understanding RepeatableSpec and InfiniteRepeatableSpec in Jetpack Compose Animations
This article explains the RepeatableSpec and InfiniteRepeatableSpec animation specifications in Jetpack Compose, detailing their constructors, parameters such as iterations, repeatMode, and initialStartOffset, and demonstrates practical Kotlin code examples for creating repeatable and endless animations.
This article continues the Compose animation series by introducing the last two animation specifications: RepeatableSpec (repeatable animation) and InfiniteRepeatableSpec (endless repeat).
RepeatableSpec is defined as:
class RepeatableSpec
(
val iterations: Int,
val animation: DurationBasedAnimationSpec
,
val repeatMode: RepeatMode = RepeatMode.Restart,
val initialStartOffset: StartOffset = StartOffset(0)
) : FiniteAnimationSpecThe four constructor parameters are:
iterations : number of times the animation repeats (required).
animation : the target animation spec to repeat (required).
repeatMode : either Restart (play from start) or Reverse (play backwards), default is Restart .
initialStartOffset : an optional offset for the whole animation, default StartOffset(0) .
Compose also provides a convenience function repeatable with the same parameters, allowing developers to create a RepeatableSpec more succinctly.
Example of using the iterations parameter:
val repeatableSpec = repeatable<Dp>(iterations = 5, animation = ...)The animation argument must be a DurationBasedAnimationSpec , which currently has three concrete implementations: TweenSpec , SnapSpec , and KeyframesSpec . SpringSpec cannot be used with RepeatableSpec .
repeatMode is an enum defined as:
enum class RepeatMode {
// Restart from the beginning
Restart,
// Play the animation in reverse
Reverse
}Using repeatMode = RepeatMode.Restart causes the animation to jump back to the start after each iteration, while Reverse plays the animation backwards, giving a smoother visual experience. When Reverse is used with an even number of repetitions, the final frame may snap back to the end, which developers should be aware of.
initialStartOffset allows an offset for the whole animation timeline. It is created with StartOffset(offsetMillis, offsetType) , where offsetType can be:
Delay : wait offsetMillis before starting the animation (default).
FastForward : skip the first offsetMillis of the animation.
For example:
val spec = repeatable(3, animation, repeatMode = RepeatMode.Reverse, initialStartOffset = StartOffset(300, StartOffsetType.Delay))
val spec2 = repeatable(3, animation, repeatMode = RepeatMode.Reverse, initialStartOffset = StartOffset(300, StartOffsetType.FastForward))With Delay , the whole animation starts 300 ms later (total duration = 300 ms + 3 × animationDuration). With FastForward , the first 300 ms are skipped, reducing the total duration.
InfiniteRepeatableSpec provides an endless repeat animation. It has the same parameters as RepeatableSpec except for the missing iterations argument.
The convenience function infiniteRepeatable is used as follows:
val spec = infiniteRepeatable(animation, repeatMode = RepeatMode.Reverse, initialStartOffset = StartOffset(300, StartOffsetType.Delay))To stop an infinite animation, switch the animation spec based on a state variable:
// Animation state
var moveToRight by remember { mutableStateOf(false) }
val targetValue = if (moveToRight) 200.dp else 10.dp
// Infinite repeat spec
val infiniteRepeatableSpec = infiniteRepeatable<Dp>(
tween(),
repeatMode = RepeatMode.Reverse,
initialStartOffset = StartOffset(300, StartOffsetType.Delay)
)
// Choose spec according to state
val animationSpec = if (moveToRight) infiniteRepeatableSpec else snap()
val startPadding by animateDpAsState(targetValue, animationSpec = animationSpec)
Column {
Box(
Modifier
.padding(start = startPadding, top = 20.dp, bottom = 10.dp)
.size(100.dp)
.background(Color.Blue)
)
Button(onClick = { moveToRight = !moveToRight }) {
Text(if (moveToRight) "Stop" else "Start")
}
}The article concludes that both RepeatableSpec and InfiniteRepeatableSpec have been fully demonstrated, completing the series on the six Compose animation specifications.
Rare Earth Juejin Tech Community
Juejin, a tech community that helps developers grow.
How this landed with the community
Was this worth your time?
0 Comments
Thoughtful readers leave field notes, pushback, and hard-won operational detail here.