Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 4a4ac67e authored by Alp Yalcin's avatar Alp Yalcin Committed by Android (Google) Code Review
Browse files

Merge "[4/n] Create the new window from the relative touch point in users’ dragShadow" into main

parents c50e3c47 c3443f3e
Loading
Loading
Loading
Loading
+51 −0
Original line number Diff line number Diff line
@@ -38,6 +38,8 @@ import android.content.res.Configuration.ORIENTATION_PORTRAIT
import android.graphics.Rect
import android.os.SystemProperties
import android.util.Size
import android.view.DragEvent
import android.window.DesktopExperienceFlags
import android.window.DesktopModeFlags
import android.window.SplashScreen.SPLASH_SCREEN_STYLE_ICON
import com.android.internal.policy.DesktopModeCompatUtils
@@ -204,6 +206,41 @@ fun calculateMaximizeBounds(displayLayout: DisplayLayout, taskInfo: RunningTaskI
    }
}

/**
 * Position the new window based on the drag event.
 * It uses the drag shadow to maintain the relative position on the new window.
 * If shadow has anomaly, the new window is created from the top-center at the drop point.
 */
fun positionDragAndDropBounds(
    newBounds : Rect,
    dragEvent : DragEvent
) {
    val shadowSurface = dragEvent.dragSurface
    if (DesktopExperienceFlags.ENABLE_INTERACTION_DEPENDENT_TAB_TEARING_BOUNDS.isTrue() &&
        shadowSurface != null &&
        shadowSurface.isValid &&
        shadowSurface.width != 0) {
        // Calculate the horizontal offset to maintain the touch point's relative
        // position on the new window.
        val dropOffset = calculateDropPositionOffset(
            dragEvent.offsetX,
            shadowSurface.width,
            newBounds.width()
        )
        // Position the new window based on the drop point and its relative offset.
        newBounds.offsetTo(
            dragEvent.x.toInt() - dropOffset,
            dragEvent.y.toInt())

    } else {
        // Position the new window to the top-center at the drop point.
        newBounds.offsetTo(
            dragEvent.x.toInt() - (newBounds.width() / 2),
            dragEvent.y.toInt(),
        )
    }
}

/**
 * Calculates the largest size that can fit in a given area while maintaining a specific aspect
 * ratio.
@@ -479,6 +516,20 @@ fun createActivityOptionsForStartTask(
    return activityOptions
}

/**
 * Calculates the horizontal offset from the left edge of a new window to the user's touch point.
 * This preserves the same relative position of the touch point as it was on the dragShadow,
 * which allows a better positioning based on user's finger.
 */
private fun calculateDropPositionOffset(
    dragOffsetX: Float,
    shadowWidth: Int,
    windowWidth: Int
): Int {
    val touchPointHorizontalRatio = dragOffsetX / shadowWidth.toFloat()
    return (windowWidth * touchPointHorizontalRatio).toInt()
}

/**
 * Calculates the desired initial bounds for applications in desktop windowing. This is done as a
 * scale of the screen bounds.
+2 −5
Original line number Diff line number Diff line
@@ -5800,14 +5800,11 @@ class DesktopTasksController(
                ) {
                    // Inherit parent's bounds.
                    newWindowBounds.set(taskInfo.configuration.windowConfiguration.bounds)

                } else {
                    newWindowBounds.set(calculateDefaultDesktopTaskBounds(displayLayout))
                }
                // Create the new window from the top-center at the drop point.
                newWindowBounds.offsetTo(
                        dragEvent.x.toInt() - (newWindowBounds.width() / 2),
                        dragEvent.y.toInt(),
                    )
                positionDragAndDropBounds(newWindowBounds, dragEvent)
            }
            IndicatorType.TO_SPLIT_RIGHT_INDICATOR -> {
                newWindowBounds.set(getSnapBounds(destinationDisplay, SnapPosition.RIGHT))