Skip to content

I created this repository with the intention of sharing useful Compose UI modifiers as I come up with them.

Notifications You must be signed in to change notification settings

HenokT/ReusableComposeModifiers

Repository files navigation

Reusable Compose Modifiers

I created this repository with the intention of sharing useful Compose UI modifiers as I come up with them.

Modifier.zoomable

The first one of many to come is the zoomable modifier that makes the modified element zoomable by capturing pinching and panning gestures. It also supports double-tap gesture for auto zooming in and out.

An obvious use case for this modifier is when you want to create a zoomable image viewer as follows:

@Composable
fun ZoomableImage(
    imageUri: String,
    modifier: Modifier = Modifier,
) {
    Box(modifier = Modifier) {
        AsyncImage(
            model = imageUri,
            placeholder = painterResource(R.drawable.placeholder),
            contentDescription = null,
            alignment = Alignment.Center,
            contentScale = ContentScale.Crop,
            modifier = modifier
                .fillMaxSize()
                .zoomable(
                    enabled = true,
                    minScale = 1f,
                    maxScale = 4f,
                    panningSpeedMultiplier = 2f,
                    doubleTapEnabled = true,
                    doubleTapScale = 3f,
                    animate = true,
                    scaleAnimationSpec = spring(
                        dampingRatio = Spring.DampingRatioLowBouncy,
                        stiffness = Spring.StiffnessLow
                    ),
                    panAnimationSpec = spring(
                        dampingRatio = Spring.DampingRatioLowBouncy,
                        stiffness = Spring.StiffnessVeryLow
                    ),
                    doubleTapScaleAnimationSpec = tween(durationMillis = 500),
                    doubleTapPanAnimationSpec = tween(durationMillis = 500),
                ),
            )
        Text(
            text = "Pinch to zoom, double-tap to zoom in/out, pan to explore zoomed image.",
            color = Color.LightGray,
            modifier = Modifier
                .align(Alignment.BottomCenter)
                .padding(16.dp)
        )
    }
}

Here is what it will look like:

zoomable-modifier-in-action

When your zoomable content is inside a container that has to detect touch gestures, like a HorizontalPager that relys on swipe gestures, you can apply the zoomable modifier to the container instead of the content. This way, the zoomable content will not interfere with the swipe gestures. Here is an example (you can see the full example here):

HorizontalPager(
    state = pagerState,
    modifier = modifier
        .fillMaxSize()
        .zoomable(),
) { page ->

    val image = images[page]
    AsyncImage(
        model = image,
        placeholder = painterResource(R.drawable.placeholder),
        contentDescription = null,
        alignment = Alignment.Center,
        contentScale = ContentScale.Crop,
        modifier = Modifier
            .fillMaxSize()
    )
}

And here is what it will look like:

zoomable-modifier-in-action

About

I created this repository with the intention of sharing useful Compose UI modifiers as I come up with them.

Topics

Resources

Stars

Watchers

Forks

Releases

No releases published

Packages

No packages published

Languages