diff --git a/ToggleProxy.py b/ToggleProxy.py index 7db5745..80c29a7 100644 --- a/ToggleProxy.py +++ b/ToggleProxy.py @@ -8,6 +8,15 @@ import commands, re, time class ToggleProxy(NSObject): def applicationDidFinishLaunching_(self, notification): + # define some title-related stuff + self.active_color = NSColor.colorWithSRGBRed_green_blue_alpha_(0, 0.5, 0, 1) + self.inactive_color = NSColor.colorWithSRGBRed_green_blue_alpha_(0.6, 0, 0, 1) + self.title_font = NSFont.fontWithName_size_('HelveticaNeue-Bold', 12.0) + + # find image files + self.active_image = NSImage.imageNamed_("active") + self.inactive_image = NSImage.imageNamed_("inactive") + # make status bar item self.statusitem = NSStatusBar.systemStatusBar().statusItemWithLength_(NSVariableStatusItemLength) self.statusitem.retain() @@ -16,23 +25,20 @@ class ToggleProxy(NSObject): self.statusitem.setHighlightMode_(False) self.statusitem.setEnabled_(True) - # define some title-related stuff - self.active_color = NSColor.colorWithSRGBRed_green_blue_alpha_(0, 0.5, 0, 1) - self.inactive_color = NSColor.colorWithSRGBRed_green_blue_alpha_(0.6, 0, 0, 1) - self.title_font = NSFont.fontWithName_size_('HelveticaNeue-Bold', 12.0) - # start working self.loadNetworkServices() self.watchForProxyChanges() self.updateProxyStatus() def loadNetworkServices(self): + """ load list of network services, the easy way """ self.services = {} output = commands.getoutput("/usr/sbin/networksetup listnetworkserviceorder") for service, device in re.findall(r'Hardware Port:\s*(.*?), Device:\s*(.*?)\)', output): self.services[device] = service def watchForProxyChanges(self): + """ install a watcher for proxy changes """ store = SCDynamicStoreCreate(None, "name.klep.toggleproxy", self.proxyStateChanged, None) SCDynamicStoreSetNotificationKeys(store, None, [ 'State:/Network/Global/Proxies' ]) @@ -41,32 +47,39 @@ class ToggleProxy(NSObject): CFRunLoopAddSource(loop, source, kCFRunLoopCommonModes) def proxyStateChanged(self, store, keys, info): + """ callback for watcher """ self.updateProxyStatus() def updateProxyStatus(self): + """ update proxy status """ proxydict = SCDynamicStoreCopyProxies(None) interface = proxydict['__SCOPED__'].keys()[0] status = proxydict['__SCOPED__'][interface] self.active = status.get('HTTPEnable', False) and True or False self.device = interface - title = NSAttributedString.alloc().initWithString_attributes_( - "Proxy %sactive" % (not self.active and "in" or ""), { - # NSFontAttributeName : self.title_font, - NSForegroundColorAttributeName : self.active and self.active_color or self.inactive_color, - } - ) - self.statusitem.setAttributedTitle_(title) + # set image + self.statusitem.setImage_( self.active and self.active_image or self.inactive_image ) + + # set tooltip if self.active: tooltip = "Proxy active on %s:%s" % ( proxydict.get('HTTPProxy', '??'), proxydict.get('HTTPPort', '??') ) else: - tooltip = "" + tooltip = "Proxy is not active" self.statusitem.setToolTip_(tooltip) def toggleProxy_(self, sender): + """ callback for clicks on menu item """ + event = NSApp.currentEvent() + + # Ctrl pressed? if so, quit + if event.modifierFlags() & NSControlKeyMask: + NSApp.terminate_(self) + return + servicename = self.services.get(self.device) if not servicename: NSLog("device '%s' not found in services?" % self.device) diff --git a/resources/active.png b/resources/active.png new file mode 100644 index 0000000..0f9c6b1 Binary files /dev/null and b/resources/active.png differ diff --git a/resources/inactive.png b/resources/inactive.png new file mode 100644 index 0000000..d8db76c Binary files /dev/null and b/resources/inactive.png differ diff --git a/resources/menuicon.psd b/resources/menuicon.psd new file mode 100644 index 0000000..ba337c4 Binary files /dev/null and b/resources/menuicon.psd differ diff --git a/setup.py b/setup.py index 97f78bf..1cf7b35 100644 --- a/setup.py +++ b/setup.py @@ -4,6 +4,10 @@ import py2app, sys, os, commands setup( app = [ 'ToggleProxy.py' ], + data_files = [ + 'resources/active.png', + 'resources/inactive.png' + ], options = dict(py2app = dict( plist = dict( LSBackgroundOnly = True