
桌面应用AI 应用插件系统【免费下载链接】WoxA cross-platform launcher that simply works项目地址https://gitcode.com/gh_mirrors/wo/Wox点击查看免费下载菜单插件Menus Plugin是 Wox 内置的系统插件之一它把当前 macOS 应用的菜单栏变成一个可全文搜索的命令集只要让目标应用保持焦点在 Wox 中输入菜单项名称的一部分即可定位并直接执行对应的菜单命令。本篇文章将基于 Wox 仓库中的官方文档与插件源码完整讲解该插件的使用方式、触发机制、菜单解析原理与底层实现帮助你快速上手也能理解它背后的 macOS 辅助功能Accessibility调用链。快速开始菜单插件的使用方式非常简单遵循聚焦应用 → 打开 Wox → 输入菜单名三步流程让目标应用保持焦点例如 Safari 或其他任意 Mac 应用打开 Wox直接输入菜单项名称的一部分在结果列表中选中目标菜单项回车即可执行对应菜单命令。官方文档给出的两个典型搜索词export preferences例如在 Safari 聚焦时输入preferencesWox 会匹配到「Safari → Settings…」这类位于应用菜单下的菜单项选中后等效于用鼠标点击该菜单。这个插件只在 macOS 上提供其元数据中SupportedOS字段明确限定为Macos见 menus_darwin.go。如何触发全局搜索与「menus」关键词从插件元数据可以看出该插件注册了两种触发方式TriggerKeywords: []string{ *, menus, },*表示全局搜索不依赖任何前缀直接在 Wox 中输入菜单项文字即可命中menus作为显式关键词输入menus后再接菜单名可以更精确地在菜单插件范围内过滤。由于全局匹配到的是形如父菜单-子菜单的完整路径当目标应用的菜单层级较深时建议直接输入目标菜单项名称的片段如export模糊匹配会自动定位。匹配规则与结果呈现插件拿到菜单项后通过 Wox 的模糊匹配引擎进行过滤见 menus_darwin.gofilteredMenus : lo.Filter(menuNames, func(menu string, _ int) bool { match, score : plugin.IsStringMatchScore(ctx, menu, query.Search) return (match score 20) || (!query.IsGlobalQuery() query.Search ) })两个细节值得注意分数阈值只有匹配且得分大于 20 的菜单项才会出现在结果中避免把无关菜单项当作搜索结果空搜索兜底当不是全局查询即通过menus关键词进入且搜索词为空时会列出当前应用的全部菜单项方便你浏览整棵菜单树。每个结果项都带有当前活动窗口应用的图标当活动窗口图标不可用时回退到内置的菜单图标图标定义见 default_plugin.go执行动作名为plugin_menus_execute回车后触发对应菜单命令。插件如何获得当前应用QueryEnv 特性声明菜单插件必须知道当前哪个应用处于焦点这依赖 Wox 的 QueryEnv 机制。插件在元数据中显式声明了两个环境变量需求见 menus_darwin.goFeatures: []plugin.MetadataFeature{ { Name: plugin.MetadataFeatureQueryEnv, Params: map[string]any{ requireActiveWindowPid: true, requireActiveWindowIcon: true, }, }, },Wox 主程序在 metadata.go 中解析这些参数requireActiveWindowPid要求查询环境附带当前活动窗口的进程 IDrequireActiveWindowIcon要求附带活动窗口图标。在查询回调中插件据此拿到query.Env.ActiveWindowPidif query.Env.ActiveWindowPid 0 { i.api.Log(ctx, plugin.LogLevelError, Active window pid is not available) return plugin.QueryResponse{} }若拿不到 PID例如 Wox 自身获得焦点、或当前窗口不可枚举插件会直接返回空结果并记录错误日志。这也是为什么使用前必须保持目标应用为焦点窗口。菜单是怎么读出来的Accessibility API 调用链从源码结构看菜单的读取与执行横跨三层插件层menus_darwin.go负责查询编排、结果过滤、缓存与动作分发cgo 桥接层util/menus/menus_darwin.go通过 cgo 声明对 Objective-C 函数的调用/* #cgo CFLAGS: -x objective-c #cgo LDFLAGS: -framework Foundation -framework Cocoa -framework AppKit char** getMenuItems(int pid, int* count); void performMenuAction(int pid, const char* title); */Go 侧提供GetAppMenuTitles(pid)读取菜单标题列表、ExecuteActiveAppMenu(pid, title)执行菜单动作并负责C.CString、C.GoString与内存释放等跨语言转换。Objective-C 实现层util/menus/menus_darwin.m核心是 macOS 的 Accessibility 框架调用链如下AXUIElementCreateApplication(pid)依据进程 PID 创建应用的可访问性元素AXUIElementCopyAttributeValue(app, kAXMenuBarAttribute, ...)获取应用菜单栏递归遍历kAXChildrenAttribute展开每一级菜单同时读取kAXTitleAttribute组装父菜单-子菜单的完整路径最终生成可搜索的标题列表。其中getMenuItemTitles的递归逻辑决定了标题的拼接规则叶子菜单项无子项输出parentTitle-title根级菜单输出裸标题当标题为空时只传递父级路径。此外实现中会跳过名为Apple的菜单即系统菜单避免把系统级菜单混入搜索结果。执行菜单动作时performMenuAction再次遍历菜单树找到完整路径与目标一致的菜单项后调用AXUIElementPerformAction(menuItem, kAXPressAction);即向该菜单项发送按下动作等效于用户真实点击该菜单。从上述实现可以推断该功能依赖 macOS 的 Accessibility 辅助功能接口因此在系统设置中需要为 Wox 授予「辅助功能」权限若读取失败插件会记录错误日志如Failed to get menu bar for app with pid ...并返回空结果这通常就是权限未授予或目标应用不暴露菜单栏的典型表现。性能设计一分钟菜单缓存菜单栏解析是较为昂贵的操作每次都要递归遍历整棵菜单树因此插件引入了按 PID 隔离的缓存见 menus_darwin.govar menusCacheTTL time.Minute var menusCache util.NewHashMap[int, menusCacheEntry]() type menusCacheEntry struct { titles []string expiresAt time.Time }查询时先查缓存命中且未过期则直接使用否则调用menus.GetAppMenuTitles重新解析并写入缓存TTL 为 1 分钟。getMenusFromCache在过期时会主动删除旧条目避免内存中堆积已退出应用的菜单数据。这意味着菜单变更后最多一分钟内即可看到新菜单项同时重复查询不会重复触发昂贵的 AX 遍历。使用提示与常见问题排查确认焦点如果输入菜单名没有任何结果先确认目标应用确实是当前焦点窗口点击一下应用窗口再回到 Wox 输入。使用更完整的路径片段层级深的菜单如文件-导出-导出为 PDF…建议输入末级菜单名或中间片段模糊匹配得分更高。通过menus关键词浏览输入menus加空格后不输入其他内容可以看到当前应用的全部菜单项列表。权限问题如果插件完全无输出且日志出现 AX 相关错误请检查系统「隐私与安全性 → 辅助功能」中是否已为 Wox 开启权限并重启 Wox 使其生效。系统菜单排除Apple菜单被实现层主动跳过这是设计行为不属于缺陷。小结Wox 的 macOS 菜单插件以极小的交互成本把点菜单变成了打字搜索其实现是 Wox 插件体系的一个典型范例通过TriggerKeywords与MetadataFeatureQueryEnv声明触发方式和环境依赖利用 cgo 桥接 Go 与 Objective-C再借助 macOS Accessibility API 完成菜单树的读取与点击动作。如果你想深入阅读实现细节推荐依次查看官方文档、插件主逻辑与Objective-C 实现三个文件。赞分享桌面应用AI 应用插件系统【免费下载链接】WoxA cross-platform launcher that simply works项目地址https://gitcode.com/gh_mirrors/wo/Wox点击查看免费下载相关推荐如何使用NW.js创建原生体验应用菜单从基础到高级的完整指南如何使用NW.js创建原生体验应用菜单从基础到高级的完整指南 NW.jsNode Webkit是一个强大的框架允许开发者使用Web技术HTML、CSS桌面应用跨平台Unity MCP 菜单项执行指南用 execute_menu_item 工具让 AI 精确操控 Unity 编辑器菜单Unity MCP 菜单项执行指南用 execute_menu_item 工具让 AI 精确操控 Unity 编辑器菜单 导读 execute_menu_itMCP 服务AI 应用游戏开发工具调用x64dbg GuiMenuClear 接口详解清空菜单项的跨进程实现与插件菜单生命周期x64dbg GuiMenuClear 接口详解清空菜单项的跨进程实现与插件菜单生命周期 本文讲解 x64dbg GUI 插件接口中的 GuiMenuClea逆向工程调试器开发工具应用安全上一篇终极指南3步让老旧Mac焕新用OpenCore Legacy Patcher重获新生下一篇TinyConsole快速入门指南5分钟学会在iOS应用中集成微型控制台创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考