Skip to content

Commit

Permalink
Support Rtl in SplitPane (#4265)
Browse files Browse the repository at this point in the history
This is related to issue:
#4258

changes
- DesktopSplitPane.kt: placable.place() -> placable.placeRelative

- SplitePaneDSL.kt: change the delta direction to follow the layout
direction
```kotlin
 @composable
    override fun Modifier.markAsHandle(): Modifier = this.run {
        val layoutDirection = LocalLayoutDirection.current
        pointerInput(containerScope.splitPaneState) {
            detectDragGestures { change, _ ->
                change.consume()
                containerScope.splitPaneState.dispatchRawMovement(
                    if (containerScope.isHorizontal)
                        if (layoutDirection == LayoutDirection.Ltr) change.position.x else -change.position.x
                    else change.position.y
                )
            }
        }
```

the problem with .onPointerEvent() Modifier, or onDrag also,  is
    whenever the layout direction is Ltr or Rtl:
moving to right always produce positive change, [expected negative if
dir =Rtl]
moving to left always produce negative change, [expected positive if dir
=Rtl]

the calculation of postion will fail if layoutDir is Rtl, because
positionPercentage will be out of range
```kotlin
fun dispatchRawMovement(delta: Float) {
        val movableArea = maxPosition - minPosition
        if (movableArea > 0) {
            positionPercentage =
                ((movableArea * positionPercentage) + delta).coerceIn(0f, movableArea) / movableArea
        }
    }
```
  • Loading branch information
ahmedhosnypro committed Feb 8, 2024
1 parent 2b12d57 commit a8e9486
Show file tree
Hide file tree
Showing 3 changed files with 34 additions and 19 deletions.
Expand Up @@ -4,8 +4,11 @@ import androidx.compose.foundation.gestures.detectDragGestures
import androidx.compose.runtime.Composable
import androidx.compose.runtime.remember
import androidx.compose.ui.Modifier
import androidx.compose.ui.composed
import androidx.compose.ui.input.pointer.pointerInput
import androidx.compose.ui.platform.LocalLayoutDirection
import androidx.compose.ui.unit.Dp
import androidx.compose.ui.unit.LayoutDirection
import androidx.compose.ui.unit.dp

/** Receiver scope which is used by [HorizontalSplitPane] and [VerticalSplitPane] */
Expand Down Expand Up @@ -83,12 +86,17 @@ interface SplitterScope {
internal class HandleScopeImpl(
private val containerScope: SplitPaneScopeImpl
) : HandleScope {
override fun Modifier.markAsHandle(): Modifier = this.pointerInput(containerScope.splitPaneState) {
detectDragGestures { change, _ ->
change.consume()
containerScope.splitPaneState.dispatchRawMovement(
if (containerScope.isHorizontal) change.position.x else change.position.y
)
override fun Modifier.markAsHandle(): Modifier = composed {
val layoutDirection = LocalLayoutDirection.current
pointerInput(containerScope.splitPaneState) {
detectDragGestures { change, _ ->
change.consume()
containerScope.splitPaneState.dispatchRawMovement(
if (containerScope.isHorizontal)
if (layoutDirection == LayoutDirection.Ltr) change.position.x else -change.position.x
else change.position.y
)
}
}
}
}
Expand Down
Expand Up @@ -121,18 +121,18 @@ internal actual fun SplitPane(
}

layout(constraints.maxWidth, constraints.maxHeight) {
firstPlaceable.place(0, 0)
firstPlaceable.placeRelative(0, 0)
if (isHorizontal) {
secondPlaceable.place(secondPlaceablePosition, 0)
splitterPlaceable.place(position, 0)
secondPlaceable.placeRelative(secondPlaceablePosition, 0)
splitterPlaceable.placeRelative(position, 0)
if (moveEnabled) {
handlePlaceable.place(handlePosition, 0)
handlePlaceable.placeRelative(handlePosition, 0)
}
} else {
secondPlaceable.place(0, secondPlaceablePosition)
splitterPlaceable.place(0, position)
secondPlaceable.placeRelative(0, secondPlaceablePosition)
splitterPlaceable.placeRelative(0, position)
if (moveEnabled) {
handlePlaceable.place(0, handlePosition)
handlePlaceable.placeRelative(0, handlePosition)
}
}
}
Expand Down
Expand Up @@ -6,6 +6,8 @@ import androidx.compose.runtime.Composable
import androidx.compose.ui.ExperimentalComposeUiApi
import androidx.compose.ui.Modifier
import androidx.compose.ui.input.pointer.*
import androidx.compose.ui.platform.LocalLayoutDirection
import androidx.compose.ui.unit.LayoutDirection
import androidx.compose.ui.unit.dp
import java.awt.Cursor

Expand All @@ -20,12 +22,17 @@ private fun DesktopHandle(
splitPaneState: SplitPaneState
) = Box(
Modifier
.pointerInput(splitPaneState) {
detectDragGestures { change, _ ->
change.consumeAllChanges()
splitPaneState.dispatchRawMovement(
if (isHorizontal) change.position.x else change.position.y
)
.run {
val layoutDirection = LocalLayoutDirection.current
pointerInput(splitPaneState) {
detectDragGestures { change, _ ->
change.consume()
splitPaneState.dispatchRawMovement(
if (isHorizontal)
if (layoutDirection == LayoutDirection.Ltr) change.position.x else -change.position.x
else change.position.y
)
}
}
}
.cursorForHorizontalResize(isHorizontal)
Expand Down

0 comments on commit a8e9486

Please sign in to comment.