Charts
Chartsanimated

ECG monitor

A live heart-rate monitor whose ECG trace scrolls continuously across the grid.

Installation

caveui components are copy-paste Jetpack Compose built entirely on Material 3 — there's no caveui dependency to add. Make sure Material 3 is on your classpath (it ships with the Compose BOM), then copy the Usage snippet below into your project.

kotlin
// build.gradle.kts (module)
dependencies {
    implementation(platform("androidx.compose:compose-bom:2025.06.00"))
    implementation("androidx.compose.material3:material3")
}

Usage

kotlin
@Composable
fun EcgMonitor(
    accent: Color = Color(0xFF22C55E),
    modifier: Modifier = Modifier,
) {
    val t = rememberInfiniteTransition(label = "ecg")
    val shift by t.animateFloat(
        0f, 1f, infiniteRepeatable(tween(1800, easing = LinearEasing)), label = "s",
    )
    Canvas(modifier.fillMaxWidth().height(110.dp)) {
        val w = size.width
        val midY = size.height / 2
        fun beat(x0: Float) = Path().apply {
            moveTo(x0, midY)
            lineTo(x0 + w * 0.14f, midY)
            lineTo(x0 + w * 0.18f, midY - size.height * 0.08f)
            lineTo(x0 + w * 0.22f, midY + size.height * 0.34f)
            lineTo(x0 + w * 0.26f, midY - size.height * 0.46f)
            lineTo(x0 + w * 0.3f, midY + size.height * 0.12f)
            lineTo(x0 + w * 0.36f, midY)
            lineTo(x0 + w * 0.5f, midY)
        }
        val style = Stroke(2.5.dp.toPx(), cap = StrokeCap.Round, join = StrokeJoin.Round)
        translate(left = -shift * w * 0.5f) {
            listOf(0f, 0.5f, 1f).forEach { f -> drawPath(beat(w * f), accent, style = style) }
        }
    }
}