Bladeren bron

Center the main window on launch and reopen.

Disable macOS window restoration and explicitly position the app in the screen center so it no longer reopens in the previous corner.

Co-authored-by: Cursor <cursoragent@cursor.com>
AhtashamShahzad1 4 weken geleden
bovenliggende
commit
7fa79fd458

+ 56 - 0
Reddit App/App/AppDelegate.swift

@@ -3,6 +3,8 @@ import AppKit
 @MainActor
 final class AppDelegate: NSObject, NSApplicationDelegate, NSWindowDelegate {
     private var windowObservers: [NSObjectProtocol] = []
+    private var shouldCenterMainWindowOnShow = true
+    private var centeringDeadline: Date?
 
     func applicationShouldTerminateAfterLastWindowClosed(_ sender: NSApplication) -> Bool {
         false
@@ -18,6 +20,7 @@ final class AppDelegate: NSObject, NSApplicationDelegate, NSWindowDelegate {
     func applicationDidFinishLaunching(_ notification: Notification) {
         installWindowObservers()
         configureMainWindows()
+        beginCenteringMainWindow()
     }
 
     func applicationDidBecomeActive(_ notification: Notification) {
@@ -26,6 +29,10 @@ final class AppDelegate: NSObject, NSApplicationDelegate, NSWindowDelegate {
     }
 
     func windowShouldClose(_ sender: NSWindow) -> Bool {
+        if isMainAppWindow(sender) {
+            shouldCenterMainWindowOnShow = true
+            centeringDeadline = nil
+        }
         sender.orderOut(nil)
         return false
     }
@@ -40,15 +47,63 @@ final class AppDelegate: NSObject, NSApplicationDelegate, NSWindowDelegate {
         RedditWebViewStore.shared.resumeMediaPlaybackAfterWindowDeminiaturize()
     }
 
+    func windowDidMove(_ sender: NSWindow) {
+        guard isMainAppWindow(sender), isCenteringMainWindow else { return }
+        AppWindow.centerOnScreen(sender)
+    }
+
     func configureMainWindows() {
         for window in NSApp.windows where isMainAppWindow(window) {
             window.isReleasedWhenClosed = false
+            window.isRestorable = false
+            window.setFrameAutosaveName("")
             if window.delegate !== self {
                 window.delegate = self
             }
         }
     }
 
+    func centerMainWindow() {
+        beginCenteringMainWindow()
+    }
+
+    private var isCenteringMainWindow: Bool {
+        guard shouldCenterMainWindowOnShow else { return false }
+        if let centeringDeadline {
+            return Date() < centeringDeadline
+        }
+        return true
+    }
+
+    private func beginCenteringMainWindow() {
+        shouldCenterMainWindowOnShow = true
+        centeringDeadline = Date().addingTimeInterval(0.6)
+        centerMainWindowIfNeeded()
+    }
+
+    private func finishCenteringMainWindow() {
+        shouldCenterMainWindowOnShow = false
+        centeringDeadline = nil
+    }
+
+    private func centerMainWindowIfNeeded() {
+        guard isCenteringMainWindow else { return }
+        guard let window = NSApp.windows.first(where: isMainAppWindow) else { return }
+
+        let centerAction = { [weak self] in
+            guard let self, self.isCenteringMainWindow else { return }
+            AppWindow.centerOnScreen(window)
+        }
+
+        centerAction()
+        DispatchQueue.main.async(execute: centerAction)
+        DispatchQueue.main.asyncAfter(deadline: .now() + 0.15, execute: centerAction)
+        DispatchQueue.main.asyncAfter(deadline: .now() + 0.35) { [weak self] in
+            centerAction()
+            self?.finishCenteringMainWindow()
+        }
+    }
+
     private func installWindowObservers() {
         let center = NotificationCenter.default
 
@@ -81,6 +136,7 @@ final class AppDelegate: NSObject, NSApplicationDelegate, NSWindowDelegate {
 
     private func showMainWindow() {
         guard let window = NSApp.windows.first(where: isMainAppWindow) else { return }
+        beginCenteringMainWindow()
         window.makeKeyAndOrderFront(nil)
         NSApp.activate(ignoringOtherApps: true)
     }

+ 1 - 0
Reddit App/App/RedditAppApp.swift

@@ -22,6 +22,7 @@ struct RedditAppApp: App {
                 }
         }
         .defaultSize(width: AppWindow.width, height: AppWindow.height)
+        .defaultPosition(.center)
         .windowStyle(.hiddenTitleBar)
         .commands {
             CommandGroup(replacing: .newItem) {}

+ 21 - 0
Reddit App/Utilities/AppWindow.swift

@@ -1,3 +1,4 @@
+import AppKit
 import CoreGraphics
 
 enum AppWindow {
@@ -11,4 +12,24 @@ enum AppWindow {
 
     /// Small top breathing room for the embedded Reddit panel.
     static let redditTopInset: CGFloat = 30
+
+    @MainActor
+    static func centerOnScreen(_ window: NSWindow) {
+        guard !window.styleMask.contains(.fullScreen) else { return }
+
+        let screen = NSScreen.main ?? window.screen
+        guard let screen else {
+            window.center()
+            return
+        }
+
+        var frame = window.frame
+        frame.size = NSSize(width: width, height: height)
+
+        let visible = screen.visibleFrame
+        frame.origin.x = visible.origin.x + ((visible.width - frame.width) / 2)
+        frame.origin.y = visible.origin.y + ((visible.height - frame.height) / 2)
+
+        window.setFrame(frame, display: true)
+    }
 }

+ 2 - 1
Reddit App/Views/Components/MainWindowLifecycleConfigurator.swift

@@ -7,12 +7,13 @@ struct MainWindowLifecycleConfigurator: NSViewRepresentable {
         view.onWindowChange = { window in
             guard let window, let delegate = NSApp.delegate as? AppDelegate else { return }
             delegate.configureMainWindows()
+            delegate.centerMainWindow()
         }
         return view
     }
 
     func updateNSView(_ nsView: WindowObservationView, context: Context) {
-        guard let window = nsView.window, let delegate = NSApp.delegate as? AppDelegate else { return }
+        guard nsView.window != nil, let delegate = NSApp.delegate as? AppDelegate else { return }
         delegate.configureMainWindows()
     }
 }