Jetpack Compose drawLine with stampedPathEffect

116 Views Asked by At

I try to draw a line with a ᐯ shape like this.

So I first created a Path with a ᐯ shape.

val lineWidth = 10.dp.toPx() * 5
val lineHeight = 5.dp.toPx() * 5

val arrowPath =
    Path().apply {
        moveTo(x = 0f, y = 0f)
        lineTo(x = lineWidth / 2f, y = lineHeight)
        lineTo(x = lineWidth, y = 0f)
    }

Then I put in a PathEffect.stampedPathEffect that uses the ᐯ-shaped Path as the pathEffect for drawLine using Canvas.

val strokeWidth = 1.dp.toPx() * 5
val arrowPathEffect =
    PathEffect.stampedPathEffect(
        shape = arrowPath,
        advance = 0f,
        phase = 0f,
        style = StampedPathEffectStyle.Translate,
    )

drawLine(
    color = Color.Black,
    start = Offset(x = size.center.x, y = 0f),
    end = Offset(x = size.center.x, y = size.height / 2),
    strokeWidth = strokeWidth,
    cap = StrokeCap.Round,
    pathEffect = arrowPathEffect,
)

However, the result was a plain line drawn with no stampedPathEffect applied. To validate the ᐯ-shaped Path I created, I drew it by itself using drawPath and it drew just as I expected.

What am I missing in the drawLine + PathEffect combination?

Full code:

Canvas(modifier = Modifier.fillMaxSize()) {
    val lineWidth = 10.dp.toPx() * 5
    val lineHeight = 5.dp.toPx() * 5
    val strokeWidth = 1.dp.toPx() * 5

    val arrowPath =
        Path().apply {
            moveTo(x = 0f, y = 0f)
            lineTo(x = lineWidth / 2f, y = lineHeight)
            lineTo(x = lineWidth, y = 0f)
        }
    val arrowPathEffect =
        PathEffect.stampedPathEffect(
            shape = arrowPath,
            advance = 0f,
            phase = 0f,
            style = StampedPathEffectStyle.Translate,
        )

    drawLine(
        color = Color.Black,
        start = Offset(x = size.center.x, y = 0f),
        end = Offset(x = size.center.x, y = size.height / 2),
        strokeWidth = strokeWidth,
        cap = StrokeCap.Round,
        pathEffect = arrowPathEffect,
    )

    translate(left = size.center.x, top = size.height * 0.8f) {
        drawPath(
            path = arrowPath,
            color = Color.Red,
            style = Stroke(width = strokeWidth),
        )
    }
}
0

There are 0 best solutions below