Skip to content

Commit

Permalink
Version 1.4.0 (#18)
Browse files Browse the repository at this point in the history
* Fix inverted zoomed in ZoomableState

* Add features
- onTap Callback
- replace onDoubleTap with doubleTapBehaviour and add DoubleTapBehaviour SAM and DefaultDoubleTapBehaviour

* Bump version

* Version 1.4.0:
- Fix default dragGestureMode (was inverted)
- Call onTransformation when single Finger dragging
- Add DragGestureMode.default
- DragGestureMode.default and ZoomableState.DefaultDoubleTapBehaviour change on `transformed` instead of `zoomed`
  • Loading branch information
Mr-Pine authored Apr 17, 2023
1 parent b09cc45 commit 05175de
Show file tree
Hide file tree
Showing 8 changed files with 104 additions and 17 deletions.
32 changes: 32 additions & 0 deletions .idea/inspectionProfiles/Project_Default.xml

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

6 changes: 6 additions & 0 deletions .idea/kotlinc.xml

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

3 changes: 1 addition & 2 deletions .idea/misc.xml

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

2 changes: 1 addition & 1 deletion buildSrc/src/main/kotlin/artifact.kt
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
val artifact = Artifact(
group = "de.mr-pine.utils",
id = "zoomables",
version = "1.3.0"
version = "1.4.0"
)
Original file line number Diff line number Diff line change
Expand Up @@ -4,4 +4,9 @@ public enum class DragGestureMode {
DISABLED,
PAN,
SWIPE_GESTURES;

public companion object {
public val default: ZoomableState.() -> DragGestureMode =
{ if (transformed) PAN else SWIPE_GESTURES }
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -35,7 +35,7 @@ public fun ZoomableImage(
contentDescription: String? = null,
onSwipeLeft: () -> Unit = {},
onSwipeRight: () -> Unit = {},
dragGestureMode: ZoomableState.() -> DragGestureMode = { if (zoomed) DragGestureMode.SWIPE_GESTURES else DragGestureMode.PAN },
dragGestureMode: ZoomableState.() -> DragGestureMode = DragGestureMode.default,
onTap: ((Offset) -> Unit)? = null,
doubleTapBehaviour: DoubleTapBehaviour? = zoomableState.DefaultDoubleTapBehaviour(coroutineScope = coroutineScope)
) {
Expand Down Expand Up @@ -74,7 +74,7 @@ public fun ZoomableImage(
contentDescription: String? = null,
onSwipeLeft: () -> Unit = {},
onSwipeRight: () -> Unit = {},
dragGestureMode: ZoomableState.() -> DragGestureMode = { if (zoomed) DragGestureMode.SWIPE_GESTURES else DragGestureMode.PAN },
dragGestureMode: ZoomableState.() -> DragGestureMode = DragGestureMode.default,
onTap: ((Offset) -> Unit)? = null,
doubleTapBehaviour: DoubleTapBehaviour? = zoomableState.DefaultDoubleTapBehaviour(coroutineScope = coroutineScope)
) {
Expand Down Expand Up @@ -117,7 +117,7 @@ public fun ZoomableImage(
contentDescription: String? = null,
onSwipeLeft: () -> Unit = {},
onSwipeRight: () -> Unit = {},
dragGestureMode: ZoomableState.() -> DragGestureMode = { if (zoomed) DragGestureMode.SWIPE_GESTURES else DragGestureMode.PAN },
dragGestureMode: ZoomableState.() -> DragGestureMode = DragGestureMode.default,
onTap: ((Offset) -> Unit)? = null,
doubleTapBehaviour: DoubleTapBehaviour? = zoomableState.DefaultDoubleTapBehaviour(coroutineScope = coroutineScope)
) {
Expand Down
20 changes: 16 additions & 4 deletions zoomables/src/main/kotlin/de/mr_pine/zoomables/ZoomableState.kt
Original file line number Diff line number Diff line change
Expand Up @@ -2,15 +2,27 @@

package de.mr_pine.zoomables

import androidx.compose.animation.core.*
import androidx.compose.animation.core.AnimationSpec
import androidx.compose.animation.core.AnimationState
import androidx.compose.animation.core.Spring
import androidx.compose.animation.core.SpringSpec
import androidx.compose.animation.core.animateTo
import androidx.compose.foundation.MutatePriority
import androidx.compose.foundation.MutatorMutex
import androidx.compose.foundation.gestures.TransformScope
import androidx.compose.foundation.gestures.TransformableState
import androidx.compose.foundation.gestures.rememberTransformableState
import androidx.compose.runtime.*
import androidx.compose.runtime.Composable
import androidx.compose.runtime.MutableState
import androidx.compose.runtime.getValue
import androidx.compose.runtime.mutableStateOf
import androidx.compose.runtime.remember
import androidx.compose.runtime.rememberUpdatedState
import androidx.compose.runtime.setValue
import androidx.compose.ui.geometry.Offset
import de.mr_pine.zoomables.ZoomableState.Rotation.*
import de.mr_pine.zoomables.ZoomableState.Rotation.ALWAYS_ENABLED
import de.mr_pine.zoomables.ZoomableState.Rotation.DISABLED
import de.mr_pine.zoomables.ZoomableState.Rotation.LOCK_ROTATION_ON_ZOOM_PAN
import kotlinx.coroutines.CoroutineScope
import kotlinx.coroutines.coroutineScope
import kotlinx.coroutines.launch
Expand Down Expand Up @@ -174,7 +186,7 @@ public class ZoomableState(
private val coroutineScope: CoroutineScope
) : DoubleTapBehaviour {
override fun onDoubleTap(offset: Offset) {
if (scale.value != 1f) {
if (transformed) {
coroutineScope.launch {
animateBy(
zoomChange = 1 / scale.value,
Expand Down
47 changes: 40 additions & 7 deletions zoomables/src/main/kotlin/de/mr_pine/zoomables/Zoomables.kt
Original file line number Diff line number Diff line change
Expand Up @@ -2,25 +2,51 @@

package de.mr_pine.zoomables

import androidx.compose.foundation.gestures.*
import androidx.compose.foundation.gestures.awaitDragOrCancellation
import androidx.compose.foundation.gestures.awaitEachGesture
import androidx.compose.foundation.gestures.awaitTouchSlopOrCancellation
import androidx.compose.foundation.gestures.calculateCentroid
import androidx.compose.foundation.gestures.calculateCentroidSize
import androidx.compose.foundation.gestures.calculatePan
import androidx.compose.foundation.gestures.calculateRotation
import androidx.compose.foundation.gestures.calculateZoom
import androidx.compose.foundation.gestures.detectTapGestures
import androidx.compose.foundation.gestures.transformable
import androidx.compose.foundation.layout.Box
import androidx.compose.foundation.layout.BoxScope
import androidx.compose.foundation.layout.offset
import androidx.compose.runtime.*
import androidx.compose.runtime.Composable
import androidx.compose.runtime.getValue
import androidx.compose.runtime.mutableStateOf
import androidx.compose.runtime.remember
import androidx.compose.runtime.setValue
import androidx.compose.ui.Modifier
import androidx.compose.ui.draw.clip
import androidx.compose.ui.geometry.Offset
import androidx.compose.ui.graphics.RectangleShape
import androidx.compose.ui.graphics.graphicsLayer
import androidx.compose.ui.input.pointer.*
import androidx.compose.ui.input.pointer.AwaitPointerEventScope
import androidx.compose.ui.input.pointer.PointerId
import androidx.compose.ui.input.pointer.PointerInputChange
import androidx.compose.ui.input.pointer.changedToUp
import androidx.compose.ui.input.pointer.changedToUpIgnoreConsumed
import androidx.compose.ui.input.pointer.pointerInput
import androidx.compose.ui.input.pointer.positionChange
import androidx.compose.ui.input.pointer.positionChanged
import androidx.compose.ui.layout.onGloballyPositioned
import androidx.compose.ui.unit.IntOffset
import androidx.compose.ui.util.fastAny
import androidx.compose.ui.util.fastForEach
import kotlinx.coroutines.CoroutineScope
import kotlinx.coroutines.launch
import java.lang.Math.pow
import kotlin.math.*
import kotlin.math.PI
import kotlin.math.abs
import kotlin.math.atan
import kotlin.math.cos
import kotlin.math.roundToInt
import kotlin.math.sin
import kotlin.math.sqrt

/**
* Creates a composable that wraps a given [Composable] and adds zoom, pan, rotation, double tap and swipe functionality
Expand All @@ -46,7 +72,7 @@ import kotlin.math.*
public fun Zoomable(
coroutineScope: CoroutineScope,
zoomableState: ZoomableState,
dragGestureMode: ZoomableState.() -> DragGestureMode = { if (zoomed) DragGestureMode.SWIPE_GESTURES else DragGestureMode.PAN },
dragGestureMode: ZoomableState.() -> DragGestureMode = DragGestureMode.default,
onSwipeLeft: () -> Unit = {},
onSwipeRight: () -> Unit = {},
minimumSwipeDistance: Int = 0,
Expand Down Expand Up @@ -202,9 +228,10 @@ public fun Zoomable(
when (zoomableState.dragGestureMode()) {
DragGestureMode.PAN -> coroutineScope.launch {
zoomableState.transform {
transformBy(1f, overSlop, 0f)
transformBy(panChange = overSlop)
}
}

DragGestureMode.SWIPE_GESTURES -> dragOffset += overSlop
else -> {}
}
Expand All @@ -213,8 +240,14 @@ public fun Zoomable(
condition = { currentEvent.changes.size < 2 }) {
when (zoomableState.dragGestureMode()) {
DragGestureMode.PAN -> {
zoomableState.offset.value += it.positionChange()
val positionChange = it.positionChange()
coroutineScope.launch {
zoomableState.transform {
transformBy(panChange = positionChange)
}
}
}

DragGestureMode.SWIPE_GESTURES -> dragOffset += it.positionChange()
else -> {}
}
Expand Down

0 comments on commit 05175de

Please sign in to comment.