如何使用 AppleScript 访问子标题组下的子菜单项

How to access submenu item under subheading group with AppleScript

我无法访问 "library-test" 子菜单项(见屏幕截图)。我的猜测是,它与菜单中标题为 "Symbols" 的其他项目 grouped/offset 相关。

我尝试将 "Symbols" 视为自己的菜单项,但没有成功。

有没有人运行以前参与过这个?谢谢!

AppleScript:

tell application "System Events"
    tell process "Sketch"
        set frontmost to true
        click menu item "Rectangle" of menu of menu item "library-test" of menu "Insert" of menu bar 1
    end tell
end tell

脚本编辑器中的错误消息:

"Can’t get menu item "library-test" of menu "Insert" of menu bar 1 of process "Sketch".

编辑:UI浏览器屏幕Reader工具提示路径正确:

AppleScript GUI 脚本的一个特点是对象的元素始终是一对多关系,即使我们可能自然地假定一对一关系。你我都知道一个菜单项只能附加一个菜单,但 AppleScript 没有,所以我们仍然必须为菜单指定一个索引。如果你写:

,事情应该能正常工作
click menu item "Rectangle" of menu 1 of menu item "library-test" [...]

菜单名称中可能有一些奇怪的字符,例如软连字符、不间断连字符、不间断 space 等。一种解决方案是尝试获取特定菜单项通过它的索引,无论名称是什么。执行此操作的处理程序类似于:

on run -- example
    clickMenu at {"Sketch", "Insert", 18, "Rectangle"}
end run

to clickMenu at menuList -- {application, menu, menu/item/index, menu/item/index, ...}
    try
        set itemCount to (count menuList)
        if itemCount < 3 then error "clickMenu handler:  menu item list contains too few items"
        set {appName, menuName} to items 1 thru 2 of menuList
        set {menuItem, found} to {last item of menuList, false}
        tell application appName to activate
        tell application "System Events" -- set up the menu path
            set appName to (name of application processes whose frontmost is true) as text -- process name might be different
            set menuPath to menu menuName of menu bar item menuName of menu bar 1 of application process appName
            if itemCount > 3 then repeat with i from 3 to (itemCount - 1) -- add sub menu items
                set menuName to item i of menuList
                if class of menuName is integer then set menuName to item menuName of (get name of menu items of menuPath)
                set menuPath to menu menuName of menu item menuName of menuPath
            end repeat
            if class of menuItem is not integer then -- go for a a partial name match of the last item
                repeat with anItem in (get name of menu items of menuPath)
                    if anItem begins with menuItem then -- can also use 'contains', etc
                        set {menuItem, found} to {anItem, true}
                        exit repeat
                    end if
                end repeat
                if not found then error "clickMenu handler:  menu item " & quoted form of menuItem & " not found"
            end if
            if (enabled of menu item menuItem of menuPath) then -- or filter for other desired property
                click menu item menuItem of menuPath
                delay 0.5
                return true -- success
            end if
            return false -- menu item not clicked
        end tell
    on error errorMessage number errorNumber
        -- error errorMessage number errorNumber -- uncomment to pass error up the chain
        log errorMessage
        return false
    end try
end clickMenu

恐怕这是个坏消息:我刚刚下载了 Sketch 并试了一下菜单层次结构。您的参考是正确的,但它似乎只在菜单关闭后的短时间内有效。无论出于何种原因,Sketch 似乎在运行时热加载特定菜单项,并在菜单关闭时再次卸载它们。

我显然没有你现有的菜单组合,因为我没有那些特定的符号,但这里有一个你可能熟悉的:

menu item "Document" of menu "Insert" of menu bar item "Insert" of menu bar 1 of process "Sketch"

我最初打开了菜单,然后将其关闭以进入 脚本编辑器 并 bash 退出 menu item 参考。它工作正常,我得到了一堆属性和属性名称:

{UIProperties:{minimum value:missing value ¬
    , orientation:missing value, position:{195, 264} ¬
    , class:menu item, accessibility description:missing value ¬
    , role description:"menu item", focused:missing value ¬
    , title:"Document", size:{173, 19}, help:missing value ¬
    , entire contents:{}, enabled:true, maximum value:missing value ¬
    , role:"AXMenuItem", value:missing value, subrole:missing value ¬
    , selected:true, name:"Document", description:"menu item"} ¬
    , UIAttributes:{"AXEnabled", "AXFrame", "AXParent", "AXChildren", ¬
    "AXSize", "AXMenuItemCmdGlyph", "AXRole", "AXMenuItemPrimaryUIElement", ¬
    "AXServesAsTitleForUIElements", "AXMenuItemCmdModifiers", "AXPosition", ¬
    "AXTitle", "AXHelp", "AXMenuItemCmdChar", "AXRoleDescription", ¬
    "AXSelected", "AXMenuItemCmdVirtualKey", "AXMenuItemMarkChar"} ¬
    , UIActions:{"AXCancel", "AXPress"}}

大约 20-30 秒后,完全相同的 menu item 引用抛出错误,报告未找到 menu item "Document"。所以我 运行 这个:

name of menu items of menu "Insert" of menu bar item "Insert" of menu bar 1 of process "Sketch"

您可能可以推断,这将 return "Insert" 菜单中所有 menu items 的名称,并且人们会期望 "Document" 在那里:

{"New Page", missing value, "Shape", "Vector", "Pencil", missing value, "Text", ¬
 "Image…", missing value, "Artboard", "Slice", "Hotspot", missing value, missing value}

没有。为了便于比较,屏幕上的菜单如下所示:

missing value 项很好 — 它们对应于水平分隔线,除了最后一个对应于 "Symbol" sub-section header。奇怪的是列表在那里终止; 字面上不再存在的附加菜单项甚至没有占位符(直到我再次打开菜单备份)。

我猜想访问这样的菜单项的唯一方法是让你的脚本点击菜单打开它,然后点击菜单项,依此类推......非常不优雅,我个人宁愿把我的电脑扔到阳光下也不愿那样做,但我在这里看不到其他选择。

该应用程序显然 可编写脚本,但它没有附带术语词典,因此我们也无能为力。