From 22e94e4f6cb5d3ea186fed2582c847de5233378a Mon Sep 17 00:00:00 2001 From: Arkadiusz Fal Date: Sat, 10 Oct 2026 22:08:29 +0200 Subject: [PATCH] Stop double-unscaling the dismiss morph's mini player target The mini player's SwiftUI global frame already ignores the scale transform on the main window's content, so mapping it out of that scale again landed the morph about 8% too large, left and high of the preview, which then jumped into place when the real mini player took over. --- .../Views/Player/ExpandedPlayerWindow.swift | 24 ++++--------------- 1 file changed, 5 insertions(+), 19 deletions(-) diff --git a/Yattee/Views/Player/ExpandedPlayerWindow.swift b/Yattee/Views/Player/ExpandedPlayerWindow.swift index dfe79048..ba4d66f4 100644 --- a/Yattee/Views/Player/ExpandedPlayerWindow.swift +++ b/Yattee/Views/Player/ExpandedPlayerWindow.swift @@ -1091,21 +1091,6 @@ final class ExpandedPlayerWindowManager { rootVC.view.layoutIfNeeded() } - /// Maps a rect seen inside the scaled main window content to where it sits - /// once `scaleMainWindow(progress: 0)` restores the identity transform. - private func unscaledMainWindowRect(_ rect: CGRect) -> CGRect { - guard let presentingView = scaledPresentingView, !presentingView.transform.isIdentity else { return rect } - let center = presentingView.center - let inverse = presentingView.transform.inverted() - func unscale(_ point: CGPoint) -> CGPoint { - let local = CGPoint(x: point.x - center.x, y: point.y - center.y).applying(inverse) - return CGPoint(x: local.x + center.x, y: local.y + center.y) - } - let origin = unscale(rect.origin) - let corner = unscale(CGPoint(x: rect.maxX, y: rect.maxY)) - return CGRect(x: origin.x, y: origin.y, width: corner.x - origin.x, height: corner.y - origin.y) - } - /// Shrinks the expanded window onto its video and flies it into the mini /// player's video preview. Returns false (doing nothing) when no target is /// available, so the caller falls back to sliding off screen. @@ -1120,12 +1105,13 @@ final class ExpandedPlayerWindowManager { return false } - // The mini player reports where it is now, inside the main window's - // scaled-down content; the morph lands once that scale is back to identity. - // The scaled content also got a smaller bottom safe area (UIKit derives it + // The mini player reports its SwiftUI global frame, which ignores the scale + // transform on the main window's content (that animates back to identity + // alongside the morph), so it is already where the mini player ends up. + // The scaled content did get a smaller bottom safe area (UIKit derives it // from the transformed frame), which comes back once unscaled and lifts // the bottom-anchored mini player by the difference. - var target = unscaledMainWindowRect(nav.miniPlayerVideoFrame) + var target = nav.miniPlayerVideoFrame if let mainWindow, let mainRootView = mainWindow.rootViewController?.view { target.origin.y -= max(0, mainWindow.safeAreaInsets.bottom - mainRootView.safeAreaInsets.bottom) }