Swift:如何激活和取消隐藏任何应用程序的窗口?

Swift:如何激活和取消隐藏任何应用程序的窗口?,swift,macos,macos-catalina,Swift,Macos,Macos Catalina,我看到NSRunningApplicationInstance.activate()方法的行为非常奇怪 让我们想象一下,我发现了一个名为“Finder”的应用程序。目前该应用程序是: 未激活和/或隐藏 我有非常简单的代码: let activeOptions: NSApplication.ActivationOptions = [.activateAllWindows, .activateIgnoringOtherApps] print("1. isActive: \(app.isActive

我看到
NSRunningApplicationInstance.activate()方法的行为非常奇怪

让我们想象一下,我发现了一个名为“Finder”的应用程序。目前该应用程序是:

未激活
和/或
隐藏

我有非常简单的代码:

let activeOptions: NSApplication.ActivationOptions = [.activateAllWindows, .activateIgnoringOtherApps]

print("1. isActive: \(app.isActive); isHidden: \(app.isHidden)")
if (!app.isActive)
{
   app.activate(options: activeOptions)
}

if ( app.isHidden )
{
   app.unhide()
}
print("2. isActive: \(app.isActive); isHidden: \(app.isHidden)")
要查找所需的应用程序,您可以使用以下代码:

let app = NSWorkspace.shared.runningApplications.filter{ $0.localizedName = "NameOfApp"}
2次运行代码结果:

  • isActive:假;伊希登:错
  • isActive:假;伊希登:错
  • isActive:正确;伊希登:错
  • isActive:正确;伊希登:错
  • 如果你愿意试试……:

  • 代码为将显示应用程序的菜单:

  • 但只有在第二次代码运行时!(为什么?)

  • 不会向我显示应用程序窗口!(为什么?

  • 我在很多应用程序中看到了类似的行为,不仅仅是Finder

    例如SourceTree应用程序



    在任何情况下,有人能用一些代码解释一下任何运行的应用程序的逻辑和显示窗口吗?

    这里是正在工作的游乐场模块。该方法是在目标应用程序出现所需状态时,使用KVO通知可观察属性。希望能有所帮助

    import Cocoa
    
    class AppActivator: NSObject {
    
        private var application: NSRunningApplication!
        private let filterName: String
    
        init(appName: String) {
            filterName = appName
        }
    
        func activate() {
            guard let app = NSWorkspace.shared.runningApplications.filter ({
                return $0.localizedName == self.filterName || $0.bundleIdentifier?.contains(self.filterName) ?? false
            }).first else {
                print("Application \(self.filterName) not found")
                return
            }
    
            guard app.activationPolicy != .prohibited else {
                print("Application \(self.filterName) prohibits activation")
                return
            }
    
            self.application = app
    
            self.unhideAppIfNeeded()
            self.activateAppIfNeeded()
        }
    
        private func unhideAppIfNeeded() {
            if application.isHidden {
                application.addObserver(self, forKeyPath: "isHidden", options: .new, context: nil)
                application.unhide()
            }
        }
    
        private func activateAppIfNeeded() {
            if !application.isHidden && !application.isActive {
                application.addObserver(self, forKeyPath: "isActive", options: .new, context: nil)
                application.activate(options: .activateIgnoringOtherApps)
            }
        }
    
        override func observeValue(forKeyPath keyPath: String?, of object: Any?, change: [NSKeyValueChangeKey : Any]?, context: UnsafeMutableRawPointer?) {
            if keyPath == "isHidden" {
                application.removeObserver(self, forKeyPath: "isHidden")
                activateAppIfNeeded()
            } else if keyPath == "isActive" {
                application.removeObserver(self, forKeyPath: "isActive")
                print("Application \(application.localizedName) - ACTIVATED!")
            }
        }
    }
    
    let activator = AppActivator(appName: "Finder")
    activator.activate()
    

    该应用程序需要一些时间才能激活。请看我已检查:不工作=(尝试打开finder,最小化它并运行代码;应用程序窗口将不显示活动和隐藏是应用程序状态,最小化是窗口状态-请不要混淆它们。