从Python访问API的Objective-C常量和枚举

1 投票
1 回答
876 浏览
提问于 2025-04-16 06:36

我正在使用pyobjc来给一些随机的Python软件添加一些必要的OSX功能。我需要从Python中访问一些在API中定义的objc常量。

一个这样的常量的例子可以在NSRunningApplication页面的很深处找到,特别是NSApplicationActivationPolicy的三个可能值。

为了让你更明白,目前的任务是列出当前正在运行的、用户可以看到的应用程序。为此,下面的代码运行得很好:

from Foundation import *
from Cocoa import *
import objc

for runningApp in sorted(
                     NSWorkspace.sharedWorkspace().runningApplications(),
                     key=lambda x: x.localizedName()
                  ):
    if runningApp.activationPolicy() == 0:
        # Do stuff

不过,我希望能让代码更易读,不想用零来进行判断,也不想在自己的代码中硬编码一个虚假的NSApplicationActivationPolicyRegular值,因为这个值在原始库中已经可以直接使用了。

我该如何通过pyobjc从Python中访问这些objc常量呢?

1 个回答

1

苹果提供的PyObjC比10.6版本的Cocoa更新的功能要早,所以它对一些新功能不了解。比如,NSRunningApplication就是一个新功能,PyObjC就不知道它。你需要在这个路径下的AppKit BridgeSupport文件中添加一些额外的信息:/System/Library/Frameworks/Python.framework/Versions/2.6/Extras/lib/python/PyObjC/AppKit/PyObjC.bridgesupport

这三行代码可以解决你想用的enum问题。

<enum name='NSApplicationActivationPolicyRegular' value='0' />
<enum name='NSApplicationActivationPolicyAccessory' value='1' />
<enum name='NSApplicationActivationPolicyProhibited' value='2' /> 

需要注意的是,像这样修改PyObjC,可能意味着你得把更新后的版本静态链接并包含到你的应用程序中去分发,因为其他人的机器上没有这些数据。最好是编译最新版本的PyObjC(这个版本会包含这些更新和其他功能),然后使用它。

撰写回答