2

如何以编程方式更改 Mac 菜单栏中的应用程序标题(启动应用程序后)?

我知道我可以在通过 Info.plist 文件中的 CFBundleName 运行程序之前设置它。但是,我需要在初始化应用程序后对其进行更改。操作我自己的 Info.plist 也行不通。

没有官方的 API 可以这样做,但是在这个讨论中有人暗示有一个秘密的函数调用可以改变包名称/菜单栏标题:

“如果你足够努力地寻找它,你可以使用 SPI,但我不会向任何人指出它,除非他们能证明他们为什么需要使用它 :-)”

我认为 Java 也使用了类似的东西。那么秘密 API 是什么?

4

1 回答 1

1

好的,我找到了方法。这是 Python 中的代码(取自此处)。它可以使用一些清理和一些错误处理,但它可以工作。关键是来自 ApplicationServices 的未记录的 CPSSetProcessName。

def _osx_set_process_name(app_title):
    """ Change OSX application title """

    from ctypes import cdll, c_int, pointer, Structure
    from ctypes.util import find_library

    app_services = cdll.LoadLibrary(find_library("ApplicationServices"))

    if app_services.CGMainDisplayID() == 0:
        print "cannot run without OS X window manager"
    else:
        class ProcessSerialNumber(Structure):
            _fields_ = [("highLongOfPSN", c_int),
                        ("lowLongOfPSN", c_int)]
        psn = ProcessSerialNumber()
        psn_p = pointer(psn)
        if (  (app_services.GetCurrentProcess(psn_p) < 0) or
              (app_services.SetFrontProcess(psn_p) < 0) ):
           print "cannot run without OS X gui process"

        print "setting process name"
        app_services.CPSSetProcessName(psn_p, app_title)

    return False

如果您立即调用它,它会更改活动监视器中的进程名称。由于某种原因,我不得不在小超时后调用它来更改菜单栏名称:

import gobject
gobject.timeout_add(100, _osx_set_process_name, "MyTitle")

请注意,如果您将它与 .app 包结合使用,您可以获得非常好的 Python 应用程序系统集成。虽然您可以更改图标、Finder 显示名称...,但我尝试的所有方法都将 CFBundleName(菜单栏中的那个)保留为“Python”。(例如,此答案仅更改了长名称(显示在停靠图标上)。还有很多其他的几乎可以工作。)

While this answer gives the intended result, it's not very elegant. I'd appreciate some insight into why I need the timeout... I think Python or pygtk changes the process name itself when I first import gtk or run the main loop.

于 2013-01-02T13:41:02.943 回答