小智 8

1-将比例保存为状态

var scale by remember { mutableStateOf(1f) }
Run Code Online (Sandbox Code Playgroud)

2- 设置图像的比例以使用此状态。我建议使用 GraphicsLayer 设置比例,以最大限度地减少无效内容,并添加您想要的任何其他转换,如下所示

Image(
        ...,
        modifier = Modifier
            .graphicsLayer(
                scaleX = scale,
                scaleY = scale
            )
    )
Run Code Online (Sandbox Code Playgroud)

3- 用于Modifier.pointerInput检测并应用缩放效果。使用 PointerInputScope,您可以检测选项卡和转换(缩放、旋转和平移)。例如,您可以添加以下内容来检测缩放手势并相应地修改比例。

modifier = Modifier
            .pointerInput(Unit) {
                detectTransformGestures { _, _, zoom, _ ->
                    scale = when {
                        scale < 0.5f -> 0.5f
                        scale > 3f -> 3f
                        else -> scale * zoom
                    }
                }
            }
Run Code Online (Sandbox Code Playgroud)

的其他参数detectTransformGestures是质心、平移和旋转。您不需要它们来进行缩放转换,但如果您尝试应用旋转和平移,则需要它们。

如果您想使用平移手势应用缩放,您可以使用detectTapGestures。这是一个例子。

modifier = Modifier
            .pointerInput(Unit) {
                detectTapGestures(
                    onDoubleTap = {
                        scale = when {
                            scale > 2f -> 1f
                            else -> 3f
                        }
                    }
                )
            }
Run Code Online (Sandbox Code Playgroud)

这是使用 CoilImage 的完整示例。任何其他图像的实现应该相同

@Composable fun SamplePreview(imageUrl: String) {
var scale by remember { mutableStateOf(1f) }
Box {
    CoilImage(
        data = imageUrl,
        contentDescription = null,
        contentScale = ContentScale.FillWidth,
        modifier = Modifier
            .align(Alignment.Center)
            .graphicsLayer(
                scaleX = scale,
                scaleY = scale
            )
            .pointerInput(Unit) {
                detectTransformGestures { _, _, zoom, _ ->
                    scale = when {
                        scale < 0.5f -> 0.5f
                        scale > 3f -> 3f
                        else -> scale * zoom
                    }
                }
            }
    ) {
        CircularProgressIndicator()
    }
}
Run Code Online (Sandbox Code Playgroud)

  • 将 `.graphicsLayer` 与 lamdba 版本一起使用。它更新可组合项而不触发重组和重新布局。类似于:`.graphicsLayer{scaleX =scale; 比例 Y = 比例}` (2认同)