KiteAnimatedImage

fun KiteAnimatedImage(animation: KiteAnimation, contentDescription: String?, modifier: Modifier = Modifier, alignment: Alignment = Alignment.Center, contentScale: ContentScale = ContentScale.Fit, alpha: Float = DefaultAlpha, colorFilter: ColorFilter? = null, filterQuality: FilterQuality = DrawScope.DefaultFilterQuality, animate: Boolean = true)

Play an already-decoded KiteAnimation: the one frame loop shared by KiteImage's byte-array overload and kiteimage-coil's KiteAsyncImage. Public because callers running their own decode pipeline deserve playback too, exactly like the KiteImage overload that takes a KiteBitmap.

The frame to show is derived from elapsed frame-clock time against the animation's cumulative delays (not chained delay() calls), so scheduling latency never accumulates: playback can't drift slow over long loops, and a janky UI skips frames like every browser does instead of slowing the GIF down. Honors per-frame delays, the NETSCAPE loop count (0 = forever), and holds the last frame once a finite loop completes.

Frames convert to ImageBitmap lazily, once each, cached per animation instance. Static (single-frame) animations just draw. animate pins the first frame when false (thumbnails, previews).