如何用Cocoa和Python (PyObjC)创建状态栏项目?

9 投票
2 回答
2758 浏览
提问于 2025-04-11 09:24

我在XCode里创建了一个全新的项目,AppDelegate.py文件里有以下内容:

from Foundation import *
from AppKit import *

class MyApplicationAppDelegate(NSObject):
    def applicationDidFinishLaunching_(self, sender):
        NSLog("Application did finish launching.")

        statusItem = NSStatusBar.systemStatusBar().statusItemWithLength_(NSVariableStatusItemLength)
        statusItem.setTitle_(u"12%")
        statusItem.setHighlightMode_(TRUE)
        statusItem.setEnabled_(TRUE)

但是,当我启动应用程序时,状态栏里没有任何项目显示出来。main.py和main.m里的其他代码都是默认的。

2 个回答

6

上面提到的使用.retain()是必要的,因为statusItem在applicationDidFinishLaunching()方法返回时会被销毁。你可以把这个变量作为MyApplicationAppDelegate实例中的一个字段,用self.statusItem来代替。

下面是一个修改过的例子,不需要使用.xib等文件...

from Foundation import *
from AppKit import *
from PyObjCTools import AppHelper

start_time = NSDate.date()


class MyApplicationAppDelegate(NSObject):

    state = 'idle'

    def applicationDidFinishLaunching_(self, sender):
        NSLog("Application did finish launching.")

        self.statusItem = NSStatusBar.systemStatusBar().statusItemWithLength_(NSVariableStatusItemLength)
        self.statusItem.setTitle_(u"Hello World")
        self.statusItem.setHighlightMode_(TRUE)
        self.statusItem.setEnabled_(TRUE)

        # Get the timer going
        self.timer = NSTimer.alloc().initWithFireDate_interval_target_selector_userInfo_repeats_(start_time, 5.0, self, 'tick:', None, True)
        NSRunLoop.currentRunLoop().addTimer_forMode_(self.timer, NSDefaultRunLoopMode)
        self.timer.fire()

    def sync_(self, notification):
        print "sync"

    def tick_(self, notification):
        print self.state


if __name__ == "__main__":
    app = NSApplication.sharedApplication()
    delegate = MyApplicationAppDelegate.alloc().init()
    app.setDelegate_(delegate)
    AppHelper.runEventLoop()
5

我为了让它正常工作,做了以下几件事:

  1. 打开 MainMenu.xib 文件。确保应用程序代理的类是 MyApplicationAppDelegate。我不确定你是否也需要这样做,但我做了。之前设置错了,所以应用程序代理根本没有被调用。

  2. 添加 statusItem.retain(),因为它会立即被自动释放。

撰写回答