You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何获取macOS 14+系统Dock的宽度?适配类Dock窗口布局

在macOS 14+获取Dock实际尺寸的非截图方案

以下是几种无需截图分析即可获取Dock完整尺寸的可行方案,均适配macOS 14+系统:

1. 借助辅助功能AXUIElement API

macOS辅助功能框架允许访问系统应用的UI元素属性,Dock的Bundle ID为com.apple.dock,可通过该API直接获取其位置和尺寸。注意:应用需在系统偏好设置「安全性与隐私」→「辅助功能」中获得用户授权。

示例Swift实现:

import ApplicationServices

func getDockFrame() -> CGRect? {
    guard let dockBundle = Bundle(identifier: "com.apple.dock") else { return nil }
    let dockElement = AXUIElementCreateApplication(dockBundle.bundleIdentifier!)
    
    // 获取位置
    var position: AnyObject?
    guard AXUIElementCopyAttributeValue(dockElement, kAXPositionAttribute as CFString, &position) == .success,
          let point = position as? CGPoint else { return nil }
    
    // 获取尺寸
    var size: AnyObject?
    guard AXUIElementCopyAttributeValue(dockElement, kAXSizeAttribute as CFString, &size) == .success,
          let dockSize = size as? CGSize else { return nil }
    
    return CGRect(origin: point, size: dockSize)
}

拿到Dock的frame后,结合当前屏幕宽度即可计算左右空白区域:(屏幕宽度 - Dock宽度) / 2,即为单侧空白的宽度。

2. 通过CGWindowList遍历系统窗口

利用Core Graphics的窗口列表接口,筛选出标记为"Dock"的系统窗口,直接读取其边界信息。该方法无需辅助功能权限,但需注意Dock窗口名称在系统版本中的一致性(macOS 14+中仍为"Dock")。

示例Objective-C实现:

#import <CoreGraphics/CoreGraphics.h>

CGRect getDockFrame() {
    CFArrayRef windowList = CGWindowListCopyWindowInfo(kCGWindowListOptionOnScreenOnly, kCGNullWindowID);
    for (NSDictionary *windowInfo in (__bridge NSArray *)windowList) {
        NSString *windowName = windowInfo[(id)kCGWindowName];
        if ([windowName isEqualToString:@"Dock"]) {
            NSDictionary *bounds = windowInfo[(id)kCGWindowBounds];
            CGRect frame = CGRectMake([bounds[@"X"] floatValue],
                                     [bounds[@"Y"] floatValue],
                                     [bounds[@"Width"] floatValue],
                                     [bounds[@"Height"] floatValue]);
            CFRelease(windowList);
            return frame;
        }
    }
    CFRelease(windowList);
    return CGRectZero;
}

3. 利用AppleScript间接查询

通过执行AppleScript脚本获取Dock的边界信息,再将结果解析为CGRect。本质依赖辅助功能权限,但可在应用内通过NSAppleScript调用,无需额外工具。

示例Swift实现:

import Foundation

func getDockFrameViaAppleScript() -> CGRect? {
    let scriptSource = """
        tell application "System Events"
            return bounds of application process "Dock"
        end tell
        """
    let appleScript = NSAppleScript(source: scriptSource)
    var error: NSDictionary?
    guard let result = appleScript?.executeAndReturnError(&error),
          let boundsArray = result.arrayValue, boundsArray.count == 4 else { return nil }
    
    guard let x1 = boundsArray[0].doubleValue,
          let y1 = boundsArray[1].doubleValue,
          let x2 = boundsArray[2].doubleValue,
          let y2 = boundsArray[3].doubleValue else { return nil }
    
    return CGRect(x: x1, y: y1, width: x2 - x1, height: y2 - y1)
}

内容的提问来源于stack exchange,提问作者TinyOlap

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.26 10:20:37