当应用程序在 mac 中获得焦点时触发苹果脚本/自动程序

Trigger an apple script / automator when an application comes to focus in mac

我想根据应用程序自动化键盘布局。我正在远程使用 Windows VM 我不想创建一个脚本,它可以:

  1. 更改应用程序切换到 Windows VM 时的键盘布局
  2. 将其改回所有其他应用程序的正常布局。

我很难找到应用程序焦点更改的触发事件。是否可以通过 automator 来完成?

或者请提出其他解决方案来解决问题。

假设你只有两种键盘布局,你可以使用下面的脚本应用。

首先,您需要打开“系统偏好设置”并查看“键盘”➔“快捷方式”➔“输入源”;查看 'selecting previous input source' 的键盘快捷键是什么,确保它已被单击,然后将其复制到脚本中标记的位置。我已将我的设置为 comd-ctrl-space (^⌘ ),但您的可能有所不同。您还应该检查“Windows VM”是否是该应用程序的正确名称:在 Finder 中找到该应用程序,select 它并键入 ⌘I 打开获取信息 window,然后查看名称和扩展名文本框。

现在执行以下操作

  1. 在脚本编辑器中复制以下脚本
  2. 将其另存为 stay-open 应用程序
    • select 'Application' 来自左下方的 'Format' 菜单
    • 单击 'Stay open after run handler' 复选框
  3. 打开系统偏好设置并执行以下操作
    • 将应用程序添加到安全和隐私中的辅助功能部分➔隐私(以便它可以发送键盘快捷键)
    • 将应用程序添加到用户和组中您帐户的“登录项”部分(以便它在登录时自动启动)

然后您可以 运行 它并进行测试。该应用程序在后台等待接收应用程序已激活或停用的通知,然后它会检查应用程序名称并在 Window VM 应用程序出现或消失时触发用于切换输入源的键盘快捷键。

use AppleScript version "2.4"
use framework "AppKit"
use scripting additions

property NSWorkspace : class "NSWorkspace"

on run
    set workSp to NSWorkspace's sharedWorkspace()
    set notifCent to workSp's notificationCenter()
    tell notifCent to addObserver:me selector:"appHasActivated:" |name|:"NSWorkspaceDidActivateApplicationNotification" object:(missing value)
    tell notifCent to addObserver:me selector:"appHasDeactivated:" |name|:"NSWorkspaceDidDeactivateApplicationNotification" object:(missing value)
end run

on idle
    -- we don't use the idle loop, so tell the system to check in once an hour
    return 3600
end idle

on appHasActivated:notif
    set targetApp to (notif's userInfo's valueForKey:"NSWorkspaceApplicationKey")
    set targetAppName to (targetApp's localizedName) as text
    if targetAppName is "Windows VM" then
        tell application "System Events"
            tell process "Windows VM"
                -- change this line to match your 'Select previous input source' keyboard shortcut
                keystroke space using {command down, control down}
            end tell
        end tell
    end if
end appHasActivated:

on appHasDeactivated:notif
    set targetApp to (notif's userInfo's valueForKey:"NSWorkspaceApplicationKey")
    set targetAppName to (targetApp's localizedName) as text
    if targetAppName is "Windows VM" then
        tell application "System Events"
            tell process targetAppName
                -- change this line to match your 'Select previous input source' keyboard shortcut
                keystroke space using {command down, control down}
            end tell
        end tell
    end if
end appHasDeactivated:

一旦您对它的工作感到满意,您可以 运行 在终端中输入以下命令:

defaults write '/path/to/$name.app/Contents/Info.plist' LSUIElement -bool yes

这会将应用程序变成后台代理,它永远不会出现在前台并且在 Dock 中是不可见的。这样你就可以忘记它了。