diff --git a/libs/WindowManager/Shell/src/com/android/wm/shell/desktopmode/DesktopTasksController.kt b/libs/WindowManager/Shell/src/com/android/wm/shell/desktopmode/DesktopTasksController.kt
index 609ac0a..d966aaa 100644
--- a/libs/WindowManager/Shell/src/com/android/wm/shell/desktopmode/DesktopTasksController.kt
+++ b/libs/WindowManager/Shell/src/com/android/wm/shell/desktopmode/DesktopTasksController.kt
@@ -863,7 +863,11 @@
         }
 
         val wct = WindowContainerTransaction()
-        if (!task.isFreeform) addMoveToDesktopChanges(wct, task, displayId)
+        if (!task.isFreeform) {
+            addMoveToDesktopChanges(wct, task, displayId)
+        } else if (Flags.enableMoveToNextDisplayShortcut()) {
+            applyFreeformDisplayChange(wct, task, displayId)
+        }
         wct.reparent(task.token, displayAreaInfo.token, true /* onTop */)
 
         if (Flags.enablePerDisplayDesktopWallpaperActivity()) {
@@ -1909,6 +1913,50 @@
         }
     }
 
+    /**
+     * Apply changes to move a freeform task from one display to another, which includes handling
+     * density changes between displays.
+     */
+    private fun applyFreeformDisplayChange(
+        wct: WindowContainerTransaction,
+        taskInfo: RunningTaskInfo,
+        destDisplayId: Int,
+    ) {
+        val sourceLayout = displayController.getDisplayLayout(taskInfo.displayId) ?: return
+        val destLayout = displayController.getDisplayLayout(destDisplayId) ?: return
+        val bounds = taskInfo.configuration.windowConfiguration.bounds
+        val scaledWidth = bounds.width() * destLayout.densityDpi() / sourceLayout.densityDpi()
+        val scaledHeight = bounds.height() * destLayout.densityDpi() / sourceLayout.densityDpi()
+        val sourceWidthMargin = sourceLayout.width() - bounds.width()
+        val sourceHeightMargin = sourceLayout.height() - bounds.height()
+        val destWidthMargin = destLayout.width() - scaledWidth
+        val destHeightMargin = destLayout.height() - scaledHeight
+        val scaledLeft =
+            if (sourceWidthMargin != 0) {
+                bounds.left * destWidthMargin / sourceWidthMargin
+            } else {
+                destWidthMargin / 2
+            }
+        val scaledTop =
+            if (sourceHeightMargin != 0) {
+                bounds.top * destHeightMargin / sourceHeightMargin
+            } else {
+                destHeightMargin / 2
+            }
+        val boundsWithinDisplay =
+            if (destWidthMargin >= 0 && destHeightMargin >= 0) {
+                Rect(0, 0, scaledWidth, scaledHeight).apply {
+                    offsetTo(
+                        scaledLeft.coerceIn(0, destWidthMargin),
+                        scaledTop.coerceIn(0, destHeightMargin),
+                    )
+                }
+            } else {
+                getInitialBounds(destLayout, taskInfo, destDisplayId)
+            }
+        wct.setBounds(taskInfo.token, boundsWithinDisplay)
+    }
+
     private fun getInitialBounds(
         displayLayout: DisplayLayout,
         taskInfo: RunningTaskInfo,
diff --git a/libs/WindowManager/Shell/tests/unittest/src/com/android/wm/shell/desktopmode/DesktopTasksControllerTest.kt b/libs/WindowManager/Shell/tests/unittest/src/com/android/wm/shell/desktopmode/DesktopTasksControllerTest.kt
index 0eb88e3..0283c02 100644
--- a/libs/WindowManager/Shell/tests/unittest/src/com/android/wm/shell/desktopmode/DesktopTasksControllerTest.kt
+++ b/libs/WindowManager/Shell/tests/unittest/src/com/android/wm/shell/desktopmode/DesktopTasksControllerTest.kt
@@ -83,6 +83,7 @@
 import com.android.window.flags.Flags
 import com.android.window.flags.Flags.FLAG_ENABLE_DESKTOP_WINDOWING_MODE
 import com.android.window.flags.Flags.FLAG_ENABLE_FULLY_IMMERSIVE_IN_DESKTOP
+import com.android.window.flags.Flags.FLAG_ENABLE_MOVE_TO_NEXT_DISPLAY_SHORTCUT
 import com.android.window.flags.Flags.FLAG_ENABLE_PER_DISPLAY_DESKTOP_WALLPAPER_ACTIVITY
 import com.android.wm.shell.MockToken
 import com.android.wm.shell.R
@@ -297,6 +298,7 @@
         whenever(displayLayout.getStableBounds(any())).thenAnswer { i ->
             (i.arguments.first() as Rect).set(STABLE_BOUNDS)
         }
+        whenever(displayLayout.densityDpi()).thenReturn(160)
         whenever(runBlocking { persistentRepository.readDesktop(any(), any()) })
             .thenReturn(Desktop.getDefaultInstance())
         doReturn(mockToast).`when` { Toast.makeText(any(), anyInt(), anyInt()) }
@@ -1746,6 +1748,154 @@
     }
 
     @Test
+    @EnableFlags(FLAG_ENABLE_MOVE_TO_NEXT_DISPLAY_SHORTCUT)
+    fun moveToNextDisplay_sizeInDpPreserved() {
+        // Set up two display ids
+        whenever(rootTaskDisplayAreaOrganizer.displayIds)
+            .thenReturn(intArrayOf(DEFAULT_DISPLAY, SECOND_DISPLAY))
+        // Create a mock for the target display area: second display
+        val secondDisplayArea = DisplayAreaInfo(MockToken().token(), SECOND_DISPLAY, 0)
+        whenever(rootTaskDisplayAreaOrganizer.getDisplayAreaInfo(SECOND_DISPLAY))
+            .thenReturn(secondDisplayArea)
+        // Two displays have different density
+        whenever(displayLayout.densityDpi()).thenReturn(320)
+        whenever(displayLayout.width()).thenReturn(2400)
+        whenever(displayLayout.height()).thenReturn(1600)
+        val secondaryLayout = mock(DisplayLayout::class.java)
+        whenever(displayController.getDisplayLayout(SECOND_DISPLAY)).thenReturn(secondaryLayout)
+        whenever(secondaryLayout.densityDpi()).thenReturn(160)
+        whenever(secondaryLayout.width()).thenReturn(1280)
+        whenever(secondaryLayout.height()).thenReturn(720)
+
+        // Place a task with a size of 640x480 at a position where the ratio of the left margin to
+        // the right margin is 1:3 and the ratio of top margin to the bottom margin is 1:2.
+        val task =
+            setUpFreeformTask(displayId = DEFAULT_DISPLAY, bounds = Rect(440, 374, 1080, 854))
+
+        controller.moveToNextDisplay(task.taskId)
+
+        with(getLatestWct(type = TRANSIT_CHANGE)) {
+            val taskChange = changes[task.token.asBinder()]
+            assertThat(taskChange).isNotNull()
+            // To preserve DP size, pixel size is changed to 320x240. The ratio of the left margin
+            // to the right margin and the ratio of the top margin to bottom margin are also
+            // preserved.
+            assertThat(taskChange!!.configuration.windowConfiguration.bounds)
+                .isEqualTo(Rect(240, 160, 560, 400))
+        }
+    }
+
+    @Test
+    @EnableFlags(FLAG_ENABLE_MOVE_TO_NEXT_DISPLAY_SHORTCUT)
+    fun moveToNextDisplay_shiftWithinDestinationDisplayBounds() {
+        // Set up two display ids
+        whenever(rootTaskDisplayAreaOrganizer.displayIds)
+            .thenReturn(intArrayOf(DEFAULT_DISPLAY, SECOND_DISPLAY))
+        // Create a mock for the target display area: second display
+        val secondDisplayArea = DisplayAreaInfo(MockToken().token(), SECOND_DISPLAY, 0)
+        whenever(rootTaskDisplayAreaOrganizer.getDisplayAreaInfo(SECOND_DISPLAY))
+            .thenReturn(secondDisplayArea)
+        // Two displays have different density
+        whenever(displayLayout.densityDpi()).thenReturn(320)
+        whenever(displayLayout.width()).thenReturn(2400)
+        whenever(displayLayout.height()).thenReturn(1600)
+        val secondaryLayout = mock(DisplayLayout::class.java)
+        whenever(displayController.getDisplayLayout(SECOND_DISPLAY)).thenReturn(secondaryLayout)
+        whenever(secondaryLayout.densityDpi()).thenReturn(160)
+        whenever(secondaryLayout.width()).thenReturn(1280)
+        whenever(secondaryLayout.height()).thenReturn(720)
+
+        // Place a task with a size of 640x480 at a position where the bottom-right corner of the
+        // window is outside the source display bounds. The destination display still has enough
+        // space to place the window within its bounds.
+        val task =
+            setUpFreeformTask(displayId = DEFAULT_DISPLAY, bounds = Rect(2000, 1200, 2640, 1680))
+
+        controller.moveToNextDisplay(task.taskId)
+
+        with(getLatestWct(type = TRANSIT_CHANGE)) {
+            val taskChange = changes[task.token.asBinder()]
+            assertThat(taskChange).isNotNull()
+            assertThat(taskChange!!.configuration.windowConfiguration.bounds)
+                .isEqualTo(Rect(960, 480, 1280, 720))
+        }
+    }
+
+    @Test
+    @EnableFlags(FLAG_ENABLE_MOVE_TO_NEXT_DISPLAY_SHORTCUT)
+    fun moveToNextDisplay_maximizedTask() {
+        // Set up two display ids
+        whenever(rootTaskDisplayAreaOrganizer.displayIds)
+            .thenReturn(intArrayOf(DEFAULT_DISPLAY, SECOND_DISPLAY))
+        // Create a mock for the target display area: second display
+        val secondDisplayArea = DisplayAreaInfo(MockToken().token(), SECOND_DISPLAY, 0)
+        whenever(rootTaskDisplayAreaOrganizer.getDisplayAreaInfo(SECOND_DISPLAY))
+            .thenReturn(secondDisplayArea)
+        // Two displays have different density
+        whenever(displayLayout.densityDpi()).thenReturn(320)
+        whenever(displayLayout.width()).thenReturn(1280)
+        whenever(displayLayout.height()).thenReturn(960)
+        val secondaryLayout = mock(DisplayLayout::class.java)
+        whenever(displayController.getDisplayLayout(SECOND_DISPLAY)).thenReturn(secondaryLayout)
+        whenever(secondaryLayout.densityDpi()).thenReturn(160)
+        whenever(secondaryLayout.width()).thenReturn(1280)
+        whenever(secondaryLayout.height()).thenReturn(720)
+
+        // Place a task with a size equals to display size.
+        val task = setUpFreeformTask(displayId = DEFAULT_DISPLAY, bounds = Rect(0, 0, 1280, 960))
+
+        controller.moveToNextDisplay(task.taskId)
+
+        with(getLatestWct(type = TRANSIT_CHANGE)) {
+            val taskChange = changes[task.token.asBinder()]
+            assertThat(taskChange).isNotNull()
+            // DP size is preserved. The window is centered in the destination display.
+            assertThat(taskChange!!.configuration.windowConfiguration.bounds)
+                .isEqualTo(Rect(320, 120, 960, 600))
+        }
+    }
+
+    @Test
+    @EnableFlags(FLAG_ENABLE_MOVE_TO_NEXT_DISPLAY_SHORTCUT)
+    fun moveToNextDisplay_defaultBoundsWhenDestinationTooSmall() {
+        // Set up two display ids
+        whenever(rootTaskDisplayAreaOrganizer.displayIds)
+            .thenReturn(intArrayOf(DEFAULT_DISPLAY, SECOND_DISPLAY))
+        // Create a mock for the target display area: second display
+        val secondDisplayArea = DisplayAreaInfo(MockToken().token(), SECOND_DISPLAY, 0)
+        whenever(rootTaskDisplayAreaOrganizer.getDisplayAreaInfo(SECOND_DISPLAY))
+            .thenReturn(secondDisplayArea)
+        // Two displays have different density
+        whenever(displayLayout.densityDpi()).thenReturn(320)
+        whenever(displayLayout.width()).thenReturn(2400)
+        whenever(displayLayout.height()).thenReturn(1600)
+        val secondaryLayout = mock(DisplayLayout::class.java)
+        whenever(displayController.getDisplayLayout(SECOND_DISPLAY)).thenReturn(secondaryLayout)
+        whenever(secondaryLayout.densityDpi()).thenReturn(160)
+        whenever(secondaryLayout.width()).thenReturn(640)
+        whenever(secondaryLayout.height()).thenReturn(480)
+        whenever(secondaryLayout.getStableBoundsForDesktopMode(any())).thenAnswer { i ->
+            (i.arguments.first() as Rect).set(0, 0, 640, 480)
+        }
+
+        // A task with a size of 1800x1200 is being placed. To preserve DP size,
+        // 900x600 pixels are needed, which does not fit in the destination display.
+        val task =
+            setUpFreeformTask(displayId = DEFAULT_DISPLAY, bounds = Rect(300, 200, 2100, 1400))
+
+        controller.moveToNextDisplay(task.taskId)
+
+        with(getLatestWct(type = TRANSIT_CHANGE)) {
+            val taskChange = changes[task.token.asBinder()]
+            assertThat(taskChange).isNotNull()
+            assertThat(taskChange!!.configuration.windowConfiguration.bounds.left).isAtLeast(0)
+            assertThat(taskChange.configuration.windowConfiguration.bounds.top).isAtLeast(0)
+            assertThat(taskChange.configuration.windowConfiguration.bounds.right).isAtMost(640)
+            assertThat(taskChange.configuration.windowConfiguration.bounds.bottom).isAtMost(480)
+        }
+    }
+
+    @Test
     fun getTaskWindowingMode() {
         val fullscreenTask = setUpFullscreenTask()
         val freeformTask = setUpFreeformTask()
